Skip to main content
LangSmith Deployment runs any framework. For agents not built on Deep Agents, LangChain, or LangGraph, deploy using either the deployments-wrap-sdk package (Google ADK) or the LangGraph Functional API (Claude Agent SDK, Strands, CrewAI, AutoGen, and other libraries).
For new builds, consider Deep Agents, an open-source harness for agents that plan, use tools, delegate to subagents, and work over long horizons. Deep Agents deploy directly to LangSmith Deployment, with Managed Deep Agents available for a fully hosted runtime.

Supported frameworks

The following frameworks have end-to-end examples in this guide. Each example exports a LangGraph-compatible graph from agent.py that Agent Server can serve:
Don’t see your framework? The Functional API accepts any callable, so you can apply the same pattern shown in the following examples to any agent library. Wrap your agent’s entrypoint with @task and @entrypoint, then deploy.

How the Functional API works

When a run arrives on Agent Server for a Functional API-wrapped agent:
  1. The platform invokes your @entrypoint-decorated agent function with the run input and any saved state from prior turns on the same thread (passed as the previous argument).
  2. The entrypoint calls your @task-decorated function, which delegates to the framework agent (Claude Agent SDK, Strands, CrewAI, AutoGen, or another library).
  3. The entrypoint returns entrypoint.final(value=..., save=...). The value is the response for this turn; save is the checkpointed state used as previous on the next turn.
  4. Agent Server persists the checkpoint, streams partial output when supported, and records traces when tracing is configured.
This pattern preserves your framework’s execution semantics while giving you standard Agent Server features: durable runs, multi-thread persistence, streaming endpoints, and LangSmith observability.

Prerequisites

Regardless of framework, you need:
  • Python 3.10+ for Functional API frameworks (Strands Agents supports Python 3.9+)
  • A LangSmith API key

General deployment pattern

Follow the same steps for each framework. Choose your stack in the tabs inside each step, combine the snippets in one module (for example agent.py), and export the @entrypoint-decorated function as a module-level variable named agent. The end-to-end example section shows complete files you can copy.
1

Install dependencies

Install Python packages for your framework plus LangGraph and LangSmith.
For Claude Agent SDK:
pip install "langsmith[claude-agent-sdk]" langgraph "langgraph-cli[inmem]"
Set ANTHROPIC_API_KEY in your environment. For an Anthropic API key, refer to the Claude console.
2

Define your agent

Build your agent using the framework of your choice, exactly as you would outside of LangSmith.
from claude_agent_sdk import ClaudeAgentOptions

options = ClaudeAgentOptions(
    model="claude-sonnet-4-6",
    system_prompt="You are a helpful assistant.",
)
3

Wrap with the Functional API

Expose your agent through an @entrypoint-decorated function named agent. Inside, use @task for the unit of work that calls into the framework. Use entrypoint.final() to return the response and persist conversation history across turns on the same thread.
import operator

from claude_agent_sdk import ClaudeSDKClient
from langgraph.func import entrypoint, task

@task
async def invoke_claude(prompt: str) -> str:
    async with ClaudeSDKClient(options=options) as client:
        await client.query(prompt)
        chunks: list[str] = []
        async for message in client.receive_response():
            chunks.append(str(message))
        return "\n".join(chunks)

@entrypoint()
async def agent(messages: list[dict], previous: list[dict] | None = None):
    history = operator.add(previous or [], messages)
    prompt = history[-1]["content"]
    response = await invoke_claude(prompt)
    new_message = {"role": "assistant", "content": response}
    return entrypoint.final(
        value=[new_message],
        save=operator.add(history, [new_message]),
    )
4

Configure tracing

Forward the framework’s native traces to LangSmith. Call tracing setup once at application startup, before creating or invoking agents.
from langsmith.integrations.claude_agent_sdk import configure_claude_agent_sdk

configure_claude_agent_sdk()
For full setup details, see Trace Claude Agent SDK applications.

End-to-end example

The following examples combine agent definition, Functional API wrapping, tracing setup, and export of the agent symbol in a single agent.py file. Pick the tab for your framework.
agent.py
import operator

from claude_agent_sdk import ClaudeAgentOptions, ClaudeSDKClient
from langgraph.func import entrypoint, task
from langsmith.integrations.claude_agent_sdk import configure_claude_agent_sdk

configure_claude_agent_sdk()

options = ClaudeAgentOptions(
    model="claude-sonnet-4-6",
    system_prompt="You are a helpful assistant.",
)

@task
async def invoke_claude(prompt: str) -> str:
    async with ClaudeSDKClient(options=options) as client:
        await client.query(prompt)
        chunks: list[str] = []
        async for message in client.receive_response():
            chunks.append(str(message))
        return "\n".join(chunks)

@entrypoint()
async def agent(messages: list[dict], previous: list[dict] | None = None):
    history = operator.add(previous or [], messages)
    prompt = history[-1]["content"]
    response = await invoke_claude(prompt)
    new_message = {"role": "assistant", "content": response}
    return entrypoint.final(
        value=[new_message],
        save=operator.add(history, [new_message]),
    )
Two things are essential for every example:
  1. Export the @entrypoint-decorated function as agent at module scope. Agent Server imports this symbol when serving the graph.
  2. Return entrypoint.final() with a save argument so conversation state persists across turns on the same thread.

Project layout

A deployable project needs these files:
my-agent/
├── agent.py              # exports the agent graph
├── langgraph.json        # Agent Server config
├── pyproject.toml        # Python dependencies
└── .env                  # Provider credentials and LangSmith variables
langgraph.json points Agent Server at the exported symbol:
langgraph.json
{
  "$schema": "https://langgra.ph/schema.json",
  "dependencies": ["."],
  "graphs": {
    "claude_agent": "./agent.py:agent"
  },
  "env": ".env"
}
pyproject.toml
[project]
name = "my-claude-agent"
version = "0.0.1"
requires-python = ">=3.10"
dependencies = [
    "langsmith[claude-agent-sdk]>=0.3.0",
    "langgraph>=0.4.0",
]
.env
LANGSMITH_API_KEY=your-langsmith-api-key
LANGSMITH_TRACING=true
LANGSMITH_PROJECT=my-claude-agent
ANTHROPIC_API_KEY=your-anthropic-api-key

Install dependencies

From your project directory:
pip install -e .

Enable tracing

Use the framework-specific .env template in Project layout. Agent Server loads this file when "env": ".env" is set in langgraph.json. Set LANGSMITH_PROJECT and your framework provider credentials in that file. For Claude Agent SDK and Strands Agents, also set LANGSMITH_TRACING=true. For CrewAI and AutoGen, tracing is enabled in agent.py through OtelSpanProcessor() and the framework instrumentors, so set LANGSMITH_API_KEY and LANGSMITH_PROJECT only. Traces show agent invocations, tool calls, and LLM interactions in the LangSmith UI. For framework-specific tracing options, see the links in Configure tracing.

Run locally

Start the local Agent Server with the LangGraph CLI:
langgraph dev
If langgraph dev reports that langgraph-api is missing, install langgraph-cli[inmem] in the same environment.
This serves the agent at http://127.0.0.1:2024 and opens LangSmith Studio. Send a request with curl:
langgraph dev may serve on a different port. Check the URL in the terminal output and update the curl commands below if needed.
# Create a thread
THREAD=$(curl -s -X POST http://127.0.0.1:2024/threads \
  -H "Content-Type: application/json" -d '{}' | python -c "import sys, json; print(json.load(sys.stdin)['thread_id'])")

# Run the agent and wait for the final response
curl -s -X POST "http://127.0.0.1:2024/threads/$THREAD/runs/wait" \
  -H "Content-Type: application/json" \
  -d '{
    "assistant_id": "ASSISTANT_ID",
    "input": [{"role": "user", "content": "Hello"}]
  }'
Replace ASSISTANT_ID with the graph key from your langgraph.json graphs object. For example, if your config is "graphs": {"claude_agent": "./agent.py:agent"}, use claude_agent; if your config is "graphs": {"strands_agent": "./agent.py:agent"}, use strands_agent.
Verify that the LangGraph API runs locally before deploying. If langgraph dev fails, deployment to LangSmith will fail as well.

Deploy to LangSmith

Once the agent runs locally, deploy it with langgraph deploy:
langgraph deploy --name my-agent
For environment configuration, deployment types, and revision management, see Deploy to cloud. For self-hosted setups, see Self-hosted deployments. For Docker-only hosting without the control plane, see Deploy standalone.