create_deep_agent(
model: str | BaseChatModel | None = | Name | Type | Description |
|---|---|---|
model | str | BaseChatModel | None | Default: NoneThe model to use. Deprecated Specify a model explicitly. Passing Accepts a OpenAI Models and Data Retention If an To disable data retention with the Responses API, use
|
tools | Sequence[BaseTool | Callable | dict[str, Any]] | None | Default: None |
system_prompt | str | SystemMessage | None | Default: None |
middleware | Sequence[AgentMiddleware[StateT_co, ContextT]] | Default: () |
subagents | Sequence[SubAgent | CompiledSubAgent | AsyncSubAgent] | None | Default: None |
skills | list[str] | None | Default: None |
memory | list[str] | None | Default: None |
permissions | list[FilesystemPermission] | None | Default: None |
backend | BackendProtocol | None | Default: None |
interrupt_on | dict[str, bool | InterruptOnConfig] | None | Default: None |
response_format | ResponseFormat[ResponseT] | type[ResponseT] | dict[str, Any] | None | Default: None |
state_schema | type[DeepAgentState] | None | Default: None |
context_schema | type[ContextT] | None | Default: None |
checkpointer | Checkpointer | None | Default: None |
store | BaseStore | None | Default: None |
debug | bool | Default: False |
name | str | None | Default: None |
cache | BaseCache | None | Default: None |
Create a deep agent.
By default, this agent has access to the following tools:
ls, read_file, write_file, edit_file, glob, grep: file operationsexecute: run shell commandstask: call subagentsThe execute tool allows running shell commands if the backend implements
SandboxBackendProtocol.
For non-sandbox backends, the execute tool will return an error message.
Additional tools the agent should have access to.
These are merged with the built-in tool suite listed above
(filesystem tools, execute, and task).
Passing tools here is additive — it never removes a built-in.
To drop a built-in tool, register a
HarnessProfile with
excluded_tools.
Caller-authored system instructions (USER) placed
first in the system prompt sent to the model.
The final authored prompt is assembled as USER -> BASE -> SUFFIX.
BASE is empty unless the active
HarnessProfile defines
base_system_prompt, and SUFFIX is the profile's optional
system_prompt_suffix. Parts are separated by blank lines.
With system_prompt=None and no profile base_system_prompt or
system_prompt_suffix, the model receives an empty authored system
prompt.
Passing a SystemMessage preserves any cache_control markers
on its existing content blocks — useful for explicit Anthropic
prompt-cache breakpoints. When profile content is present, its
assembled BASE and SUFFIX are appended as an additional text
content block after the caller's blocks.
See Prompt assembly for the full case-by-case breakdown.
Additional middleware to apply after the base stack but before the tail middleware. The full ordering is:
Base stack:
SkillsMiddleware (if skills is provided)FilesystemMiddlewareSubAgentMiddleware
(if any inline subagents — declarative
SubAgent or
CompiledSubAgent
— are available)SummarizationMiddlewarePatchToolCallsMiddlewareAsyncSubAgentMiddleware (if async subagents are provided)User middleware is inserted here.
Tail stack:
extra_middleware (if any)_ToolExclusionMiddleware (if profile has excluded_tools)AnthropicPromptCachingMiddleware (unconditional; no-ops for
non-Anthropic models)BedrockPromptCachingMiddleware
when langchain-aws is installed (no-ops for non-Bedrock models)FireworksPromptCachingMiddleware
when langchain-fireworks is installed (no-ops for non-Fireworks models)MemoryMiddleware (if memory is provided)HumanInTheLoopMiddleware (if interrupt_on is provided)After assembly, any entries in the profile's
excluded_middleware are filtered from the final stack. Class
entries match exact type; string entries match
AgentMiddleware.name exactly (e.g. "SummarizationMiddleware"
drops the summarization middleware via its public alias).
Entries that match nothing in the assembled stack raise
ValueError, as does excluding any class in the harness's
protected scaffolding set (e.g.,
FilesystemMiddleware
or SubAgentMiddleware).
To run without the task tool, set
general_purpose_subagent=GeneralPurposeSubagentProfile(enabled=False)
on the active harness profile and pass no synchronous
subagents via subagents=. Async subagents are unaffected.
Subagent specs available to the main agent.
This collection supports three forms:
SubAgent: A declarative synchronous subagent spec.CompiledSubAgent: A pre-compiled runnable subagent.AsyncSubAgent: A remote/background subagent spec.SubAgent entries are invoked through the task tool. They should
provide name, description, and system_prompt, and may also
override tools, model, middleware, interrupt_on, skills,
permissions, and response_format. See interrupt_on below for
inheritance and override behavior.
CompiledSubAgent entries are also exposed through the task tool,
but provide a pre-built runnable instead of a declarative prompt
and tool configuration.
AsyncSubAgent entries are identified by their async-subagent
fields (graph_id, and optionally url/headers) and are routed
into AsyncSubAgentMiddleware instead of SubAgentMiddleware.
They should provide name, description, and graph_id, and may
optionally include url and headers. These subagents run as
background tasks and expose the async subagent tools for launching,
checking, updating, cancelling, and listing tasks.
If no subagent named general-purpose is provided, a default
general-purpose synchronous subagent is added automatically unless
the active harness profile disables it. With no synchronous
subagents in play — none passed and the default disabled via
general_purpose_subagent=GeneralPurposeSubagentProfile(enabled=False)
— the task tool is not exposed. Async subagents are independent.
List of skill source paths (e.g., ["/skills/user/", "/skills/project/"]).
Paths must be specified using POSIX conventions (forward slashes)
and are relative to the backend's root. When using
StateBackend (default), provide skill files via
invoke(files={...}). With FilesystemBackend, skills are loaded
from disk relative to the backend's root_dir. Later sources
override earlier ones for skills with the same name (last one wins).
List of memory file paths (AGENTS.md files) to load
(e.g., ["/memory/AGENTS.md"]).
Display names are automatically derived from paths.
Memory is loaded at agent startup and added into the system prompt.
List of FilesystemPermission rules for the main agent
and its subagents.
Rules are evaluated in declaration order; the first match wins. If no rule matches, the call is allowed.
Each rule's mode can be:
"allow" (default): the call proceeds."deny": the tool returns a permission-denied error."interrupt": the call pauses for human approval via
HumanInTheLoopMiddleware. A HumanInTheLoopMiddleware is
auto-installed when any interrupt-mode rule is present, and the
generated interrupt_on entries are merged with the
interrupt_on argument below (user-supplied entries win per
tool name). Requires a langchain version that supports the
when predicate on InterruptOnConfig.Subagents inherit these rules unless they specify their own
permissions field, which replaces the parent's rules entirely.
FilesystemMiddleware applies these permissions at the tool
level for its built-in filesystem tools, not at the backend
level. Direct backend usage does not currently incorporate
permissions.
Optional backend for file storage and execution.
Pass a Backend instance (e.g. StateBackend()).
For execution support, use a backend that
implements SandboxBackendProtocol.
Mapping of tool names to interrupt configs.
Pass to pause agent execution at specified tool calls for human approval or modification.
This config always applies to the main agent.
For subagents:
SubAgent specs inherit the top-level interrupt_on
config by default.SubAgent provides its own interrupt_on, that
subagent-specific config overrides the inherited
top-level config.CompiledSubAgent runnables do not inherit top-level
interrupt_on; configure human-in-the-loop behavior inside the
compiled runnable itself.AsyncSubAgent specs do not inherit top-level
interrupt_on; configure any approval behavior on the remote
subagent itself.For example, interrupt_on={"edit_file": True} pauses before
every edit.
A structured output response format to use for the agent.
Schema class that defines immutable run-scoped context.
Passed through to create_agent.
Optional Checkpointer for persisting agent state
between runs.
Passed through to create_agent.
Optional store for persistent storage (required if backend
uses StoreBackend).
Passed through to create_agent.
Whether to enable debug mode.
Passed through to create_agent.
The name of the agent.
Passed through to create_agent.
The cache to use for the agent.
Passed through to create_agent.
Custom state schema for the agent graph. Must be a
TypedDict subclass of
DeepAgentState so the
built-in DeltaChannel reducer on messages is preserved.
Generally, prefer defining state extensions with middleware so the extra fields stay scoped to the hooks and tools that use them.
When provided, this schema is used as the base graph schema and
is merged with state schemas contributed by middleware. It is
also forwarded when compiling declarative
SubAgent specs for
the task tool, so subagents see the same custom fields as the
parent.
CompiledSubAgent
runnables do not inherit this schema because they are already
compiled — compile those runnables with a compatible state
schema if they need access to the same custom state fields.
Remote
AsyncSubAgent
specs likewise use the schema configured on the remote graph.
from deepagents.graph import DeepAgentState
class MyState(DeepAgentState):
page_url: str
file_urls: list[str]
agent = create_deep_agent(model=..., state_schema=MyState)