Chapter 3
20 min read
Section 22 of 175

Claude Agent SDK Deep Dive

How Claude Code Works

Introduction

The Claude Agent SDK is Anthropic's official toolkit for building Claude-powered agents. It provides the building blocks used by Claude Code and offers a clean API for creating your own agentic applications.

Why the SDK: The Claude Agent SDK encapsulates best practices for building agents with Claude. Instead of reinventing patterns, you can leverage battle-tested components.

SDK Overview

Key Features

  • Agent loop management: Built-in orchestration with retries and error handling
  • Tool system: Declarative tool definitions with type safety
  • Computer use: Built-in tools for browser and desktop control
  • Memory: Conversation management and context handling
  • Streaming: Real-time output for responsive interfaces

Installation

install.sh
1# Python installation
2pip install anthropic
3
4# The Agent SDK is part of the anthropic package
5from anthropic import Agent

Core Concepts

The Agent Class

🐍agent_basics.py
1from anthropic import Agent
2from anthropic.tools import ComputerTool, BashTool, TextEditorTool
3
4# Create an agent with tools
5agent = Agent(
6    model="claude-sonnet-4-20250514",
7    tools=[
8        BashTool(),           # Execute shell commands
9        TextEditorTool(),     # Edit files
10        ComputerTool(),       # Browser and desktop control
11    ],
12    system_prompt="""
13You are a helpful coding assistant.
14Use the available tools to accomplish tasks.
15Always verify your work after making changes.
16""",
17)
18
19# Run the agent
20result = agent.run("Create a Python script that fetches weather data")
21print(result.output)

Tool Definitions

Tools are defined with schemas that tell Claude how to use them:

🐍tool_definitions.py
1from anthropic.tools import Tool
2from pydantic import BaseModel
3
4class SearchParams(BaseModel):
5    query: str
6    max_results: int = 10
7
8class WebSearchTool(Tool):
9    """Search the web for information."""
10
11    name = "web_search"
12    description = "Search the web and return relevant results"
13    input_schema = SearchParams
14
15    def execute(self, params: SearchParams) -> str:
16        # Implementation
17        results = search_api.search(params.query, params.max_results)
18        return self.format_results(results)
19
20    def format_results(self, results: list) -> str:
21        lines = []
22        for r in results:
23            lines.append(f"- {r['title']}: {r['url']}")
24            lines.append(f"  {r['snippet']}")
25        return "\n".join(lines)

Messages and Conversation

🐍conversation.py
1from anthropic import Agent, Conversation
2
3# Create a persistent conversation
4conversation = Conversation()
5
6# First interaction
7agent = Agent(model="claude-sonnet-4-20250514")
8response = agent.run(
9    "Create a todo list app",
10    conversation=conversation,
11)
12
13# Continue the conversation (agent remembers context)
14response = agent.run(
15    "Add a feature to mark items as complete",
16    conversation=conversation,
17)
18
19# Access conversation history
20for message in conversation.messages:
21    print(f"{message.role}: {message.content[:100]}...")

Building Agents

Basic Agent Pattern

🐍basic_agent.py
1from anthropic import Agent
2from anthropic.tools import BashTool, TextEditorTool
3
4def create_coding_agent():
5    """Create a basic coding agent."""
6    return Agent(
7        model="claude-sonnet-4-20250514",
8        tools=[
9            BashTool(),
10            TextEditorTool(),
11        ],
12        system_prompt="""
13You are a senior software engineer.
14Your job is to help write, debug, and improve code.
15
16Guidelines:
17- Always read files before modifying them
18- Run tests after making changes
19- Explain what you're doing and why
20""",
21        max_iterations=50,
22    )
23
24# Usage
25agent = create_coding_agent()
26result = agent.run("Add input validation to the user signup form")
27
28if result.success:
29    print(f"✓ Task completed: {result.summary}")
30else:
31    print(f"✗ Task failed: {result.error}")

Agent with Custom Tools

🐍custom_tools_agent.py
1from anthropic import Agent
2from anthropic.tools import Tool
3from pydantic import BaseModel
4
5# Define custom tools
6class GitParams(BaseModel):
7    command: str
8
9class GitTool(Tool):
10    name = "git"
11    description = "Run git commands"
12    input_schema = GitParams
13
14    def execute(self, params: GitParams) -> str:
15        import subprocess
16        result = subprocess.run(
17            ["git"] + params.command.split(),
18            capture_output=True,
19            text=True,
20        )
21        return result.stdout + result.stderr
22
23
24class DatabaseParams(BaseModel):
25    query: str
26
27class DatabaseTool(Tool):
28    name = "database_query"
29    description = "Run SQL queries against the database"
30    input_schema = DatabaseParams
31
32    def execute(self, params: DatabaseParams) -> str:
33        # Safety check
34        if self.is_destructive(params.query):
35            return "Error: Destructive queries require explicit approval"
36        return self.db.execute(params.query)
37
38
39# Create agent with custom tools
40agent = Agent(
41    model="claude-sonnet-4-20250514",
42    tools=[
43        GitTool(),
44        DatabaseTool(),
45        BashTool(),
46        TextEditorTool(),
47    ],
48    system_prompt="You are a DevOps assistant with git and database access.",
49)

Streaming Agent Output

🐍streaming_agent.py
1from anthropic import Agent
2
3agent = Agent(
4    model="claude-sonnet-4-20250514",
5    tools=[...],
6)
7
8# Stream responses
9async for event in agent.run_stream("Refactor the auth module"):
10    match event.type:
11        case "text":
12            print(event.text, end="", flush=True)
13        case "tool_start":
14            print(f"\n[Using {event.tool_name}]")
15        case "tool_result":
16            print(f"[{event.tool_name} completed]")
17        case "complete":
18            print(f"\n✓ Done: {event.summary}")

Working with Tools

Built-in Tools

ToolPurposeCapabilities
BashToolExecute shell commandsRun any bash command, capture output
TextEditorToolEdit filesCreate, modify, view files
ComputerToolGUI controlBrowser automation, screenshots, clicks

BashTool in Detail

🐍bash_tool_usage.py
1from anthropic.tools import BashTool
2
3# Default configuration
4bash = BashTool()
5
6# With custom configuration
7bash = BashTool(
8    timeout=300,           # Max seconds per command
9    working_dir="/app",    # Default working directory
10    env={                  # Environment variables
11        "NODE_ENV": "development",
12    },
13    allowed_commands=[     # Whitelist (optional)
14        "npm", "git", "python", "pytest",
15    ],
16)
17
18# The tool handles:
19# - Command execution
20# - Output capture (stdout + stderr)
21# - Timeout handling
22# - Exit code interpretation

TextEditorTool in Detail

🐍text_editor_usage.py
1from anthropic.tools import TextEditorTool
2
3editor = TextEditorTool()
4
5# The tool supports these operations:
6# - view: Read file contents
7# - create: Create new file
8# - str_replace: Replace text in file
9# - insert: Insert text at line
10
11# Claude calls it like:
12# {
13#   "command": "view",
14#   "path": "/app/src/main.py"
15# }
16
17# Or for edits:
18# {
19#   "command": "str_replace",
20#   "path": "/app/src/main.py",
21#   "old_str": "def old_function():",
22#   "new_str": "def new_function():"
23# }

ComputerTool in Detail

🐍computer_tool_usage.py
1from anthropic.tools import ComputerTool
2
3# Computer tool for GUI automation
4computer = ComputerTool(
5    display_width=1920,
6    display_height=1080,
7)
8
9# Capabilities:
10# - screenshot: Capture current screen
11# - click: Click at coordinates
12# - type: Type text
13# - key: Press key combinations
14# - scroll: Scroll the page
15# - move: Move mouse cursor
16
17# Example: Claude can browse the web
18agent = Agent(
19    model="claude-sonnet-4-20250514",
20    tools=[ComputerTool()],
21)
22
23result = agent.run(
24    "Go to github.com and find the anthropic-sdk-python repository"
25)

ComputerTool Safety

ComputerTool gives the agent control of a computer. Only use it in sandboxed environments (containers, VMs) when running untrusted tasks.

Advanced Patterns

Multi-Agent Orchestration

🐍multi_agent.py
1from anthropic import Agent
2
3# Create specialized agents
4researcher = Agent(
5    model="claude-sonnet-4-20250514",
6    system_prompt="You are a research specialist. Find and summarize information.",
7    tools=[WebSearchTool(), ReadFileTool()],
8)
9
10coder = Agent(
11    model="claude-sonnet-4-20250514",
12    system_prompt="You are a coding specialist. Implement features and fix bugs.",
13    tools=[BashTool(), TextEditorTool()],
14)
15
16reviewer = Agent(
17    model="claude-sonnet-4-20250514",
18    system_prompt="You are a code reviewer. Check for bugs and improvements.",
19    tools=[ReadFileTool(), BashTool()],
20)
21
22# Orchestration
23async def implement_feature(spec: str):
24    # Research phase
25    research = await researcher.run(
26        f"Research best practices for: {spec}"
27    )
28
29    # Implementation phase
30    implementation = await coder.run(
31        f"Implement this feature: {spec}\n\nResearch: {research.output}"
32    )
33
34    # Review phase
35    review = await reviewer.run(
36        f"Review the implementation for: {spec}"
37    )
38
39    return {
40        "research": research,
41        "implementation": implementation,
42        "review": review,
43    }

Error Handling and Retries

🐍error_handling.py
1from anthropic import Agent
2from anthropic.exceptions import ToolExecutionError, AgentTimeoutError
3
4agent = Agent(
5    model="claude-sonnet-4-20250514",
6    tools=[...],
7    max_iterations=50,
8    retry_config={
9        "max_retries": 3,
10        "backoff_factor": 2,
11        "retry_on": [ToolExecutionError],
12    },
13)
14
15try:
16    result = agent.run(
17        "Deploy the application to production",
18        timeout=600,  # 10 minutes max
19    )
20except ToolExecutionError as e:
21    print(f"Tool failed: {e.tool_name} - {e.message}")
22except AgentTimeoutError:
23    print("Agent took too long")
24except Exception as e:
25    print(f"Unexpected error: {e}")

Checkpointing and Resume

🐍checkpointing.py
1from anthropic import Agent, Checkpoint
2
3agent = Agent(
4    model="claude-sonnet-4-20250514",
5    tools=[...],
6    checkpoint_interval=5,  # Save state every 5 iterations
7)
8
9# Start with checkpointing
10result = agent.run(
11    "Complete the migration",
12    checkpoint_dir="./checkpoints",
13)
14
15# Resume from checkpoint if interrupted
16agent = Agent.from_checkpoint("./checkpoints/latest")
17result = agent.resume()

Use Checkpoints for Long Tasks

For tasks that might take hours (large refactors, migrations), enable checkpointing. This allows resuming if the process is interrupted.

Summary

The Claude Agent SDK provides:

  1. Agent class: Orchestrates the agent loop with tools
  2. Built-in tools: Bash, TextEditor, Computer for common operations
  3. Custom tools: Easy-to-define tools with Pydantic schemas
  4. Streaming: Real-time output for responsive interfaces
  5. Advanced: Multi-agent, error handling, checkpointing
Chapter Complete: You now understand how Claude Code works under the hood. In the next chapter, we'll explore how OpenAI Codex takes a different approach with cloud-based sandboxed execution.