acpmux: fix closed summary cache invalidation
Follow-up correctness fixes for the closed-summary cache:
- keep list and full serialized rows on independent generations, so building one form cannot make the other form appear fresh;
- capture the generation before constructing a row;
- remove cached bytes when a session is purged, deleted, or reopened;
- invalidate time-expiring tags when their deadline passes;
- keep summary construction out of
write_snapshot, avoiding nested metadata and permission locks in the writer; - cover list-then-full reads, appends after close, shown/attached state, tag expiry, concurrent writers, cold loading, and purge eviction against an uncached walk.
Leo asked: “you (or other guys) should audit my computer and see what is taking up all the CPU and optimize against that.” The prior cache benchmark on a profiled Mac running the NEXT nightly measured the same 7,828-record fixture (7,295 closed) at 227.378→150.376 ms for watch/list, 207.694→149.910 ms for sessions?usage, and 235.739→181.206 ms for peer summaries. These follow-ups preserve those bytes and invalidation behavior.
| metric | before | after | delta | harness |
|---|---|---|---|---|
| watch/list full build CPU | 227.378 ms | 150.376 ms | -33.9% | measure_7828_full_idle_closed_summary_cache |
| sessions?usage full build CPU | 207.694 ms | 149.910 ms | -27.8% | measure_7828_full_idle_closed_summary_cache |
| peer sync summaries CPU | 235.739 ms | 181.206 ms | -23.1% | measure_7828_full_idle_closed_summary_cache |
Validation runs through cmux-ci for the acpmux test suite and clippy.
agent-identity footer --repo manaflow-ai/cmux
Agent session: agent session
![View with [code]smith](https://pr-comments-assets.blacksmith.sh/codesmith/view-with-codesmith-dark-v3-3x.png)
![Autofix with [code]smith](https://pr-comments-assets.blacksmith.sh/codesmith/autofix-with-codesmith-dark-3x.png)
Need help on this PR? Tag @codesmith-bot with what you need.
Summary by cubic
Fixes correctness bugs in the closed-summary cache so cached rows never serve stale data, and reorders the purge event so watchers can't resolve a just-purged session.
- Tracks list and full serialized rows on independent generations and tag-expiry deadlines, so building one form can't make the other look fresh; empty rows are never served.
- Builds rows lazily on cache miss;
write_snapshotonly evicts entries, avoiding nested metadata and permission locks in the writer. - Evicts entries when tags expire or sessions are purged, deleted, or reopened.
- Emits the purge event only after the session is unregistered from live lookup and its cache entry is removed.
- Adds tests covering list-then-full reads, appends after close, shown/attached state, tag expiry, concurrent writers, cold loading, and purge eviction.