Skip to content

Sealed code generation cannot seat: graph activation loops on 'code graph database conflict' every retry, no generation ever serves #765

Description

@ScriptedAlchemy

Observed on the operator daemon (proj_a5b3d7e3ebe14ca7), 2026-08-31, PR #707 tip binary

After the #762 fix handoff (pin adb623efecb7, binary built from PR branch + #764 shutdown lane), the operator daemon runs memory-stable (HWM 29.9 GiB, RSS returning to ~14 GiB after each phase, no OOM in 2+ hours — the #762 shape is gone). But the code index never converges to a serving generation:

  • The startup active generation is refused: active generation is incompatible with the production owner configuration (expected after the binary upgrade — sanitizer/chunker/policy revisions moved).
  • The scheduler stages and seals a fresh generation (staging finished ~07:46, sealed artifact tracedecay.sealed/278bea7a…).
  • Every graph activation attempt fails with code-index graph projection failed: code graph database conflict (GraphDbError::Conflict), including attempts made after the fresh seal (07:48, 07:58, 08:11, spaced by the 600 s seat backoff). Each attempt burns ~30–70 s before failing, consistent with a full replay/verification pass.
  • event=code_index_graph_activation_retry_scheduled repeats forever; retention passes log no code generation is currently serving for this project and graph_replay_release_failed error=DeadlineExceeded every ~100 s.

Journal state at the time (read-only sqlite, project db)

  • graph_publication_replay_v1: newest code rows are sequences 10 and 11 (two code-scope namespaces); newest overall is 14 (project-memory). No new journal row was ever written for the freshly sealed generation — the publish conflicts before journaling.
  • graph_publication_replay_tombstones_v1: empty.
  • graph_verified_heads_v1: heads exist at replay sequences 6, 7, 8, 10, 11 (five code-scope namespaces).

So the wedge is deterministic and pre-journal: GraphPublicationOperations prepare/replay returns Conflict on every attempt for both the crashed incarnation's sealed generation and a freshly sealed one. Candidate sites are the expected-prior-head mismatch arm (registry/publication.rs, the return Err(GraphDbError::Conflict) after the historical-seat guard) and the sealed-digest mismatch checks; the mapped Conflict is fieldless, so the log line carries no discriminating context.

Why this matters

Repro pointers

  • Live daemon PID 2408079 journal, 06:29–08:15 UTC window (journalctl --user -u tracedecay.service), plus RSS curves in /fast/tmp/td-sem-verify/rss5.ndjson.
  • The wedge survived a clean daemon restart (same conflicts on the prior incarnation from 06:36) and a fresh seal, so it reproduces from the durable journal + store state.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    bugSomething isn't working

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions