Skip to main content

Pydantic AI

Connect a Pydantic AI agent to Civic. For standalone scripts, use Pydantic AI's native MCPServerStreamableHTTP with a Civic token. For web apps, use per-user Civic Auth tokens.

Prerequisites

  • Python 3.11+
  • A Civic account at app.civic.com with a configured toolkit

Installation

pip install pydantic-ai python-dotenv

Authentication

For standalone scripts and autonomous agents — the simplest path.

Generate a Civic Token

  1. Log in to app.civic.com
  2. Click your account name in the bottom left
  3. Go to Install → MCP URL
  4. Click Generate Token and copy it immediately — it won't be shown again
warning

Never commit your token to source control. Store it in environment variables or a secrets manager. Tokens expire after 30 days.

Set Environment Variables

CIVIC_TOKEN=your-civic-token-here
CIVIC_URL=https://app.civic.com/hub/mcp

For production agents, lock to a specific toolkit by appending a profile parameter:

CIVIC_URL=https://app.civic.com/hub/mcp?profile=your-toolkit-alias

Use the Token

Pass the token as a Bearer token in the Authorization header:

headers = {"Authorization": f"Bearer {os.environ['CIVIC_TOKEN']}"}
headers: { Authorization: `Bearer ${process.env.CIVIC_TOKEN}` }
Full credentials guide

Token generation, URL parameters, OAuth vs token comparison

# .env
CIVIC_TOKEN=your-civic-token-here
ANTHROPIC_API_KEY=your-anthropic-key
import os
import asyncio
from dotenv import load_dotenv
from pydantic_ai import Agent
from pydantic_ai.mcp import MCPServerStreamableHTTP

load_dotenv()

server = MCPServerStreamableHTTP(
"https://app.civic.com/hub/mcp",
headers={"Authorization": f"Bearer {os.environ['CIVIC_TOKEN']}"},
)

agent = Agent("anthropic:claude-sonnet-4-6", mcp_servers=[server])

async def main():
async with agent.run_mcp_servers():
result = await agent.run("List open PRs in civicteam/ai-chatbot")
print(result.output)

asyncio.run(main())
note

Use mcp_servers=[server] — not toolsets=[server]. The mcp_servers parameter is the current Pydantic AI API for MCP connections.

Production Configuration

For production agents, lock to a specific toolkit by adding profile to the MCP URL:

server = MCPServerStreamableHTTP(
f"https://app.civic.com/hub/mcp?profile={os.environ['CIVIC_PROFILE_ID']}",
headers={"Authorization": f"Bearer {os.environ['CIVIC_TOKEN']}"},
)

When a profile is specified, the session is locked by default — the agent cannot switch toolkits or modify its own guardrails. This prevents prompt injection attacks from escaping the defined tool scope.

Reference Implementation

pydantic-ai-reference-implementation-civic

Complete implementation with FastAPI chat UI, streaming responses, and deployment guide

Next Steps