OpenHands architecture: stateless event-driven design

Blog 15 min read

Autonomous software engineering has moved past the theoretical phase. OpenHands scores approximately 77% on SWE-Bench Verified using Claude Sonnet 4.5. The secret isn't a magical new model; it's an architecture that treats code as the universal action and confines mutable state to a single ConversationState. This design allows an LLM to run for hours, recover from its own errors, and complete complex tasks with just a few thousand lines of Python.

The core mechanism is an append-only EventLog. This log maintains robustness without the bloat of external orchestration layers. Whether the Workspace is a local process or a Docker container, it executes commands while the core agent logic remains immutable and portable via LiteLLM.

The market has noticed. OpenTechHub lists the project at exactly 78,800 stars with a green activity status as of June 30, 2026. While competitors drown in bespoke tool definitions, this approach proves that giving an agent basic bash and file editing capabilities yields superior engineering outcomes. The following sections detail the blueprint for building autonomous systems that prioritize observable execution over opaque reasoning.

The Mental Model of OpenHands as a Stateless Event-Driven Agent

OpenHands V1 Stateless Architecture: Agent, Conversation, Workspace, Event Stream

The EventLog is the immutable single source of truth. Starting Nov 2025, the V1 architecture replaced the monolithic V0 design with four distinct roles. An Agent now acts as a pure function mapping history to the next Action, possessing zero internal state. This constraint forces all components to remain immutable Pydantic models, leaving the Conversation as the sole owner of mutable state in the entire loop.

Collapsing the explicit `AgentController` and `Runtime` abstractions into the simplified Conversation and Workspace pair marked the shift from V0 to V1. Configuration complexity dropped notably, ditching the hundreds of fields previously required. Executing commands happens via local processes or isolated sandbox environments using Docker through the Workspace, which returns standardized Observations. Decoupling agent logic from the intelligence layer keeps the system model-agnostic, letting teams swap between high-performance and cost-effective LLMs dynamically.

Reconstructing all context awareness from the event stream rather than caching it in memory is the cost of such strict separation. Data volume passed to the LLM per turn increases under this model. Deterministic replay and strong parallelization become possible capabilities that stateful controllers cannot match. Inspecting every prompt and response as a typed event gives builders the power to debug production agents with far greater tractability.

Executing Engineering Tasks via Append-Only EventLog and LocalWorkspace

Persistent engineering workflows execute by wrapping every interaction as an immutable Event containing a unique ID and timestamp. A few thousand lines of Python enable an LLM to run for hours, recover from errors, and finish complex tasks without human intervention. The append-only EventLog records every Action emitted by the stateless Agent and every resulting Observation from the environment. Entries are never edited, ensuring a complete audit trail for debugging.

Execution occurs within a LocalWorkspace or an isolated Docker container. Arbitrary commands cannot damage the host system while full filesystem access remains available. The agent can retry failed bash commands or Python scripts indefinitely because each error message feeds back into the context window as a new observation event. Agent logic remains distinct from the intelligence layer, so teams switch between high-cost models and lower-cost options dynamically.

Tension exists between context completeness and token costs due to reliance on an append-only log. Full history enables self-correction, yet unchecked growth eventually hits provider limits. Compression strategies like the Condenser become necessary for builders to maintain long-running sessions efficiently. Replayability takes priority over raw speed, allowing operators to reconstruct exact failure states from the event stream alone.

Stateless Agent vs Traditional Stateful Loops in OpenHands V1

A stateless Agent reading strictly from an append-only event log replaces mutable agent memory in OpenHands V1. Traditional stateful loops often trap autonomous systems in infinite recursion when internal state updates conflict with external observations. Hidden state drift disappears by functioning as a pure function from history to next Action. Auxiliary services including Stuck Detection and Persistence consume the stream without mutating data directly, ensuring the Conversation remains the single source of truth. This design allows the system to resolve over 53% of real-world GitHub issues on the SWE-bench Verified benchmark when paired with strong models. V1 collapses control logic into the loop runner, unlike V0 which relied on a complex AgentController with hundreds of configuration fields.

Serializing every observation as an event adds latency to high-frequency tool calls. This constraint enables Docker sandboxes to restart mid-task without losing context since the workspace simply re-hydrates from the log. Deterministic debugging capabilities become available to builders, a feature absent in architectures where state hides inside the agent process.

Inside the Canonical Agent Loop and Action Observation Protocol

The Five Phases of the Agent.step Function

Execution within the V1 SDK follows a rigid five-step sequence inside `Agent.step` to resolve tasks autonomously. The cycle starts by clearing any confirmed actions waiting in the queue, preventing old operations from blocking fresh inputs. Next, the system checks for a UserPromptSubmit hook that might intercept or alter the message stream before further processing. Phase three constructs the LLM prompt, a moment where the Condenser activates if token counts near their ceiling. The fourth step invokes the LLM using built-in retry logic designed specifically to catch `LLMContextWindowExceedError` and avoid total collapse during large context windows. Finally, the agent classifies the response and dispatches tool calls, content, or reasoning outputs to their correct handlers.

This structure supports a full agentic loop capable of finishing complex engineering work without step-by-step supervision. Separating prompt construction from execution lets the system handle `LLMContextWindowExceedError` gracefully instead of crashing. Builders adopting this pattern must include exponential backoff in phase four to avoid hitting provider rate limits. Strict ordering prevents race conditions where observations arrive before actions are fully logged. Deterministic flow allows the system to run for hours without human intervention.

Typed Pydantic Models for Actions and Observations

Strict interaction schemas govern every exchange between agent and environment using typed Pydantic models. Operations remain restricted to specific classes: CmdRunAction runs shell commands while FileEditAction applies code changes using `str_replace_editor` semantics. Delegation happens when the agent calls AgentDelegateAction, spawning a sub-agent for parallel threads on a shared workspace. An AgentFinishAction explicitly ends the loop once objectives are met. Rigid typing stops the model from hallucinating unsupported tools, a frequent failure point in looser frameworks. Treating delegation as the tool rather than implicit behavior enables complex, multi-stage engineering tasks without context loss. Separating action definition from execution logic lets the same agent code run against local processes or remote Docker containers interchangeably. Explicit schemas reduce error rates during autonomous operation.

Verbosity is the limitation here; every state change demands full object serialization instead of a simple function call. This overhead enables the append-only EventLog to serve as a deterministic single source of truth for debugging.

Sub-Agent Delegation vs Parent Context Pollution

Parallel dispatch via `ThreadPoolExecutor` isolates verbose `grep` outputs from the parent's EventLog. Triggering an AgentDelegateAction spawns independent threads that share the Workspace filesystem but keep distinct observation histories. Sub-agents inherit the parent's LLM configuration yet prevent context window pollution by filtering raw outputs before merging final summaries. Engineers can run concurrent diagnostic tasks without bloating the primary prompt with redundant file contents. Parallel threads ensure the parent agent receives only distilled conclusions rather than accumulating intermediate results linearly. Increased memory overhead is the constraint for maintaining multiple thread states simultaneously. This approach prevents local context overflow but does not reduce total token usage across the system. Enterprise deployments using Kubernetes for orchestration can scale this pattern to handle complex, multi-file engineering problems efficiently. The following table contrasts the two delegation modes:

Feature Sequential Delegation Parallel Delegation
Context Growth Linear accumulation Isolated per thread
Execution Time Additive latency Concurrent completion
Output Visibility Full intermediate logs Summarized returns
Resource Use Lower memory footprint Higher thread overhead

Unbounded context growth directly triggers LLMContextWindowExceedError conditions in long-running sessions. OpenHands treats sub-agent outputs as transient data rather than permanent conversation history. The parent agent remains agile enough to pivot strategies based on high-level feedback rather than raw data. Workflows should prioritize result synthesis over intermediate step visibility. The full agentic loop stays transparent while internal mechanics hide noisy details from the primary decision path.

Memory Compression and Stuck Detection for Strong Execution

LLMSummarizingCondenser Mechanics and 80-Event Threshold

OpenHands prevents context window overflow during extended autonomous sessions by enforcing an 80-event ceiling through the `LLMSummarizingCondenser`. The default policy sets `max_size = 80` and `keep_first = 4`, a configuration that retains critical initial instructions while discarding intermediate noise. Once the visible event count surpasses this limit, the system invokes a cheaper LLM to summarize middle events, preserving only the first four entries and the most recent ones. This mechanism directly addresses the finite context constraints of underlying models without requiring manual intervention or session resets.

Conceptual illustration for Memory Compression and Stuck Detection for Strong Execution
Conceptual illustration for Memory Compression and Stuck Detection for Strong Execution

Preserving the initial events maintains the original task definition, while keeping recent entries ensures the agent reacts to immediate feedback. Relying on a secondary LLM for summarization introduces additional latency and API costs during high-volume execution phases. The cost is explicit: the system sacrifices raw token fidelity for sustained operational continuity, preventing `LLMContextWindowExceedError` crashes. Compression occurs proactively on every step check, meaning context window management remains continuous rather than reactive to failure states alone.

Triggering Condensation via Proactive Checks and ContextWindowExceedError

Memory compression activates through proactive size validation on every execution step or reactively upon `LLMContextWindowExceedError` signals. The system continuously monitors the event stream length, triggering the LLMSummarizingCondenser before the underlying model rejects the prompt due to token limits. This dual-trigger architecture ensures that long-horizon tasks, such as resolving complex GitHub issues, proceed without manual session resets or data loss. By deferring to a cheaper LLM for summarization only when necessary, the framework optimizes operational costs tied to actual usage rather than fixed seat licenses.

Relying solely on reactive triggers risks interrupting the agentic loop if the error handling itself consumes excessive context. Operators must configure the proactive threshold conservatively to account for variable observation sizes in Docker sandboxes. Unlike static truncation, this event-driven approach preserves the logical continuity required for multi-step engineering work. A slight latency increase occurs during summarization phases, yet this remains acceptable given the alternative of total task failure. Builders should prioritize proactive configuration to maintain the smooth autonomy expected of modern software-engineering agents.

Cost Efficiency: 2x API Spend Reduction vs Quality Preservation

Separating agent logic from the intelligence layer reduces API spend by approximately 2× with no quality loss, according to the V1 paper. This efficiency stems from offloading memory compression to cheaper models while reserving high-performance endpoints for complex reasoning tasks. Operators retain full control over spending by selecting specific LLM providers, directly tying operational costs to actual usage rather than fixed monthly seats. The architecture allows teams to switch between high-cost/high-performance models and lower-cost options dynamically depending on the task complexity.

Self-hosted tasks typically incur roughly $0.15, $0.60 each in API fees when using frontier models for the primary loop. Introducing a secondary model for condensation adds configuration overhead and requires monitoring two distinct API streams for errors. Avoiding vendor lock-in and premium pricing of closed-loop SaaS coding agents often justifies this added operational complexity for enterprise-scale deployments. Builders should implement this pattern when session lengths consistently trigger context limits, as the cost savings compound rapidly over thousands of events.

Deploying Secure Workspaces and Integrating LiteLLM Providers

DockerWorkspace Isolation and the Action Execution Server Stack

OpenHands supports multiple workspace implementations, including `DockerWorkspace`, which encapsulates the agent within a secure boundary rather than running processes directly on the local filesystem. This configuration is necessary for executing untrusted code without compromising the host system.

  1. Initialize the workspace configuration to specify the Docker image and resource limits.
  2. The system launches a container hosting a lightweight FastAPI application known as the Action Execution Server.
  3. This server manages persistent tools, including a tmux session for shell access and an IPython kernel for code interpretation.
  4. A VSCode Server instance runs on a sibling port, allowing developers to attach directly to the live environment for debugging.

Meanwhile, openHands wraps the LLM layer with LiteLLM to ensure provider portability and model agnosticism.

  1. Configure the agent by specifying your chosen LLM provider and API key credentials through the system's configuration interface.
  1. Select a target model from available providers to suit specific software development tasks.
  1. Use the LiteLLM integration to manage provider switching and maintain compatibility across different LLM backends.
  2. Verify connectivity by initiating a task to ensure the agent can successfully communicate with the selected model.

The platform is designed to be model-agnostic, meaning it can interface with any Large Language Model (LLM), allowing for flexible cost and performance configurations depending on the user's choice of provider. Builders can implement retry logic within their provider configuration to mitigate transient connectivity loss, ensuring strong operation during autonomous loops.

LocalWorkspace vs DockerWorkspace: Dev Testing vs Production Security

Select LocalWorkspace for rapid iteration on host filesystems, but switch to DockerWorkspace when executing untrusted code requires strict isolation.

  1. Configure the agent to use the host process space for low-latency unit tests and local file editing.
  2. Deploy the Docker implementation to run a FastAPI Action Execution Server inside a container boundary.
  3. This setup manages a persistent tmux session and IPython kernel while preventing host system compromise.
  4. Operators retain full cost control by connecting personal API keys rather than paying fixed seat licenses.

Organizations increasingly mandate isolated containers locally and at scale to ensure autonomous agents cannot damage underlying infrastructure. The trade-off involves added complexity in managing container lifecycles versus the raw speed of direct process execution. The V1 design principles emphasize optional isolation rather than mandatory sandboxing, giving users the choice based on their trust model.

Feature LocalWorkspace DockerWorkspace
Execution Context Host Process Containerized
Security Model Trusts User Code Isolates Untrusted Code
Best Use Case Development Production

Builders often reserve LocalWorkspace for trusted debugging sessions where filesystem latency matters most. Production systems handling external inputs typically apply containerized boundaries to mitigate arbitrary command execution risks effectively, using the sharp boundaries set in the V1 architecture between the Agent, Conversation, and Workspace components.

About

Priya Nair serves as AI Industry Editor at AI Agents News, where she tracks the business dynamics of autonomous software engineering. Her daily work involves analyzing product launches and platform shifts for tools like Devin and Claude Code, making her uniquely qualified to dissect OpenHands. This article connects her market-level oversight with the technical realities of building agents, translating high-level industry moves into actionable insights for engineers. By examining OpenHands' architecture and SWE-Bench performance, Priya bridges the gap between vendor announcements and practical implementation. Her reporting at AI Agents News ensures that coverage remains grounded in verified data rather than hype, offering builders a neutral assessment of how open-source options compare to commercial alternatives. This perspective helps technical leaders evaluate whether to adopt existing solutions or use frameworks like OpenHands to construct their own agentic workflows.

Conclusion

Scaling autonomous coding agents reveals that raw resolution rates matter less than the operational friction of managing mixed trust environments. While high success metrics on benchmark datasets prove capability, the real challenge emerges when integrating untrusted external code into daily workflows without compromising host integrity. Relying solely on host process execution invites unacceptable risk as agent autonomy expands, yet full containerization for every task introduces latency that kills developer momentum. Teams must adopt a hybrid execution strategy immediately, reserving direct host access strictly for trusted debugging while enforcing container boundaries for all production-grade autonomous loops. This architectural shift ensures that cost efficiency does not come at the expense of system stability. Start by auditing your current agent configurations this week to identify any workflows running unvalidated code outside of isolated environments. Implement a strict policy where any agent interacting with external inputs or third-party repositories must execute within a DockerWorkspace boundary. This proactive segmentation allows organizations to use the power of open-source agents while maintaining a defensible security posture. The path forward requires balancing speed with safety through deliberate architectural choices rather than defaulting to convenience.

Such high engagement indicates a reliable system where builders can find support and plugins for their autonomous agent deployments quickly.

Q: Does the stateless architecture impact token usage or context limits?

A: Reconstructing context from the event stream increases data volume passed to the LLM per turn compared to cached state. Builders must implement memory compression strategies like the Condenser to stay within model limits while maintaining full audit trails.

Q: Can I switch AI providers without rewriting my agent logic?

A: Decoupling agent logic from the intelligence layer keeps the system model-agnostic through LiteLLM integration. Teams can dynamically swap between high-performance and cost-effective options to optimize for either speed or the $0.15, $0.60 task cost range.

Frequently Asked Questions

Self-hosted tasks usually cost between $0.15 and $0.60 per run using frontier models. This low price point allows developers to run approximately 77% of complex SWE-Bench Verified tasks without exceeding small project budgets significantly.

The system resolves over 53% of real-world GitHub issues when paired with strong models like Claude 4.5. This performance level means your agent can handle the majority of standard software engineering benchmarks autonomously and effectively.

OpenTechHub lists the project at exactly 78,800 stars with a green activity status as of June 2026. Such high engagement indicates a robust ecosystem where builders can find support and plugins for their autonomous agent deployments quickly.

Reconstructing context from the event stream increases data volume passed to the LLM per turn compared to cached state. Builders must implement memory compression strategies like the Condenser to stay within model limits while maintaining full audit trails.

Decoupling agent logic from the intelligence layer keeps the system model-agnostic through LiteLLM integration. Teams can dynamically swap between high-performance and cost-effective options to optimize for either speed or the $0.15–$0.60 task cost range.

References