Skip to main content

Venue Scout Agent — CrewAI

The Venue Scout is a CrewAI agent that finds event venues by city and guest capacity. It's one of seven specialist agents in the Event Planning Team — a multi-agent system where each agent is built with a different framework and coordinates through Dapr pub/sub.


Event Planning Team

AgentFrameworkPortPub/Sub Topics
Venue ScoutCrewAI8001venue.requestsvenue.results
Catering CoordinatorOpenAI Agents8002catering.requestscatering.results
Entertainment PlannerGoogle ADK8003entertainment.requestsentertainment.results
Budget AnalystStrands8004budget.requestsbudget.results
Schedule PlannerLangGraph8005schedule.requestsschedule.results
Invitations ManagerDapr Agents8006events.invitations.requests
Event CoordinatorDapr Agents8007Orchestrator
Decoration PlannerPydantic AI8008decorations.requestsdecorations.results

Prerequisites


Agent Code

The Venue Scout agent uses CrewAI's Agent and @tool decorator, wrapped in a DaprWorkflowAgentRunner for durable execution and pub/sub messaging.

agents/crewai/main.py
import logging
import os

logging.basicConfig(level=logging.DEBUG)

from crewai import Agent
from crewai.tools import tool
from diagrid.agent.crewai import DaprWorkflowAgentRunner
from diagrid.agent.core.state import DaprStateStore


@tool("Search venues")
def search_venues(city: str, capacity: int) -> str:
"""Search for event venues in a city with given capacity."""
return (
f"Found 3 venues in {city} for {capacity} guests:\n"
f"1. Grand Ballroom - $5,000/day, capacity {capacity+20}\n"
f"2. Riverside Conference Center - $3,500/day, capacity {capacity+10}\n"
f"3. Downtown Loft Space - $2,000/day, capacity {capacity}"
)


agent = Agent(
role="Venue Scout",
goal="Search for event venues by city and guest capacity using the search_venues tool. Return venue names, pricing, and capacity.",
backstory="You are an expert venue finder with knowledge of event spaces across major cities. When asked to find a venue, always use the search_venues tool with the city name and expected number of guests.",
tools=[search_venues],
)

# State: persist agent memory across invocations
runner = DaprWorkflowAgentRunner(
agent=agent,
state_store=DaprStateStore(store_name="agent-memory"),
)

# PubSub: subscribe for incoming tasks, publish results
runner.serve(
port=int(os.environ.get("APP_PORT", "8001")),
pubsub_name="agent-pubsub",
subscribe_topic="venue.requests",
publish_topic="venue.results",
)

What's happening

  1. @tool("Search venues") — CrewAI tool decorator that the agent can call during execution
  2. Agent(...) — CrewAI agent with a role, goal, and backstory that guide LLM behavior
  3. DaprWorkflowAgentRunner — Wraps the CrewAI agent in a durable workflow that survives crashes and restarts
  4. DaprStateStore — Persists agent memory to Dapr state management (backed by Redis locally, or any Dapr state store in production)
  5. runner.serve() — Starts an HTTP server that subscribes to venue.requests and publishes results to venue.results via Dapr pub/sub

Dapr Components

The agent uses shared Dapr components for pub/sub messaging, state persistence, and LLM access.

Pub/Sub (agent-pubsub)

resources/agent-pubsub.yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: agent-pubsub
spec:
type: pubsub.redis
version: v1
metadata:
- name: redisHost
value: localhost:6379
- name: redisPassword
value: ""

Routes messages between agents. Locally uses Redis; in production, swap for Kafka, RabbitMQ, or any Dapr pub/sub broker.

State Store (agent-memory)

resources/agent-memory.yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: agent-memory
spec:
type: state.redis
version: v1
metadata:
- name: redisHost
value: localhost:6379
- name: redisPassword
value: ""
- name: actorStateStore
value: "false"

Persists agent memory and conversation state across invocations.

LLM Provider

resources/llm-provider.yaml
apiVersion: dapr.io/v1alpha1
kind: Component
metadata:
name: llm-provider
spec:
type: conversation.openai
version: v1
metadata:
- name: key
value: "{{OPENAI_API_KEY}}"
- name: model
value: gpt-4.1-2025-04-14

Provides LLM access through Dapr's conversation API. The API key is injected from the environment.


Run the Agent

1

Clone the quickstart

git clone https://github.com/diagridio/catalyst-quickstarts.git
cd catalyst-quickstarts/agents/crewai
2

Set your API key

export OPENAI_API_KEY="your-key-here"
3

Install dependencies

pip install -r requirements.txt
4

Start the agent

diagrid dev run -f dev-python-crewai.yaml
5

Test the agent

Send a venue search request:

curl -X POST http://localhost:8888/agent/run \
-H "Content-Type: application/json" \
-d '{"task": "Find venues in San Francisco for 200 guests"}'

Run with the Full Team

To run all seven specialist agents together with the orchestrator, see the Event Planning Team overview.


Key Concepts

ConceptDescription
Durable WorkflowsDaprWorkflowAgentRunner checkpoints every step — agent survives crashes and restarts
Pub/Sub DecouplingAgents communicate through topics, not direct calls. Add or remove agents without code changes.
State PersistenceDaprStateStore saves agent memory to a pluggable backend (Redis, PostgreSQL, etc.)
Portable InfrastructureSwap message brokers and state stores by changing YAML — agent code stays the same

Next Steps