---
title: "How do I call Ballet playbooks from Google ADK?"
description: "TL;DR: Use the Agent Development Kit's McpToolset with StreamableHTTPConnectionParams to connect to Ballet's MCP endpoint, or define a FunctionTool that calls the execute endpoint. Point the toolset at https://app.ballet.dev/mcp with an Authorization header and add it to your agent's tools."
canonical_url: "https://docs.ballet.dev/articles/how-do-i-call-ballet-playbooks-from-google-adk-jxG6oinH4u"
md_url: "https://docs.ballet.dev/articles/how-do-i-call-ballet-playbooks-from-google-adk-jxG6oinH4u.md"
---
# How do I call Ballet playbooks from Google ADK?

**TL;DR:** Use the Agent Development Kit's `McpToolset` with `StreamableHTTPConnectionParams` to connect to Ballet's MCP endpoint, or define a `FunctionTool` that calls the execute endpoint. Point the toolset at `https://app.ballet.dev/mcp` with an `Authorization` header and add it to your agent's `tools`.

## Who this is for

Python developers building agents with Google's Agent Development Kit (ADK).

## Option A: Connect with McpToolset

Attach an `McpToolset` configured for remote Streamable HTTP. The toolset imports Ballet's tools and manages the connection lifecycle.

```python
from google.adk.agents import LlmAgent
from google.adk.tools.mcp_tool import McpToolset, StreamableHTTPConnectionParams
import os

ballet_tools = McpToolset(
    connection_params=StreamableHTTPConnectionParams(
        url="https://app.ballet.dev/mcp",
        headers={"Authorization": f"Bearer {os.environ['BALLET_API_TOKEN']}"},
    ),
    # optional: restrict which tools the agent can call
    tool_filter=["list_playbooks", "run_playbook", "get_run"],
)

root_agent = LlmAgent(
    model="gemini-2.5-flash",
    name="ops_agent",
    instruction="You run Ballet playbooks to complete operational tasks.",
    tools=[ballet_tools],
)
```

Use `McpToolset` (lowercase "c"); the older `MCPToolset` spelling is deprecated. For per-request auth, pass a `header_provider` callable instead of static `headers`.

## Option B: Define one playbook as a FunctionTool

To expose a single playbook, wrap the REST execute endpoint in a function and register it as a tool.

```python
import json, os, httpx
from google.adk.agents import LlmAgent

async def run_onboarding(customer_id: str) -> dict:
    """Run the customer onboarding playbook in Ballet."""
    url = f"https://app.ballet.dev/api/playbooks/{os.environ['BALLET_PLAYBOOK_ID']}/execute"
    headers = {
        "Authorization": f"Bearer {os.environ['BALLET_API_TOKEN']}",
        "Content-Type": "application/json",
    }
    run = None
    async with httpx.AsyncClient(timeout=None) as http:
        async with http.stream("POST", url, headers=headers,
                               json={"input": {"customerId": customer_id}}) as res:
            async for line in res.aiter_lines():
                if line.startswith("data:"):
                    event = json.loads(line[5:].strip())
                    if event.get("type") == "run_stop":
                        run = event["run"]
    return {"success": run and run.get("success"), "output": run and run.get("output")}

root_agent = LlmAgent(
    model="gemini-2.5-flash",
    name="onboarding_agent",
    instruction="Use run_onboarding to onboard new customers.",
    tools=[run_onboarding],
)
```

ADK wraps a plain function as a tool automatically. See [Run playbooks over the REST API](/articles/how-do-i-run-a-playbook-over-the-rest-api-KQIz0apagm) for event details.

## Which option should I use?

- **McpToolset** — expose all (or a filtered set of) playbooks to the agent.
- **FunctionTool** — expose one playbook with an explicit signature.

## Related articles

- [How do I use Ballet playbooks in an agent framework?](/articles/how-do-i-use-ballet-playbooks-in-an-agent-framework-q3PWTx18lY)
- [The MCP endpoint](/articles/how-do-i-connect-to-ballets-mcp-endpoint-1ydPKBzHZm)
- [Run playbooks over the REST API](/articles/how-do-i-run-a-playbook-over-the-rest-api-KQIz0apagm)
