This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository.
- Install dependencies:
make install(requires uv, pre-commit, and deno) - Run all checks:
pre-commit run --all-files - Run tests:
make test - Build docs:
make docsormake docs-serve(local development)
- Run specific test:
uv run pytest tests/test_agent.py::test_function_name -v - Run test file:
uv run pytest tests/test_agent.py -v - Run with debug:
uv run pytest tests/test_agent.py -v -s
Agent System (pydantic_ai_slim/pydantic_ai/agent/)
Agent[AgentDepsT, OutputDataT]: Main orchestrator class with generic types for dependency injection and output validation- Entry points:
run(),run_sync(),run_stream()methods - Handles tool management, system prompts, and model interaction
Model Integration (pydantic_ai_slim/pydantic_ai/models/)
- Unified interface across providers: OpenAI, Anthropic, Google, Groq, Cohere, Mistral, Bedrock, HuggingFace
- Model strings:
"openai:gpt-5","anthropic:claude-sonnet-4-5","google:gemini-2.5-pro" ModelRequestParametersfor configuration,StreamedResponsefor streaming
Graph-based Execution (pydantic_graph/ + _agent_graph.py)
- State machine execution through:
UserPromptNode→ModelRequestNode→CallToolsNode GraphAgentStatemaintains message history and usage trackingGraphRunContextprovides execution context
Tool System (tools.py, toolsets/)
@agent.tooldecorator for function registrationRunContext[AgentDepsT]provides dependency injection in tools- Support for sync/async functions with automatic schema generation
Output Handling
TextOutput: Plain text responsesToolOutput: Structured data via tool callsNativeOutput: Provider-specific structured outputPromptedOutput: Prompt-based structured extraction
Dependency Injection
@dataclass
class MyDeps:
database: DatabaseConn
agent = Agent('openai:gpt-5', deps_type=MyDeps)
@agent.tool
async def get_data(ctx: RunContext[MyDeps]) -> str:
return await ctx.deps.database.fetch_data()Type-Safe Agents
class OutputModel(BaseModel):
result: str
confidence: float
agent: Agent[MyDeps, OutputModel] = Agent(
'openai:gpt-5',
deps_type=MyDeps,
output_type=OutputModel
)This is a uv workspace with multiple packages:
pydantic_ai_slim/: Core framework (minimal dependencies)pydantic_evals/: Evaluation systempydantic_graph/: Graph execution engineexamples/: Example applicationsclai/: CLI tool
- Unit tests:
tests/directory with comprehensive model and component coverage - VCR cassettes:
tests/cassettes/for recorded LLM API interactions - Test models: Use
TestModelfor deterministic testing - Examples testing:
tests/test_examples.pyvalidates all documentation examples - Multi-version testing: Python 3.10-3.13 support
pyproject.toml: Main workspace configuration with dependency groupspydantic_ai_slim/pyproject.toml: Core package with model optional dependenciesMakefile: Development task automationuv.lock: Locked dependencies for reproducible builds
- Model Provider Integration: Each provider in
models/directory implements theModelabstract base class - Message System: Vendor-agnostic message format in
messages.pywith rich content type support - Streaming Architecture: Real-time response processing with validation during streaming
- Error Handling: Specific exception types with retry mechanisms at multiple levels
- OpenTelemetry Integration: Built-in observability support
- Local docs:
make docs-serve(serves at http://localhost:8000) - Docs source:
docs/directory (MkDocs with Material theme) - API reference: Auto-generated from docstrings using mkdocstrings
macOS Note: The docs build uses cairosvg for social card generation, which requires the cairo C library. On macOS with Homebrew, Python may fail to locate the library. Fix by setting the library path:
export DYLD_FALLBACK_LIBRARY_PATH="/opt/homebrew/lib"
export PKG_CONFIG_PATH="/opt/homebrew/lib/pkgconfig:/opt/homebrew/share/pkgconfig"
uv run mkdocs build # or mkdocs serve- Package manager: uv (fast Python package manager)
- Lock file:
uv.lock(commit this file) - Sync command:
make syncto update dependencies - Optional extras: Define groups in
pyproject.tomloptional-dependencies
This is the list of best practices for working with the codebase.
When asked to rename a class, you need to rename the class in the code and add a deprecation warning to the old class.
from typing_extensions import deprecated
class NewClass: ... # This class was renamed from OldClass.
@deprecated("Use `NewClass` instead.")
class OldClass(NewClass): ...In the test suite, you MUST use the NewClass instead of the OldClass, and create a new test to verify the
deprecation warning:
def test_old_class_is_deprecated():
with pytest.warns(DeprecationWarning, match="Use `NewClass` instead."):
OldClass()In the documentation, you should not have references to the old class, only the new class.
Always reference Python objects with the "`" (backticks) around them, and link to the API reference, for example:
The [`Agent`][pydantic_ai.agent.Agent] class is the main entry point for creating and running agents.Every pull request MUST have 100% coverage. You can check the coverage by running make test.