> ## Documentation Index
> Fetch the complete documentation index at: https://notes.kodekloud.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Integrating BigQuery via MCP Toolbox

> Shows how to integrate BigQuery with an LLM agent using the MCP Toolbox to run SQL, inspect schema, and perform churn analysis with filtered tools.

It's Monday morning in week 2 and Claire's question is still pinned to the corner of your screen:\
Which five accounts have the sharpest usage drops?

The MCP Toolbox lives in your project folder and publishes nine tools. Your agent must now choose the right ones to complete the churn analysis. The good news: most of your architecture stays the same.

![A slide titled "What Doesn't Change" showing three teal rounded squares labeled "Model" (brain icon), "Churn Agent" (robot icon), and "Runner" (circular arrows). Arrows show flow from Model to Churn Agent and from Runner back to the Churn Agent.](https://mintcdn.com/kodekloud-c4ac6d9a/YiW0Xl5gQ25uff6L/images/AI-Agents-For-Data-Analytics/Building-Agent-With-BigQuery/Integrating-BigQuery-via-MCP-Toolbox/model-churn-agent-runner-feedback.jpg?fit=max\&auto=format\&n=YiW0Xl5gQ25uff6L\&q=85\&s=dd3a8f49ef5aa8961847d7742c5b7afc)

What doesn't change: the model (LiteLLM, pointing to Claude via API), and the runner (an in-memory runner with the same session and async loop). The only difference is that the agent now receives an MCP toolset (the Toolbox) instead of plain Python functions. The model still drives the logic; the Toolbox supplies scoped capabilities (SQL execution, schema inspection, forecasting, etc.).

## High-level setup

At a glance you wire the toolset into the agent just like any other tool:

```python theme={null}
bigquery_tools = MCPToolset(...)
agent = LlmAgent(
    model=model,
    instruction=INSTRUCTION,
    tools=[bigquery_tools],
)
```

MCPToolset is ADK’s bridge to the MCP server (the Toolbox). In this example the toolset is configured to start the Toolbox as a subprocess using a stdio connection:

```python theme={null}
bigquery_tools = MCPToolset(
    connection_params=StdioConnectionParams(
        server_params=StdioServerParameters(
            command="./toolbox",
            args=["--prebuilt", "bigquery", "--stdio"],
            env={**os.environ, "BIGQUERY_PROJECT": PROJECT},
        ),
    ),
    tool_filter=["execute_sql", "get_table_info"],
)
```

### What each connection parameter means

| Parameter | Purpose | Example / notes |
| - | -: | - |
| `command` | Path to the Toolbox binary | `./toolbox` |
| `args` | Plugin selection and connection mode | `["--prebuilt", "bigquery", "--stdio"]` |
| `env` | Environment for the subprocess (credentials, project) | `{**os.environ, "BIGQUERY_PROJECT": PROJECT}` |
| `tool_filter` | Tools to expose to the model | `["execute_sql", "get_table_info"]` |

Pass `os.environ` into the subprocess environment so the Toolbox can inherit your credentials and authenticate to BigQuery.

The `tool_filter` is important: every tool you hand to the model is a potential distraction. For churn analysis the agent needs to read the schema and run queries — so that’s what you expose.

## Instruction: the agent’s working context

Give the model the table and the columns it should consider. The instruction string becomes the agent’s working context:

```python theme={null}
INSTRUCTION = """
Table: analytics.customer_features
Columns: customer_id, region, plan_tier, usage_30d,
    usage_delta_30d, support_tickets_90d, tenure_days
"""
```

If you prefer automatic discovery, omit the `Columns:` stanza and keep `get_table_info` in the toolset so the agent can inspect the table before querying (example below).

## Running the agent — an example session

When you run the script you’ll see the Toolbox start and the ADK filter the tools the agent receives:

```bash theme={null}
$ python churn_agent.py
[toolbox] Initialized 9 tools (--prebuilt bigquery --stdio)
[adk] tool_filter → 2 tools: execute_sql, get_table_info
```

Ask the agent about a specific customer and it will decide whether to call `execute_sql`. For example:

You: Is customer cust-0003115 at risk?\
agent → execute\_sql

The agent composes and issues the SQL itself:

```sql theme={null}
SELECT * FROM analytics.customer_features
WHERE customer_id = 'cust-0003115';
```

The row comes back via the Toolbox. The agent reads the signals and reports a verdict:

```bash theme={null}
→ 1 row  usage_30d=0.11  usage_delta_30d=-26.86  support_tickets_90d=5
Agent: high risk. Usage 0.11, delta -26.86 — a collapse in usage.
5 support tickets in 90 days • 1 recommended retention action
```

## Answering Claire: Which five accounts have the sharpest drops?

Ask the agent directly and it will construct the ORDER BY / LIMIT query on `usage_delta_30d`:

You: Which five accounts have the sharpest usage drops right now?\
agent → execute\_sql

```sql theme={null}
SELECT customer_id, usage_delta_30d FROM analytics.customer_features
ORDER BY usage_delta_30d ASC LIMIT 5;
```

Example agent output (truncated for brevity):

```bash theme={null}
cust-0031142    -32.41
cust-0003115    -26.86
cust-0019827    -19.33
cust-0042210    -1.00
cust-002771...   -X.XX
```

Because the agent can query the table directly, follow-up questions such as “Clarify churn next week” are handled by changing the query or adding a WHERE clause — the model composes the SQL for you.

## Letting the agent discover schema automatically

If you want the agent to inspect the table itself, remove the explicit column list and keep `get_table_info` in the toolset. The agent will call `get_table_info` first, learn the schema, and then run queries:

```python theme={null}
INSTRUCTION = """
Table: analytics.customer_features
"""

tool_filter = ["execute_sql", "get_table_info"]
```

## Expanding agent capabilities with additional Toolbox tools

The Toolbox exposes more than SQL. Add analytics tools like `forecast` or `ask_data_insights` and the agent can perform time-series forecasting or automated insight generation without you hand-coding those analyses:

```python theme={null}
INSTRUCTION = """
Table: analytics.customer_features
"""

tool_filter = [
    "execute_sql",
    "get_table_info",
    "forecast",
    "ask_data_insights",
]
```

Or point the agent at a different table by changing the `Table:` line in `INSTRUCTION`. The MCP Toolbox plus tool filtering gives you a compact way to surface only the capabilities the model needs while letting the model drive SQL and analyses.

## Links & references

* BigQuery docs: [https://cloud.google.com/bigquery](https://cloud.google.com/bigquery)
* ADK / MCP Toolbox: refer to your Toolbox distribution or internal docs for download and prebuilt plugin details

Carefully scope the `tool_filter` and subprocess environment. Exposing unnecessary tools or leaking credentials into the subprocess can increase security risk. Use least privilege for production deployments.

> **[Watch Video](https://learn.kodekloud.com/user/courses/ai-agents-for-data-analytics/module/4e6bc78e-00a8-405d-97ce-830c7892b1b1/lesson/52d81209-1e09-47f8-b559-240edd7517d9)**

> **[Practice Lab](https://learn.kodekloud.com/user/courses/ai-agents-for-data-analytics/module/4e6bc78e-00a8-405d-97ce-830c7892b1b1/lesson/33600170-0019-483b-93e1-25f5c023ba30)**


This documentation is built and hosted on [Mintlify](https://mintlify.com), a developer documentation platform.