The Rollout
How coding agents remember: a field study of six session-history formats
Over the last eleven months, the coding agents on one of our Macs wrote 3,096 session transcripts totaling 3.8 GB — roughly a million logged events across Claude Code, Codex, Cursor, GitHub Copilot CLI, OpenCode, and Hermes. Every one of those files is the complete record of a working session: what was asked, what was tried, what broke, what shipped.
There is a useful way to think about these files. The model has no memory of its own; when the session ends, everything it will ever be able to recall about that refactor is what it managed to write down at the time. The session file is the agent’s dream journal, kept while the dream is happening. Six agents keep six very different journals, and the differences are not cosmetic. They decide what the agent can resume, what a tool like a history browser can show you, what you can audit six months later, and what is silently lost.
A companion post covers where these files live on disk. This one is about what is inside them. We measured it.
Method
We ran a read-only measurement harness over every session store on one machine: 184 Claude Code sessions, 2,706 Codex rollouts, 14 Cursor Agent transcripts, 20 Copilot CLI sessions, 61 OpenCode sessions, and 111 Hermes sessions, spanning August 2025 to July 2026. The harness parses every event, classifies it (user message, assistant message, tool activity, metadata), and records aggregates only: counts, byte sizes, ratios, field coverage, timings. No transcript content leaves the analysis, and the numbers below are corpus totals, not excerpts. The script and the raw aggregates are in the Agent Sessions repo.
Honest caveats, stated up front. This is one machine and one user, so the usage mix differs per agent: Codex did most of the daily work here, Cursor saw fourteen sessions. Cross-agent comparisons are indicative, not a controlled experiment. Where a number depends on usage rather than format, we say so.
Finding 1: the journal is almost all margin notes
The first thing the data shows is how expensive remembering is. Divide each store’s total size by the number of user-visible messages in it, and you get the cost of remembering one human sentence:
The headline ratio is starker than the bar chart. In the Claude Code corpus, visible conversation text (what you typed plus what the model said to you) is 3.0% of the bytes. In Codex it is 2.6%. Everything else is tool calls, tool output, reasoning items, metadata envelopes, and bookkeeping. The journal is almost entirely margin notes about the dream, not the dream itself.
That is not waste, mostly. Tool output is the evidence of what actually happened, and it is the part you grep for later. But the volumes are worth knowing: the largest single Codex session on this machine is a 212 MB JSONL file, and Claude Code’s largest is 19 MB. Any tool that reads these naively into memory will eventually meet one of those.
Cursor is the interesting outlier. At 1.8 KB per user message, with half its bytes being visible text, its transcript is lean because it is incomplete: in our corpus it records zero tool events and zero per-event timestamps. The transcript reads well and remembers almost nothing about how the work was done. It is a diary with the verbs removed.
Finding 2: some agents know what they cost, and some have no idea
The second axis is self-knowledge: what the format records about its own execution. The spread here is wide.
Copilot CLI is the quantified dreamer. Every assistant message carries the
model name, output token count, and request IDs; every tool execution carries
the model that requested it; and at shutdown it writes a full accounting
event: total conversation tokens, premium request count, API duration, even
the size of its own event file. Hermes keeps a ledger in the same spirit: its
sessions table has thirty-three columns, including input, output, cache-read,
cache-write, and reasoning token counts, plus estimated_cost_usd and
actual_cost_usd. OpenCode records tokens and a cost figure on each
message row. These three can answer “what did this session cost” from local
data alone.
The bigger names are thriftier. Codex writes turn-level token_count events
with cumulative usage, which is enough for totals but not for per-message
attribution, and no dollar figure. Claude Code stamps every assistant event
with the model and a usage block, which is genuinely good, and also the
occasion for a correction: our companion post claimed Claude Code writes no
per-event model. Wrong. In this corpus, all 36,376 assistant events carry
message.model. We measured our own claim and it failed; the fix is in both
posts.
Cursor’s transcript records none of this. The model hint lives in a separate metadata database, and the events themselves are undated. If you want to know what a Cursor session cost, the answer is on the vendor’s dashboard, not your disk.
Finding 3: the dreams they are no longer allowed to reread
Reasoning is where the field is converging, quietly, on the same policy: sealed.
Codex is explicit about it. In the forty most recent rollouts here, all 7,339
reasoning items are opaque encrypted_content blobs. They sit on your disk,
in your file, and neither you nor the agent that wrote them can read them
back.
Claude Code turns out to have gone the same way, with less announcement. Its
thinking blocks have a thinking text field and a cryptographic signature.
In the thirty most recent sessions on this machine, 2,567 of 2,628 thinking
blocks have a signature and an empty text field. About 2.5% still carry
plaintext. The agent’s private reasoning is now certified rather than
recorded: the file can prove the thinking happened, and cannot say what it
was.
The rest of the field is split. Copilot writes both a reasoningText and a
reasoningOpaque field, hedging per message. OpenCode stores reasoning as
first-class part rows, 743 of 1,207 with readable text, the rest empty
depending on the provider. Hermes keeps a plaintext reasoning_content
column.
There are real reasons for sealing: provider policies, distillation concerns, resumability across stateless APIs. But it changes what your archive is. A year of session history used to include why the agent did things; increasingly it only includes what it did. If the why matters to you, the readable summary the agent chooses to say out loud is now the only record of it, which is worth knowing when you decide how much to trust that summary.
Finding 4: remembering is not the same as being able to recall
The last measurement is retrieval. A memory you cannot search is barely a memory, and this is where the two storage philosophies split cleanly.
The JSONL camp (Claude Code, Codex, Copilot, Cursor) has no index of any
kind. Finding a word in this machine’s 3.4 GB of Codex history means reading
3.4 GB: a naive grep -rl takes 10.8 seconds, and a full structured parse of
the corpus takes 16.6 seconds. Do that on every keystroke of a search box and
you understand why history browsers build their own indexes.
Hermes answers the same class of question in 0.4 milliseconds, four orders of magnitude faster, because it ships a trigram full-text index inside its database. It pays for recall honestly: twelve of its eighteen tables are search infrastructure, and actual message content is about 11% of the database’s bytes. Hermes spends most of its memory on being able to remember. OpenCode sits in between: proper relational rows (a query away from anything) but no full-text index, and reconstructing one message means joining an average of 3.6 part rows.
Neither philosophy wins outright. JSONL survives crashes by construction (a truncated last line is the entire failure mode), diffs cleanly, and can be read by any tool ever written. Databases answer questions. The scorecard shows how each agent actually trades this off:
The bottom row deserves its own sentence. None of the six formats has public schema documentation. Every parser of these files, including ours, is built by reverse engineering, and every one of them breaks a little when a vendor renames a field. For files this valuable, that is a strange industry norm.
What a session format should be
Having read a million events written six different ways, here is the standard we would hold any of them to, and how the field measures against it.
Write like a log, read like a database. Append-only JSONL for the write
path, because a crash mid-write should cost one line, not a database
recovery. A sidecar index (SQLite is fine) for the read path, rebuilt from
the log whenever it is stale. Today every agent picks exactly one half:
the JSONL camp cannot search and the database camp cannot tail -f. Hermes
is closest to the right shape, but the log half of it is inside the database
rather than beside it.
Attribute every message. Model, timestamps, token usage, and cost belong on each message, not in a session header, because sessions switch models mid-flight and post-hoc accounting depends on it. Claude Code and OpenCode are closest here. Codex should move usage from turn level to message level. Cursor should start writing timestamps into its own transcript, which in 2026 is a modest ask.
Seal reasoning honestly. If reasoning must be opaque, say so in the format: a documented field, a stated policy, and a user-visible switch where policy allows one. Claude Code’s silent shift from plaintext thinking to signature-only is the pattern to avoid, less because of the sealing than because nothing announced it. Users planning to audit their own history a year out deserve to know the why is no longer being kept.
Publish the schema. One versioned page per vendor, listing the event types and stability guarantees. Codex already versions its files internally and tolerates unknown fields, which is most of the work. The ecosystem that wants to exist around these files — history browsers, usage analytics, team knowledge tools — is currently built on guesswork.
The files themselves are the good news. Every agent in this study writes its journal locally, completely, and by default, and none of it leaves your machine on its own. The formats are six dialects of the same instinct, and the instinct is right: the work is worth remembering.
Agent Sessions is a free, local-only macOS browser for all six of these stores; it reads them read-only and never writes back. The measurement script and raw aggregates behind every number here are in the repo, and the companion post on the exact disk locations is here.