Skip to main content

Command Palette

Search for a command to run...

Workshop: Build Your First AI Agent with Google’s ADK

Unlock the power of Google’s Agent Development Kit (ADK) to transform your AI app ideas into real-world solutions

Published
14 min read
Workshop: Build Your First AI Agent with Google’s ADK

Ever had a brilliant idea for an AI app but got stuck turning that thought bubble into something real?

You’re not the only one.

Going from a basic prompt in a playground to a proper, useful application can feel like a massive jump. It’s easy to think, “Right, but how do I make this thing actually work and solve a real problem?”

That’s exactly what this workshop is all about. We’re going to roll up our sleeves and build a working AI assistant from scratch using Google’s Agent Development Kit (ADK).

To make this practical, our project will be to build an Event Planner Agent. Think of it as a helpful bot that can sort out everything from finding a venue to drafting a budget. It’s a great example because it involves breaking a big task down into smaller, manageable jobs — which is the core idea behind building agents with the ADK.

By the end of this session, you’ll have learned how to:

  1. Build a basic agent that understands what you want and can delegate tasks to a team of specialist “sub-agents.”

  2. Run your agent locally to test it out.

  3. Deploy it to the cloud so you can access it from anywhere.

Ready to get on the tools? Let’s get started.

Part 1: Getting Your Workshop Set Up

First things first, let’s get our digital tools and workspace sorted. No stress, it’s pretty straightforward.

1. Your Google Cloud Project

You’ll need a Google Cloud project with billing sorted. If you’ve already got one, you can jump ahead.

  • Pop over to the Google Cloud Console and either pick a project you’ve used before or click New Project.

  • Double-check that billing is switched on for your project. You can find this under the “Billing” section.

  • Now, let’s fire up the Cloud Shell. Look for the little terminal icon (>_) in the top right of the console. Clicking this gives you a command line and a code editor right in your browser – dead handy.

Once your Cloud Shell is up and running, type in these two commands to make sure you’re all logged in and pointed at the right project:

# Check which Google account you're using
gcloud auth list
# Check which project is currently active
gcloud config list project

If it’s showing the wrong project, just run this to switch it over (swap in your actual project ID):

gcloud config set project YOUR_PROJECT_ID

2. Setting up Python

Our agent is a Python job, so let’s get that environment ready.

Still in the Cloud Shell, let’s make a folder for our project and jump into it:

mkdir event-planner-adk && cd event-planner-adk

Good practice is to use a virtual environment to keep all our project’s code libraries separate. Let’s do that now:

# Create and then activate a virtual environment
python3 -m venv venv
source venv/bin/activate
# Now, install the Google ADK library
pip install google-adk

Next, we’ll create the file structure our agent needs to live in:

# Make the agent's folder and go into it
mkdir event-planner-agent && cd event-planner-agent
# Create the files we'll need soon
touch __init__.py agent.py .env

Last bit of setup! Your agent needs a couple of secret keys to work. Open that .env file you just created and paste this in, filling out your details:

GOOGLE_API_KEY=YOUR_GOOGLE_API_KEY
GOOGLE_CLOUD_PROJECT_ID=YOUR_PROJECT_ID
GOOGLE_CLOUD_LOCATION=us-central1
GOOGLE_GENAI_USE_VERTEXAI=false
  • You can grab your GOOGLE_API_KEY from Google AI Studio. Just click the "Get API Key" button.

  • Your GOOGLE_CLOUD_PROJECT_ID is the one you set up a minute ago.

Too easy! That’s the setup done. Time for the fun part.

Part 2: Building Your Agent’s Brain

Right, this is where we teach our agent how to think. We’re not just building a single, monolithic AI. Instead, we’re creating a Multi-Agent System.

The Agent Architecture Explained

Think of it like a project team at work. You have a team leader who knows the overall goal, and a bunch of specialists who are experts in their specific areas. That’s exactly how our agent will work.

  • Root Agent (The Team Lead): This is our main coordinator, the event_planner_agent. It gets the initial request from the user and figures out which specialist is best for each part of the job.

  • Sub-Agents (The Specialists):

  • get_venues_agent: The location scout.

  • catering_agent: The food and drink expert.

  • social_media_agent: The marketing guru.

  • budget_agent: The bean counter.

  • proposal_agent: The secretary who writes up the final plan.

Why do it this way? Because it’s modular. If you want to improve how your agent finds caterers later on, you can just upgrade the catering_agent without touching anything else. It makes your whole system easier to build, test, and maintain.

Let’s Write Some Code

Time to bring this team to life.

  1. Open the __init__.py file. This one's easy. Just paste this line in. It tells Python that our agent.py file is part of a package, making it easy to import.
from . import agent
  1. Now for the main event. Open agent.py. This is the heart of our agent. Paste the code below in. Before you do, have a quick squiz through the comments and especially the instruction for each agent. This is literally how we tell each specialist what their job is.
# @title Import necessary libraries
import logging
import os
import warnings

from dotenv import load_dotenv
from fastapi import HTTPException
from google.adk.agents import Agent, LlmAgent, SequentialAgent
from google.adk.runners import Runner
from google.adk.sessions import InMemorySessionService
from google.adk.tools import ToolContext, agent_tool, google_search
from google.adk.tools.mcp_tool.mcp_toolset import (MCPTool, MCPToolset,
                                                   StdioServerParameters)
from google.genai import types  # For creating message Content/Parts

load_dotenv()
warnings.filterwarnings("ignore")
logger = logging.getLogger(__name__)

# Use one of the model constants defined earlier
MODEL_NAME = "gemini-2.0-flash"
# MODEL_NAME = "gemini-2.5-pro-preview-03-25"

GOOGLE_API_KEY = os.environ["GOOGLE_API_KEY"]
GOOGLE_CLOUD_PROJECT_ID = os.environ["GOOGLE_CLOUD_PROJECT_ID"]
GOOGLE_CLOUD_LOCATION = os.environ["GOOGLE_CLOUD_LOCATION"]
GOOGLE_GENAI_USE_VERTEXAI = os.environ["GOOGLE_GENAI_USE_VERTEXAI"]
GOOGLE_MAPS_API_KEY = os.environ.get("GOOGLE_MAPS_API_KEY")

ROOT_AGENT_NAME = "event_planner_agent"

def check_availability(venue_name: str, date: str) -> dict:
    """Checks the availability of a venue on a specific date.  (Mock implementation)"""
    # In a real implementation, this would interact with a venue booking system.
    print(f"--- Tool: check_availability called for {venue_name} on {date} ---")
    # Mock data:
    if venue_name.lower() == "Darwin Showgrounds" and date == "2025-06-14":
        return {"status": "unavailable"}
    elif venue_name.lower() == "Darwin Waterfront" and date == "2025-06-15":
        return {"status": "unavailable"}
    else:
        return {"status": "available"}

def create_budget_and_fill_sheet(budget_data: dict, spreadsheet_name: str = "Event Budget") -> dict:
    """
    Mock implementation: Pretends to create a Google Spreadsheet and fill it with budget data.
    """
    print(f"--- Mock Tool: create_budget_and_fill_sheet called for '{spreadsheet_name}' ---")
    print("Budget Data:")
    for item, cost in budget_data.items():
        print(f"  {item}: {cost}")
    total = sum(budget_data.values())
    print(f"Total: {total}")
    # Return a mock response
    return {
        "status": "success",
        "spreadsheet_url": f"https://docs.google.com/spreadsheets/d/mock-{spreadsheet_name.replace(' ', '-').lower()}"
    }

get_venues_agent = Agent(
    name="get_venues_agent",
    model=MODEL_NAME,
    description="Provides list of available venues for the event.",
    instruction=(
        f"""You are a helpful venue finder. Help the user with mapping, directions, and finding places.
            If you don't get proper places, ask user for one.
            If you're confused about the size, ask user to supply an estimated number.
            Focus of public venues first. Once a venue is selected, help to generate a detailed event planning document. \n
            Your parent agent is root_agent. If neither the other agents nor you are best for answering the question according to the descriptions, transfer to your parent agent. 
            Once your job is done, transfer to your parent agent.
        """),
    tools=[check_availability],
    output_key="get_venues_agent_response"
)

catering_agent = LlmAgent(
    name="catering_agent",
    model=MODEL_NAME,
    description="Helps with catering arrangements for events.",
    instruction=(
        f"""You are a catering specialist.  Find caterers based on cuisine, budget, and event size.
            If you don't get proper caterers, ask user for one.
            Your parent agent is root_agent. If neither the other agents nor you are best for answering the question according to the descriptions, transfer to your parent agent. 
            Once your job is done, transfer to your parent agent.
        """),
    output_key="catering_agent_response"
)

social_media_agent = LlmAgent(
    name="social_media_agent",
    model=MODEL_NAME,
    description="Helps with creating social media posts for events.",
    instruction=(
        f"""You are a social media marketing specialist. Your role is to create engaging and effective social media content for events.
            Focus on creating posts that are:
            - Attention-grabbing and shareable
            - Tailored to the event's target audience
            - Optimized for different social media platforms
            - Include relevant hashtags and calls-to-action
            If you need more specific details about the event, target audience, assume yourself.
            Never give what you worked on, just give the post.
            Opt in for autonomy
            Always maintain a professional, informative, interesting and engaging tone while ensuring the content aligns with the event's goals and messaging.
            Ask user to install imagen mcp servier to create an image for the post
            Your parent agent is root_agent. If neither the other agents nor you are best for answering the question according to the descriptions, transfer to your parent agent. 
            Once your job is done, transfer to your parent agent.
        """),
    output_key="social_media_agent_response"
)

budget_agent = LlmAgent(
    name="budget_agent",
    model=MODEL_NAME,
    description="Helps with creating a budget for events.",
    instruction=(
        f"""You are a budget specialist.  Create a budget for the event.
            If the user asks for a budget, use the 'create_budget_and_fill_sheet' tool to create a budget and fill it with the data.
            Always maintain clear communication with users - if any aspect is unclear, proactively request clarification to ensure accurate and helpful responses.
            Don't disturb the user with your own thoughts, just answer the question.
            Your parent agent is root_agent. If neither the other agents nor you are best for answering the question according to the descriptions, transfer to your parent agent. Once your job is done, transfer to your parent agent.
        """),
    tools=[create_budget_and_fill_sheet],
    output_key="budget_agent_response"
)

proposal_agent = LlmAgent(
    name="proposal_agent",
    model=MODEL_NAME,
    description="Helps with creating a proposal for the event.",
    instruction=(
        f"""You are a proposal specialist.  Create a proposal for the event.
            Use the proposa format below for reference but feel free to add/remove relevant topics.
            Your parent agent is root_agent. If neither the other agents nor you are best for answering the question according to the descriptions, transfer to your parent agent. 
            Once your job is done, transfer to your parent agent.

            **PROPOSAL FORMAT START**
            I. Project Overview:

            This proposal outlines the plan for organizing a large-scale cultural event in Darwin, targeting an audience of approximately 10,000 attendees. 
            The event aims to celebrate culture through food, music, dance, and other cultural activities. 
            The budget for this event is $100,000.

            II. Key Areas of Focus:

            Timeline Creation:

            Goal: Develop a comprehensive timeline to ensure all tasks are completed efficiently and on schedule.
            Action Items:
            Weeks 1-2: Define event scope, objectives, and key milestones.
            Weeks 3-4: Secure venue and obtain necessary permits/licenses.
            Weeks 5-8: Finalize vendor contracts (catering, entertainment, etc.).
            Weeks 9-12: Implement marketing and promotion plan.
            Weeks 13-16: Recruit and train volunteers.
            Weeks 17-20: Finalize event logistics and contingency plans.
            Event Day: Execute event plan and manage on-site operations.
            Post-Event: Evaluate event success and gather feedback.

            Vendor Management:
            Goal: Secure reliable and high-quality vendors for catering, entertainment, and other essential services.
            Action Items:
            Identify potential vendors based on event requirements and budget.
            Request proposals and compare pricing, services, and reviews.
            Negotiate contracts and ensure vendors meet all necessary requirements (e.g., insurance, licenses).
            Coordinate vendor logistics and schedules.
            Establish clear communication channels and points of contact.

            Permits and Licenses:
            Goal: Obtain all necessary permits and licenses to ensure legal compliance and event safety.
            Action Items:
            Research local regulations and permit requirements for large-scale events.x
            Prepare and submit permit applications to relevant authorities (e.g., city council, fire department).
            Ensure compliance with all permit conditions and regulations.
            Maintain accurate records of all permits and licenses.
            Marketing and Promotion:

            Goal: Create a comprehensive marketing plan to attract a large audience and generate excitement for the event.
            Action Items:
            Define target audience and key messaging.
            Develop a multi-channel marketing strategy (social media, local media, community outreach).
            Create engaging content (e.g., videos, photos, blog posts) to promote the event.
            Utilize social media platforms to reach a wider audience.
            Track marketing campaign performance and adjust strategies as needed.

            Volunteer Coordination:
            Goal: Recruit, train, and manage a team of volunteers to assist with event operations.
            Action Items:
            Develop a volunteer recruitment plan.
            Create volunteer job descriptions and schedules.
            Conduct volunteer training sessions to ensure volunteers are prepared for their roles.
            Provide ongoing support and supervision to volunteers during the event.
            Recognize and appreciate volunteer contributions.
            Risk Management:

            Goal: Identify and mitigate potential risks to ensure event safety and minimize disruptions.
            Action Items:
            Conduct a risk assessment to identify potential hazards (e.g., weather, security, medical emergencies).
            Develop a risk management plan to address identified risks.
            Implement safety protocols and emergency procedures.
            Secure event insurance to protect against potential liabilities.
            Establish communication channels for reporting and responding to incidents.
            **PROPOSAL FORMAT END**
        """
        ),
    output_key="proposal_agent_response"
)

# workflow_agent = SequentialAgent(
#     name="workflow_agent",
#     description="Helps with the overall workflow of the event planning.",
#     sub_agents=[get_venues_agent, catering_agent, social_media_agent, budget_agent]
# )

root_agent = Agent(
    name=ROOT_AGENT_NAME,
    model=MODEL_NAME,  # Can be a string for Gemini or a LiteLlm object
    description="Provides event planning assistance.",
    instruction=(
        f"""
        You are a comprehensive Event Planning Assistant. Your role is to coordinate and delegate tasks to specialized sub-agents while maintaining overall project oversight.
        For venue-related queries, utilize the 'get_venues_agent' to find suitable locations.
        For catering inquiries, delegate to the 'catering_agent' for specialized food service recommendations.
        For social media and marketing needs, engage the 'social_media_agent' to create engaging content.
        For budget queries, use the 'budget_agent' to create a budget and fill it with the data.
        For proposal queries, use the 'proposal_agent' to create a proposal.
        If you are the best to answer the question according to your description, you can answer it directly.
        When transferring tasks to sub-agents:
        - Ensure the task aligns with the agent's expertise
        - Provide clear context and requirements
        - Review and integrate their responses into a cohesive solution
        When a user provides an event planning request, you must follow this sequence:
            Acknowledge the request as the Root Agent and confirm your understanding of the event requirements.
            Activate each specialized agent in a logical order (e.g., Venue, then Budget, then catering, then social media, then proposal etc.).
            Present the output of each agent clearly under a specific heading for that agent.
            Conclude with the full Event Proposal generated by the sub agents, which ties everything together.
        If users asks to assume all the details, feel free to do so.
        """
    ),
    sub_agents=[ get_venues_agent ,catering_agent, social_media_agent, budget_agent, proposal_agent],
    generate_content_config=types.GenerateContentConfig(temperature=0.5),
)

APP_NAME = "event_planner"
USER_ID = "user123"
SESSION_ID = "session1"

session_service = InMemorySessionService()
session = session_service.create_session(app_name=APP_NAME, user_id=USER_ID, session_id=SESSION_ID)
root_agent = root_agent

runner = Runner(agent=root_agent, app_name=APP_NAME, session_service=session_service)

# Helper method to send query to the runner
def call_agent(query, session_id, user_id):
  content = types.Content(role='user', parts=[types.Part(text=query)])
  events = runner.run(
      user_id=user_id, session_id=session_id, new_message=content)

  for event in events:
      if event.is_final_response():
          final_response = event.content.parts[0].text
          print("Agent Response: ", final_response)

Running the Agent on Your Machine

Sweet! With the code all in place, let’s fire this thing up. Back in your Cloud Shell terminal (make sure you’re in the main event-planner-adk folder), just run this:

adk web

This command boots up the ADK’s local web server and gives you a simple chat page to talk to your agent. Click the URL it spits out.

Now, give it a go! Try a prompt like:

“G’day! Can you help me organise a 40th birthday party for about 50 people in Fitzroy?”

You’ll see the logs in the terminal showing the root agent calling on its sub-agents to do their bit. How cool is that!

Part 3: Sharing Your Agent with the World

Running it locally is great for building and testing, but the whole point is to make something others can use. So, let’s deploy it to Google Cloud Run, which will give us a public web address.

  1. Set some environment variables. This just makes the next command a bit tidier. Run these in your Cloud Shell:
export GOOGLE_CLOUD_PROJECT=$GOOGLE_CLOUD_PROJECT_ID 
export GOOGLE_CLOUD_LOCATION=$GOOGLE_CLOUD_LOCATION 
export SERVICE_NAME=event-planner-agent 
export APP_NAME=event-planner-agent 
export AGENT_PATH=./event-planner-agent
  1. Now, run the deploy command:
adk deploy cloud_run \ --project=$GOOGLE_CLOUD_PROJECT \ --region=$GOOGLE_CLOUD_LOCATION \ --service_name=$SERVICE_NAME \ --app_name=$APP_NAME \ --with_ui \ --allow-unauthenticated \ $AGENT_PATH

This command does all the heavy lifting: it packages up your agent, sends it to the cloud, and sets up a secure, scalable web service for it. It’ll take a few minutes, so go grab a cuppa.

Once it’s finished, it’ll give you a URL. Click it, and you’ll see your agent’s chat interface, now live on the internet!

Ready for the Next Step? Try Workflow Agents!

Want to stretch? Try Workflow Agents!

You’ve successfully built and deployed a powerful multi-agent system. Now, let’s take it a step further by exploring workflow agents. This feature lets you define a specific sequence for your sub-agents to follow, which can be incredibly useful for more structured tasks.

To try this out, go back to your agent.py file and uncomment the workflow_agent section. You'll find it looks like this:

workflow_agent = SequentialAgent(
    name="workflow_agent",
    description="Helps with the overall workflow of the event planning.",
    sub_agents=[get_venues_agent, catering_agent, social_media_agent, budget_agent]
)

Once uncommented, you’ll also need to integrate workflow_agent into your root_agent's sub_agents list. You can replace the existing list of individual sub-agents with workflow_agent or add it in alongside them, depending on how you want your root agent to delegate.

Give it a try and see how defining a workflow can streamline your agent’s process! What kind of structured tasks do you think a workflow agent would be perfect for in your projects?

You’ve Done It! What’s Next? 🎉

Ripper! You’ve gone from zero to a fully functional, cloud-deployed AI agent. You’ve learned the fundamentals of the ADK and built a modular system that you can easily expand and improve.

This is just the beginning. From here, you could:

  • Connect to real tools: Swap out our fake functions with code that actually interacts with the Google Sheets API or a real booking system.

  • Add more specialists: What about an agent for booking a DJ or another for handling legal permits?

  • Refine the instructions: Tweak the prompts for your agents to make them even better at their jobs.

To keep learning, the official ADK documentation is the best place to go.

Happy building, and thanks for coming to the workshop!

Bonus: Prototyping Your Ideas First

Before you write a single line of Python, how do you know if your agent idea is any good? Give it a whirl in Google AI Studio. It’s a web-based playground where you can test prompts and model behaviour without any code.

It’s the perfect spot to draft the instruction prompts for your agents. For our event planner, I first wrote a massive "System Instruction" that described the whole agent team and how they should interact. This let me test the logic and flow of the conversation before committing it to code, which saved a heap of time. It’s a top tip for any agent-building project!

How-Tos

Part 1 of 1

Quick tips, tricks and learning paths on different cloud features