# How Prime Agent Preserves Session State with Snapshot and Replay on Reconnection

> Discover how Prime Agent uses snapshot and replay to preserve session state on reconnection. Learn how its caching and streaming technology reconstructs conversation history and tool context.

- Repository: [Prime Intellect/prime-agent](https://github.com/PrimeIntellect-ai/prime-agent)
- Tags: how-to-guide
- Published: 2026-08-18

---

**Prime Agent maintains a chunked snapshot transcript cache on the daemon side that streams historical session data to reconnecting clients, enabling the client-side replay engine to reconstruct the full conversation state and tool context before resuming live operations.**

In long-running AI coding sessions, network interruptions and process restarts are inevitable. The Prime Agent system, developed by PrimeIntellect-ai, implements a robust snapshot and replay mechanism that ensures zero data loss when clients reconnect to active sessions. This architecture centers on the `SnapshotTranscriptCache` class, which balances memory efficiency with disk durability to preserve complete session histories including tool results and pending actions.

## The Snapshot Transcript Cache Architecture

When a session initializes, the daemon creates a dedicated `SnapshotTranscriptCache` instance defined in [`packages/coding-agent/src/modes/daemon/snapshot-transcript-cache.ts`](https://github.com/PrimeIntellect-ai/prime-agent/blob/main/packages/coding-agent/src/modes/daemon/snapshot-transcript-cache.ts). If the session already contains messages, the cache immediately encodes them via `encodeMessages()` and marks the cache as complete. As new messages arrive during the session, the daemon appends encoded chunks using `appendEncodedChunk()`, ensuring the transcript remains current for any future reconnections.

### Memory Management and Disk Spilling

The cache implements a two-tier storage strategy to handle varying session sizeswithout exhausting RAM. By default, the cache maintains up to `SNAPSHOT_MEMORY_CACHE_BYTES` (4 MiB) of data in memory. Once this threshold exceeds, the cache automatically spills to temporary files in the configured `cacheRoot` directory. Individual chunks are capped at `SNAPSHOT_TARGET_CHUNK_BYTES` (512 KB), creating a sequence of manageable JSONL fragments that can be streamed efficiently to clients regardless of total session size.

### Chunk Generation and Retrieval

The `createSnapshotTranscriptChunks` method serializes messages into JSONL lines, while `storeChunk` handles the actual persistence to disk when necessary. For scenarios where chunks are still being generated while a client is reconnecting, the cache exposes a `waitForChunk(index)` method that allows the daemon supervisor to await specific chunk availability before transmission, ensuring consistency even during active write operations.

## Streaming Snapshots During Reconnection

When a client socket attaches to an existing session, the `DaemonSupervisor` class in [`packages/coding-agent/src/modes/daemon/daemon-supervisor.ts`](https://github.com/PrimeIntellect-ai/prime-agent/blob/main/packages/coding-agent/src/modes/daemon/daemon-supervisor.ts) initiates the snapshot protocol. The supervisor first transmits a `session_snapshot_begin` envelope to signal the start of historical data transmission. It then iterates over the transcript cache using the `[Symbol.iterator]` implementation, emitting each chunk as a `session_snapshot_chunk` event containing the payload, chunk index, snapshot ID, and active session ID.

### Completion and Error Signaling

After the final chunk transmits, the daemon sends `session_snapshot_end` to indicate the replay stream is complete. If the cache encounters an error during serialization or disk access, the supervisor emits `session_snapshot_failed` instead, providing an error message that allows the client to fall back to initializing a fresh session state rather than hanging indefinitely.

## Client-Side Session Restoration

On the client side, the `DaemonAgentConnection` class in [`packages/coding-agent/src/modes/agent-connection/daemon-agent-connection.ts`](https://github.com/PrimeIntellect-ai/prime-agent/blob/main/packages/coding-agent/src/modes/agent-connection/daemon-agent-connection.ts) manages the reconstruction process. As `session_snapshot_chunk` events arrive, the client appends each payload to a local buffer, parsing the JSONL content to rebuild the `AgentMessage[]` array. Once the `session_snapshot_end` event triggers, the client passes the reconstructed transcript to `createDaemonReplayInfo()`, which restores tool execution results, turn boundaries, and any queued actions to their exact pre-disconnection state.

### Resuming Live Operations

Following successful replay, the client switches from snapshot consumption to the standard daemon protocol handled by `DaemonClient` in [`packages/coding-agent/src/modes/daemon/daemon-client.ts`](https://github.com/PrimeIntellect-ai/prime-agent/blob/main/packages/coding-agent/src/modes/daemon/daemon-client.ts). This transition allows the user to continue interacting with the session as if no interruption occurred, with all context and intermediate states preserved.

## Implementation Examples

### Initializing the Server-Side Cache

```typescript
import { SnapshotTranscriptCache } from "../daemon/snapshot-transcript-cache.js";

function initializeSessionCache(state: ActiveSessionState, initialMessages: readonly AgentMessage[]) {
  const cache = new SnapshotTranscriptCache({
    activeSessionId: state.activeSessionId,
    snapshotId: `snap-${Date.now()}`,
    cacheRoot: "/tmp/prime-agent-snapshots",
    messages: initialMessages,
  });

  // Real-time updates as the session progresses
  state.runtime.session.onMessage((msg) => {
    const encoded = Buffer.from(JSON.stringify(msg));
    cache.appendEncodedChunk(encoded);
  });

  return cache;
}

```

### Transmitting Snapshot Data to Clients

```typescript
async function transmitSnapshot(
  client: DaemonSocketClient, 
  cache: SnapshotTranscriptCache
) {
  client.send({ type: "session_snapshot_begin" });

  for (let i = 0; i < cache.chunkCount; i++) {
    const chunk = cache.readChunk(i);
    client.send({
      type: "session_snapshot_chunk",
      snapshotId: cache.snapshotId,
      index: i,
      activeSessionId: cache.activeSessionId,
      messages: chunk,
    });
  }

  client.send({ 
    type: "session_snapshot_end", 
    snapshotId: cache.snapshotId 
  });
}

```

### Reconstructing State on the Client

```typescript
import { DaemonAgentConnection } from "./daemon-agent-connection.js";

const conn = new DaemonAgentConnection(socket);
const transcript: AgentMessage[] = [];

conn.on("session_snapshot_begin", () => {
  transcript.length = 0;
});

conn.on("session_snapshot_chunk", (event) => {
  const lines = event.messages.toString("utf8").split("\n");
  for (const line of lines) {
    if (line.trim()) transcript.push(JSON.parse(line));
  }
});

conn.on("session_snapshot_end", () => {
  replayEngine.restoreFromHistory(transcript);
  console.log("Session state restored, resuming live stream");
});

```

### Handling Snapshot Failures

```typescript
conn.on("session_snapshot_failed", (event) => {
  console.warn(`Snapshot ${event.snapshotId} failed: ${event.errorMessage}`);
  // Initialize empty session state as fallback
  replayEngine.initializeEmptySession();
});

```

## Summary

- **SnapshotTranscriptCache** in [`snapshot-transcript-cache.ts`](https://github.com/PrimeIntellect-ai/prime-agent/blob/main/snapshot-transcript-cache.ts) maintains a rolling transcript with automatic memory-to-disk spilling at 4 MiB thresholds and 512 KB chunk sizes.
- **DaemonSupervisor** coordinates snapshot transmission using three distinct protocol events: `session_snapshot_begin`, `session_snapshot_chunk`, and `session_snapshot_end`.
- **Wait-for-chunk semantics** allow the daemon to stream data that is still being generated, ensuring clients receive consistent snapshots even during active session writes.
- **Client-side replay** via `DaemonAgentConnection` reconstructs the full `AgentMessage[]` history and restores tool states before transitioning to live `DaemonClient` operations.
- **Failure handling** through `session_snapshot_failed` ensures graceful degradation when cache errors occur.

## Frequently Asked Questions

### What triggers the snapshot transmission when a client reconnects?

When a client socket attaches to an existing session, the `DaemonSupervisor` automatically detects the connection and initiates the snapshot protocol by calling `sendSnapshotBegin()`. This happens immediately upon socket attachment, before any live events are streamed, ensuring the client receives complete historical context first.

### How does Prime Agent handle extremely large session histories?

The system uses configurable chunking via `SNAPSHOT_TARGET_CHUNK_BYTES` (default 512 KB) combined with memory limits set by `SNAPSHOT_MEMORY_CACHE_BYTES` (default 4 MiB). Once the memory limit exceeds, the cache spills chunks to temporary files in the `cacheRoot` directory, allowing sessions with gigabytes of history to be cached without RAM exhaustion.

### What happens if the snapshot transmission fails midway?

If the cache encounters serialization errors or disk I/O issues during streaming, the `DaemonSupervisor` emits a `session_snapshot_failed` event containing the `snapshotId` and `errorMessage`. The client can then handle this by initializing a fresh session state or retrying the connection, preventing the UI from hanging on incomplete data.

### Does this mechanism preserve state across daemon restarts?

The snapshot and replay mechanism primarily handles client reconnections while the daemon remains running. While the cache spills to disk at `cacheRoot`, the current implementation focuses on memory management rather than persistent storage across daemon process restarts. For full durability across daemon restarts, additional persistence layers would need to rebuild the cache from the spilled chunks on daemon initialization.