# openhands.sdk.agent

> API reference for openhands.sdk.agent module

### class Agent

Bases: [`AgentBase`](#class-agentbase)

Main agent implementation for OpenHands.

The Agent class provides the core functionality for running AI agents that can
interact with tools, process messages, and execute actions. It inherits from
AgentBase and implements the agent execution logic.

#### Example

```pycon  theme={null}
>>> from openhands.sdk import LLM, Agent, Tool
>>> llm = LLM(model="claude-sonnet-4-20250514", api_key=SecretStr("key"))
>>> tools = [Tool(name="TerminalTool"), Tool(name="FileEditorTool")]
>>> agent = Agent(llm=llm, tools=tools)
```

#### Properties

* `agent_context`: AgentContext | None
* `condenser`: CondenserBase | None
* `filter_tools_regex`: str | None
* `include_default_tools`: list\[str]
* `llm`: LLM
* `mcp_config`: dict\[str, Any]
* `model_config`: ClassVar\[ConfigDict] = (configuration object)
  Configuration for the model, should be a dictionary conforming to \[ConfigDict]\[pydantic.config.ConfigDict].
* `security_policy_filename`: str
* `system_prompt_filename`: str
* `system_prompt_kwargs`: dict\[str, object]
* `tools`: list\[Tool]

#### Methods

#### init\_state()

Initialize the empty conversation state to prepare the agent for user
messages.

Typically this involves adding system message

NOTE: state will be mutated in-place.

#### model\_post\_init()

This function is meant to behave like a BaseModel method to initialise private attributes.

It takes context as an argument since that’s what pydantic-core passes when calling it.

* Parameters:
  * `self` – The BaseModel instance.
  * `context` – The context.

#### step()

Taking a step in the conversation.

Typically this involves:

1. Making a LLM call
2. Executing the tool
3. Updating the conversation state with

LLM calls (role=”assistant”) and tool results (role=”tool”)

4.1 If conversation is finished, set state.execution\_status to FINISHED
4.2 Otherwise, just return, Conversation will kick off the next step

If the underlying LLM supports streaming, partial deltas are forwarded to
`on_token` before the full response is returned.

NOTE: state will be mutated in-place.

### class AgentBase

Bases: `DiscriminatedUnionMixin`, `ABC`

Abstract base class for OpenHands agents.

Agents are stateless and should be fully defined by their configuration.
This base class provides the common interface and functionality that all
agent implementations must follow.

#### Properties

* `agent_context`: AgentContext | None
* `condenser`: CondenserBase | None
* `filter_tools_regex`: str | None
* `include_default_tools`: list\[str]
* `llm`: LLM
* `mcp_config`: dict\[str, Any]
* `model_config`: ClassVar\[ConfigDict] = (configuration object)
  Configuration for the model, should be a dictionary conforming to \[ConfigDict]\[pydantic.config.ConfigDict].
* `name`: str
  Returns the name of the Agent.
* `prompt_dir`: str
  Returns the directory where this class’s module file is located.
* `security_policy_filename`: str
* `system_message`: str
  Compute system message on-demand to maintain statelessness.
* `system_prompt_filename`: str
* `system_prompt_kwargs`: dict\[str, object]
* `tools`: list\[Tool]
* `tools_map`: dictstr, \[ToolDefinition]
  Get the initialized tools map.
  :raises RuntimeError: If the agent has not been initialized.

#### Methods

#### get\_all\_llms()

Recursively yield unique base-class LLM objects reachable from self.

* Returns actual object references (not copies).
* De-dupes by id(LLM).
* Cycle-safe via a visited set for all traversed objects.
* Only yields objects whose type is exactly LLM (no subclasses).
* Does not handle dataclasses.

#### init\_state()

Initialize the empty conversation state to prepare the agent for user
messages.

Typically this involves adding system message

NOTE: state will be mutated in-place.

#### model\_dump\_succint()

Like model\_dump, but excludes None fields by default.

#### model\_post\_init()

This function is meant to behave like a BaseModel method to initialise private attributes.

It takes context as an argument since that’s what pydantic-core passes when calling it.

* Parameters:
  * `self` – The BaseModel instance.
  * `context` – The context.

#### abstractmethod step()

Taking a step in the conversation.

Typically this involves:

1. Making a LLM call
2. Executing the tool
3. Updating the conversation state with

LLM calls (role=”assistant”) and tool results (role=”tool”)

4.1 If conversation is finished, set state.execution\_status to FINISHED
4.2 Otherwise, just return, Conversation will kick off the next step

If the underlying LLM supports streaming, partial deltas are forwarded to
`on_token` before the full response is returned.

NOTE: state will be mutated in-place.

#### verify()

Verify that we can resume this agent from persisted state.

This PR’s goal is to not reconcile configuration between persisted and
runtime Agent instances. Instead, we verify compatibility requirements
and then continue with the runtime-provided Agent.

Compatibility requirements:

* Agent class/type must match.
* Tools:

  * If events are provided, only tools that were actually used in history
    must exist in runtime.
  * If events are not provided, tool names must match exactly.

All other configuration (LLM, agent\_context, condenser, system prompts,
etc.) can be freely changed between sessions.

* Parameters:
  * `persisted` – The agent loaded from persisted state.
  * `events` – Optional event sequence to scan for used tools if tool names
    don’t match.
* Returns:
  This runtime agent (self) if verification passes.
* Raises:
  `ValueError` – If agent class or tools don’t match.


---

> To find navigation and other pages in this documentation, fetch the llms.txt file at: https://docs.openhands.dev/llms.txt