subagentcoworkers

.com 20 pages
the fast path

Redis 7 — the fast path

The local fleet runs one redis: the subagentjobs-redis container, image redis:7-alpine. It holds only what the durable stores can regenerate — the repo's standing PG-canonical / Redis-L2 convention, written into the migration 008 header itself: "Redis (localhost:6379) holds only cheap per-run scratch … this table is the source of truth." Every key family below carries a TTL as a safety net, never as the freshness guarantee — where freshness matters, the write path invalidates explicitly (DEL jobs:{board} on upsert).

baked 2026-07-10 from docker ps --format '{{.Names}}\t{{.Image}}'subagentjobs-redis · redis:7-alpine

The real keyspace

snap:{board} · TTL 3600 durable-store lib.rs:27 · board snapshot hash (CDC) jobs:{board} · TTL 3600 lib.rs:29 · per-board job list, DEL-invalidated graph:{min_weight} · TTL 300 lib.rs:31 · skill graph, expensive query idx:q:{sha256} · TTL 300 lib.rs:383 · repo-index query cache snap:doc:/doc:{sha} · TTL 3600 lib.rs:519 · crawled doc pages, CDC-busted route:queue · list, NO TTL flush_route_queue.py:28 · Stop-hook drained deploy:{domain}:status|verify ledger.sh:46 EX 3600 · verify-site.sh:64 EX 300 ragq:{sha16} · TTL 3600 crawlers/ragcache.py:30 · docs-rag L2 postgres (durable) subagentjobs-postgres · postgres:16-alpine the canonical store — see /postgres redis holds only what PG can regenerate sqlite FTS5 · rag.sqlite docs/.crawl-state · owns docs/docs — see /indexdb

One box per real key family — prefix, TTL, and owning file:line, each grep-verified against crates/durable-store/src/lib.rs, crawlers/ragcache.py, scripts/hooks/flush_route_queue.py, and plugins/cwc-deploy/skills/fleet-expansion/scripts/ before baking (2026-07-10). Arrows point at the durable owner of each family's canonical state; the dashed arrow marks the one family (ragq:) whose durable tier is sqlite FTS5, not postgres.

The three tiers, animated

L1 lru_cache(256) in-process, deserialized L2 redis · TTL 3600 cross-process, JSON L3 durable sqlite FTS5 + postgres

These are crawlers/ragcache.py's real tiers, verbatim from its own header (ragcache.py:6-8): L1 functools.lru_cache(maxsize=256) holds deserialized result objects per-process (ragcache.py:90); L2 redis holds serialized JSON under ragq:{sha16} at TTL 3600 so concurrent sessions share hot queries (ragcache.py:30, 92); L3 is the durable index itself. The durable-store families in the map above follow the same read-through shape in Rust.

Why a fast path at all — the token framing

A cache hit is work no model re-derives. When a subagent's docs-rag query lands in L1 or L2, the answer costs zero re-parsing and zero re-ranking — and, upstream of that, zero tokens spent re-reading source files to reconstruct something a sibling session already computed. The same framing explains route:queue: the model-routing hooks (scripts/hooks/route_agent_model.py, record_agent_usage.py) RPUSH their telemetry records to redis and return immediately, so dispatch latency never waits on postgres — the Stop hook (.claude/settings.jsonflush_route_queue.py) drains the list into agent_dispatch_events after the turn, off the critical path.

deploy:* is the same idea at deploy time: per-run scratch (deploy:{domain}:status EX 3600, deploy:{domain}:verify EX 300) beside the durable fact_fleet_deploy ledger, never instead of it — a crashed deploy wave resumes from the postgres ledger, not from redis.

Companion pages: /indexdb (the repo index these caches front) and /postgres (the durable spine the arrows point at).