Skip to content

Session Harness Sandbox Separation for Long-Running Agents

Split a long-running agent into three replaceable primitives — Session log, stateless Harness, provisioned Sandbox — so each scales and crash-recovers independently.

The three primitives

A monolithic agent process couples model inference, session state, and execution environment. When any one of them churns — models shift, execution targets multiply, or a crash forces recovery — the others pay the cost. This pattern splits the process along layers whose churn rates differ by orders of magnitude (Anthropic, 2026):

  • Session — an append-only event log of everything that happened. This is the authoritative state, not any in-memory harness object.
  • Harness — a stateless loop that calls the model and routes tool calls. Any harness instance can resume any session through wake(sessionId).
  • Sandbox — a provisioned environment where the agent runs code and edits files. It presents a uniform tool interface whatever the target.
graph TD
    H[Harness: stateless loop] -->|emitEvent| S[Session: append-only log]
    H -->|execute tool| SB[Sandbox: execution env]
    S -->|getEvents| H
    SB -->|tool result| H
    H2[Another harness instance] -.->|wake, resume| S

Stable APIs as the seams

The split works because the interfaces between primitives are narrow and stable. Anthropic documents the reference shape (Anthropic, 2026):

Surface Call Role
Sandbox execute(name, input) Dispatch a tool or MCP call; returns a string result
Sandbox provision({resources}) Spin up the execution environment on demand
Session emitEvent(id, event) Append a durable event to the log
Session getEvents() Slice the event stream positionally for context reconstruction
Harness wake(sessionId) Reboot a harness instance against an existing session

LangChain's Deep Agents Deploy (April 2026) ships the same three-layer architecture on open models and sandboxes: "The high level architecture (harness, agent server, sandboxes) is the same" (LangChain, 2026).

Why statelessness pays

Because the Session, not the Harness, is the source of truth, two properties fall out.

Crash recovery is free. Any other harness can replace a failed one: it calls wake(sessionId) and replays the events. "Any Harness instance can pick up any Session and continue from where it left off. This is what makes horizontal scaling trivial" (Anthropic, 2026).

Inference starts before provisioning finishes. The harness can call the model against the event log while the sandbox is still starting up. Anthropic reports about a 60% p50 and over 90% p95 reduction in time-to-first-token from this decoupling (Anthropic, 2026).

Each layer changes on its own cadence: models over months to a year, harness code session to session, sandboxes per session. Narrow APIs let each layer churn independently — Anthropic draws an operating-system analogy, "the abstractions outlasted the hardware" (Anthropic, 2026).

Security follows the split

Credentials never reach the sandbox. Two patterns hold this invariant (Anthropic, 2026):

  • Resource-bundled auth — git tokens wired into local remotes during provision, then discarded from the sandbox environment
  • Vault-proxied auth — OAuth tokens kept in a credential store the harness reaches through an MCP proxy, so the sandbox sees only tool responses

"The tokens are never reachable from the sandbox where Claude's generated code runs" (Anthropic, 2026). The API shape enforces this separation, not convention.

Many brains, many hands

A stateless harness and a uniform sandbox interface compose into a fan-out. Multiple harnesses attach to overlapping sessions, and one harness dispatches to many kinds of sandbox. "The harness doesn't know whether the sandbox is a container, a phone, or a Pokémon emulator" (Anthropic, 2026). This supports A/B model rollouts, migrations that do not rewrite session logs, and work spread across specialized targets.

When this is overbuilt

The cost exceeds the benefit under three conditions:

  • Short, single-sandbox sessions. You never exercise crash recovery, provisioning is short, and no model migration is planned. A coupled harness is simpler to build and debug.
  • Unbounded log growth without retention. The Session is append-only and grows in step with session length. Long sessions force compaction, and "the standard ways to address this all involve irreversible decisions about what to keep" (Anthropic, 2026).
  • Event-schema evolution. Replay correctness needs a stable event shape. When the schema changes across harness versions, old logs stop replaying under new code, and migration is expensive and error-prone.

For complex multi-agent coordination, "a flat log is fundamentally insufficient" (Yan, Medium, April 2026) — extra memory layers must sit on top of the Session.

Example

A coding agent is asked to migrate a repository from Python 3.10 to 3.12 over a multi-hour run. Midway through, the harness process crashes.

Without virtualized primitives, the in-memory conversation and partial tool results are lost. A new process cannot tell a git clone that was attempted and failed from one that finished. The task restarts from scratch, rerunning destructive operations or producing inconsistent state.

With the Session, Harness, and Sandbox split, recovery follows the log:

  • The Session log holds every event up to the crash: the provision call, each execute("bash", ...) with its return, and every model turn and tool result
  • A replacement harness calls wake(sessionId) and receives the log through getEvents()
  • The sandbox still holds the on-disk state from before the crash, in the same container and filesystem, so the harness reconciles by reading the last few events and resuming at the next tool call
  • Git credentials that set up the remote during provision are not re-exposed to the sandbox, so no credentials leak across the crash boundary

The user sees a brief pause, not a restart. On resume, the model call dominates time-to-first-token, not reprovisioning the sandbox (Anthropic, 2026).

Key Takeaways

  • Three virtualized primitives with narrow APIs: Session (emitEvent, getEvents), Harness (stateless, wake-able), Sandbox (execute, provision)
  • The Session is the source of truth; statelessness of the harness makes crash recovery and horizontal scale fall out of the design
  • TTFT improves because inference starts against the event log in parallel with sandbox provisioning — measured at ~60% p50, >90% p95 reduction by Anthropic
  • Security is structural: credentials never reach the sandbox because the API shape prevents it
  • Overbuilt for short single-sandbox sessions; watch for unbounded log growth and event-schema drift
Feedback