The goal & what was built
The whole project is the migration: re-implement RocksDB as a pure-Zig 0.16 LSM key-value engine,
built bottom-up under strict TDD, and finish by making byte-exact RocksDB the only on-disk format
zrocks emits — proven by having a real librocksdb v11.4.0 binary open zrocks's flush,
compaction, range-delete and WAL output through a verify_open oracle.
The result is a working, durable, crash-recoverable, leveled-compacting LSM store with a CLI:
foundation (slice/status/coding/comparator/arena/CRC32C/options) → Env over std.Io →
WAL · skiplist · memtable · WriteBatch → block-based SST (builder/reader, bloom, footer) → LRU cache →
iterators → VersionEdit/VersionSet/MANIFEST → recovery → flush + leveled/universal/FIFO compaction →
snapshots → column families, merge operator, prefix seek, compaction filter, range delete, transactions,
checkpoints → then the format migration to byte-exact RocksDB.
Timeline
Times are CEST. Blue = core engine build (Phases 0–7); violet = RocksDB-only format migration.
- 05-28 08:15 Phase 0 — Foundation: build/harness, Slice/Status, coding (varint+fixed), comparator, arena, options, CRC32C (M0.0–M0.6).
- 05-28 08:32 Phase 1 — Environment: Env over
std.Io+ MemEnv (M1.0). - 05-28 08:43 Phase 2 — Write durability core: InternalKey, WriteBatch, WAL, skiplist, memtable (M2.0–M2.4).
- 05-28 09:06 Phase 3 — Block-based SST: block builder/reader, bloom + filter block, footer, TableBuilder/Reader, LRU cache (M3.0–M3.5).
- 05-28 09:41 Phase 4 — Iterators & in-memory DB: merging/two-level iterators, Put/Get/Delete/Write/iter (M4.0–M4.1).
- 05-28 18:09 Phase 5 — Persistence: VersionEdit, VersionSet/MANIFEST, recovery + durable open (M5.0–M5.2).
- 05-28 18:50 Phase 6 — Compaction → embedded KV store: SST read path, flush, leveled compaction, snapshots + CLI. GATE: LevelDB-equivalent core (M6.0–M6.3).
- 05-28 22:09 Phase 7 — RocksDB extensions: column families, merge operator, prefix bloom/seek, universal+FIFO, compaction filter, DeleteRange, transactions, checkpoints (M7.0–M7.7). READ-interop with real RocksDB v11.4.0 + Chromium LevelDB.
- 05-29 16:26 Migration — interop tooling: real RocksDB v11.4.0 fixture + built-from-source oracle;
verify_openwidened to point-Get + Seek/range-scan + absent-key. - 05-29 20:04 → 23:52 RocksDB-only migration (8 branches): properties-always → SST-default-flip → manifest-rocksdb-exact (
kNewFile4tag 103 + seqnos) → filter-rocksdb-only (FastLocalBloom) → range-del-rocksdb → partitioned-index-drop → remove-native-and-tests. Native/clean formats deleted. - 05-30 10:46 Done — "End of Opus 4.8 run." Directive fulfilled: byte-exact RocksDB is the only format. Part II below dissects this final phase.
Token usage
Across all 125 transcripts (1 main session + 3 helper sessions + 121 subagent/workflow runs). Cache reads dominate because every agent turn re-reads its cached context cheaply; the real generation cost is the output column. "Total" sums input+output+cache-create+cache-read.
| Model | Output | Input | Cache create | Cache read | Total | Role |
|---|---|---|---|---|---|---|
claude-opus-4-7 | 4,115,123 | 145,341 | 37,685,149 | 1,070,637,462 | 1,112,583,075 | Primary driver — orchestration + all coding subagents |
claude-sonnet-4-6 | 351,668 | 47,628 | 5,661,202 | 102,440,903 | 108,501,401 | Lighter-weight subagent work |
claude-opus-4-8 | 10,208 | 7,876 | 69,667 | 308,802 | 396,553 | Reporting sessions (this report) |
| All | 4,476,999 | 200,845 | 43,416,018 | 1,173,387,167 | 1,221,481,029 |
By day
| Day | Output tokens | Cache read | Tool calls | Agents spawned | |
|---|---|---|---|---|---|
| 2026-05-28 | 2,748,676 | 550,233,848 | 2,589 | 39 | |
| 2026-05-29 | 1,675,993 | 618,047,526 | 3,735 | 4 | |
| 2026-05-30 | 69,896 | 5,490,851 | 63 | 0 |
Day 1 (28th) built the entire Phases 0–7 core; day 2 (29th) drove the most tool-heavy work — read-interop tooling plus the RocksDB-only migration.
Tool usage
| Tool | Calls | |
|---|---|---|
Bash | 3,321 | |
Read | 1,570 | |
Edit | 1,040 | |
Write | 128 | |
StructuredOutput | 115 | |
TaskUpdate | 84 | |
Agent | 43 | |
TaskCreate | 42 | |
ToolSearch · Monitor · Workflow · EnterWorktree · … | ≤14 ea |
531 ran in the main orchestration session; 5,852 (92%) ran inside subagents — the coding happened in delegated agents, as the workflow intended.
The Bash/Read/Edit shape is the TDD loop: run zig build test, read the
failure, edit, repeat. StructuredOutput calls are workflow agents returning validated JSON
(design verdicts, migration findings). 43 Agent spawns + 4 Workflow runs drove
121 subagent transcripts.
Tool failure analysis
128 errored tool results out of 6,383 — an overall 2.0% failure rate. Breakdown by tool and by cause below.
By tool
| Tool | Errors | Calls | Rate | |
|---|---|---|---|---|
StructuredOutput | 40 | 115 | 34.8% | |
EnterWorktree | 4 | 4 | 100% | |
Monitor | 1 | 10 | 10.0% | |
Bash | 65 | 3,321 | 2.0% | |
Edit | 15 | 1,040 | 1.4% | |
Write | 1 | 128 | 0.8% | |
Read | 2 | 1,570 | 0.1% |
By root cause
| Category | Count |
|---|---|
| Schema-mismatch / transient / misc (mostly StructuredOutput retries + "model temporarily unavailable") | 76 |
| Bash: command / Zig compile error (the expected red side of TDD) | 31 |
| File not found / EISDIR | 13 |
| Edit: stale read or non-unique match | 6 |
| Permission / denied | 2 |
What the failures actually were
- StructuredOutput (40, the biggest bucket) — workflow agents whose first JSON didn't satisfy the
required schema, e.g.
must have required property 'verdict_note'/'already_rocksdb_exact'. These are self-correcting retries: the harness rejects the output and the agent re-emits a valid object. No work was lost; they inflate the count without being real failures. - EnterWorktree (4, 100%) — a subagent tried to call
EnterWorktreewhile already running with acwd/worktree override: "cannot be called from a subagent with a cwd override." A harness guardrail, not a code bug; the orchestrator owns worktree creation. - Bash (65, ~2%) — dominated by expected failures:
zig build testexiting non-zero on the red step of red→green TDD, plus a handful ofcaton a not-yet-existingMEMORY.mdand two transient "claude-opus-4-7 is temporarily unavailable" auto-permission stalls. - Edit (15, ~1.4%) — "
File has been modified since read… Read it again" and "Found 2 matches… set replace_all." Standard edit-contract hiccups, immediately retried. - Read / Write (3) — one
EISDIR(read a directory as a file), one missing file, one write-before-read. All recovered on the next call.
Process: TDD cadence & orchestration
Commit shape
| Prefix | Commits |
|---|---|
feat | 75 |
Merge (per-milestone --no-ff) | 75 |
test | 54 |
chore | 37 |
refactor | 31 |
fix / docs | 5 |
61 commits say "red", 51 say "green" — the literal failing-test-first / make-it-pass rhythm of every milestone.
Agent orchestration
A single main session acted as orchestrator; nearly all code was written by delegated subagents, one per milestone, mostly in isolated git worktrees. Four deterministic workflows structured the bigger fan-outs:
execute-roadmap— drove the Phase 0–7 milestone buildnext-directions— post-core roadmap explorationrocksdb-only-migration-design— design + adversarial verification of the migrationrocksdb-only-execute— milestone-by-milestone, each gated byverify_open
43 direct Agent spawns + 78 workflow-launched agents = 121 subagent transcripts.
The final RocksDB-only format migration
This is the last phase of the timeline above, examined on its own. Goal: make byte-exact RocksDB the
only on-disk format zrocks emits, delete every native/“clean” write path, and prove it by having a
real librocksdb v11.4.0 binary open the output via a widened verify_open oracle that
exercises point-Get, Seek+range-scan, and absent-key checks.
Headline numbers
Token total = design workflow (1,581,977) + execute workflow (1,071,431). Wall clock (5h 14m) < workflow CPU time (5h 19m) because the design phase had agents running in parallel.
Two-phase structure
| Phase | Workflow | Started | Duration | Agents | Tokens | Tool calls | Status |
|---|---|---|---|---|---|---|---|
| 1. Design + verify | zrocks-rocksdb-only-migration-design | 17:22 UTC | 41.5 min | 19 | 1,581,977 | 613 | completed |
| 2. Execute | zrocks-rocksdb-only-execute | 18:05 UTC | 278.2 min | 9 | 1,071,431 | 1,068 | completed |
Phase 1 fanned out 9 design agents (one per format component) and 9 adversarial verifiers in parallel, then a single synthesizer produced the sequenced plan (28 min, 183 k tokens by itself).
Phase 2 ran the 9 plan milestones sequentially on the shared repo (each had to commit before the next started, because they all touch src/format/ and src/db/).
Per-milestone breakdown (execution phase)
| # | Milestone | Commit | Model | Duration | Tokens | Tool calls | Tests after | Oracle |
|---|---|---|---|---|---|---|---|---|
| 1 | oracle-widen widen verify_open to Get+Seek+absent-key | d3c39a6 | sonnet‑4‑6 | 26:40 | 48,652 | 49 | 530 | OPEN_OK 11 |
| 2 | properties-always emit full 29-field RocksDB v11 table-properties | 94ae493 | opus‑4‑7 | 15:01 | 83,325 | 45 | 530 | OPEN_OK 11 |
| 3 | sst-default-flip delete sst_output enum + native single-level index + native finish path | 33d7b6f | opus‑4‑7 | 41:39 | 204,807 | 137 | 524 | OPEN_OK 11 |
| 4 | manifest-rocksdb-exact compaction emits kNewFile4 (tag 103) with min/max seqnos — fixed latent bug | 26a9639 | opus‑4‑7 | 15:19 | 111,705 | 55 | 525 | OPEN_OK 8 |
| 5 | filter-rocksdb-only FastLocalBloom full filter in every SST; drop block-based-bloom write path | 22a3afe | opus‑4‑7 | 22:19 | 113,679 | 101 | 525 | OPEN_OK 11 |
| 6 | range-del-rocksdb emit/read range tombstones in rocksdb.range_del meta-block format | 4c6e3fb | opus‑4‑7 | 28:35 | 111,886 | 62 | 528 | OPEN_OK 5 |
| 7 | wal-writebatch-cf replace kColumnFamilyTag=0x10 with RocksDB CF value-type bytes (0x4/0x5/0x6/0xE) | b13f6a2 | opus‑4‑7 | 37:12 | 160,351 | 414 | 532 | OPEN_OK 11 |
| 8 | partitioned-index-drop delete partitioned_index.zig (373 LoC); drop Options.IndexType | 55f0668 | sonnet‑4‑6 | 38:18 | 119,790 | 107 | 528 | OPEN_OK 11 |
| 9 | remove-native-and-tests final sweep: SharedManifest.writeSnapshot emits kNewFile4 | aba5a2b | opus‑4‑7 | 53:05 | 117,236 | 98 | 529 | OPEN_OK 34 |
Oracle column = result of /home/ghpu/rocksdb-interop/verify_open <db> on the milestone’s gate fixture (a full flush+compaction+range-del+WAL DB).
Intermediate dips to 5 / 8 are expected — each step proves its own component opens in isolation while later steps still emit native formats for the others.
The final 34 means the final fixture is richer (more keys + multi-level + tombstones) and reads end-to-end.
Tool usage (migration)
Across all 28 migration subagents.
| Tool | Calls | Share |
|---|---|---|
Bash (zig build, git, grep, oracle) | 1,083 | |
Read | 401 | |
Edit | 104 | |
StructuredOutput (schema-bound return) | 69 | |
Write | 10 | |
Monitor | 9 | |
ToolSearch | 3 | |
TaskStop | 2 |
Read/Edit/Bash dominance is the signature of strict TDD on a Zig codebase: read the file, write a red test, build, edit, build, run the oracle. Almost no Write (large new files) — the migration is mostly deletion.
Model mix (migration)
| Model | Agents | Tokens |
|---|---|---|
| claude-opus-4-7 | 17 | 1,910,733 |
| claude-sonnet-4-6 | 11 | 878,675 |
Sonnet 4.6 handled the 9 design agents (broad-but-shallow assessment) and 2 execute steps with narrow, well-specified scope (oracle-widen, partitioned-index-drop). Opus 4.7 handled all adversarial verifiers, the synthesizer, and 7 of 9 execute milestones — everywhere the work touched contended core files (db.zig, compaction.zig, table_builder.zig).
Resulting diff
17 files changed +1,320 insertions -1,810 deletions net −490 LoC 21 commits to main
Net negative LoC despite adding RocksDB format features — because nine entire native/“clean” write paths were deleted in the process.
Failure analysis (migration)
The migration completed with 0 retries and 0 quarantined milestones. Every one of the 28 subagents finished on its first attempt; every one of the 9 execute milestones merged to main. The execute workflow’s pre-commit gate (full zig build test + the real-RocksDB verify_open oracle) was the safety net that made retries unnecessary — an agent that broke the gate would have been quarantined and its dependents skipped, but none did.
| Event | Where | Outcome |
|---|---|---|
| Latent bug discovered mid-flight | Milestone 4 (manifest-rocksdb-exact) |
Fixed in-band. Before the migration, compaction.zig:commitCompaction emitted compaction outputs via addFile (legacy kNewFile=7, no seqnos). This wasn’t caught earlier because no test exercised compaction after a multi-level fill. The milestone’s red test surfaced it; the same milestone’s green commit (4d0f04b) fixed it by switching to addFile4 with real min/max seqnos.
|
| Oracle count regression at milestone 6 | range-del-rocksdb (OPEN_OK 5) |
Expected. The narrower fixture used by intermediate gates only carries 5 live non-tombstoned keys; the gate’s contract is “real RocksDB opens it,” not a fixed count. The next milestone’s richer fixture lifted it back to 11, and the final milestone’s end-to-end DB hit 34. |
2x TaskStop in subagent traces |
Execute phase (long-running background zig build jobs) |
Cooperative. Both were agent-initiated stops of own background zig build test jobs after a faster path produced the answer — no test was abandoned.
|
| Subagent retries | — | 0 / 28 — every agent reported attempt=1, state=done. |
What the migration deleted
Options.sst_outputenum + field (forced single output format)- Native single-level SST index path (write side)
- Two-level partitioned SST index (
src/format/partitioned_index.zig, 373 LoC + 3 tests +Options.IndexType) - Block-based-bloom write path (read path retained for LevelDB interop)
- Bespoke range-tombstone serialization (replaced by
rocksdb.range_del) kColumnFamilyTag=0x10WAL prefix (replaced by RocksDB CF value-type bytes)- Per-CF MANIFEST snapshot path emitting legacy
kNewFile=7
Evidence on disk (post-migration)
$ zrocks /tmp/demo put keyN value-from-zrocks-N # via the zrocks CLI $ ls /tmp/demo 000002.log CURRENT MANIFEST-000003 $ /home/ghpu/rocksdb-interop/verify_open /tmp/demo # the REAL librocksdb binary OPEN_OK count=10 key0=value-from-zrocks-0 … key9=value-from-zrocks-9
Plus the CI self-consistency gate tests/rocksdb_write_interop_test.zig, which on every zig build test asserts on the raw bytes that footer is format_version=5 / crc32c, metaindex carries rocksdb.properties, and MANIFEST uses kNewFile4 with no stray kColumnFamilyAdd.
main; 125 session transcripts (≈44 MB) under the project's Claude history; DEVSTATE.md.
Token figures are exact sums of per-message usage; failure analysis counts tool_result
blocks with is_error. Part II sources: the design + execute workflow journals
(wf_19b0a837-1b4, wf_d94d13f7-c95), 28 subagent traces, and git log
bf8bc96..aba5a2b. All times CEST unless suffixed UTC.