Repository navigation
refactor(runtime): converge AgentRun metadata into the RuntimeInvocation event spine #4311
Description
Problem
Maka currently represents one physical runtime attempt through overlapping durable identities and ledgers:
RuntimeEventis the canonical execution and model-history fact.AgentRunHeaderis a mutable per-run record containing route, configuration, lineage, and lifecycle projection state.AgentRunEventis a separate append-only operational ledger containing lifecycle, provider-attempt, accounting, checkpoint, permission, and diagnostic records.- Phase 0–3 define one
invocationIdperrunId; production construction commonly sets them to the same value.
This was a reasonable migration shape: AgentRun first extracted one execution from SessionManager and supplied durable recovery metadata; Runtime v2 then introduced RuntimeEvent as the canonical fact model without a flag-day storage migration. The transition is now incomplete.
PR #4286 exposed the cost directly. Provider-owned reasoning lives on RuntimeEvent, but its source route is resolved through event.runId -> AgentRunHeader. Every normal, continuation, compaction, overflow, and durable-reload exit therefore has to carry both records. One missing Header path deterministically removed compatible reasoning from provider requests even though the durable replay boundary had admitted it.
Renaming AgentRun or AgentRunHeader would preserve that split. The goal is to remove the duplicate authority, not give it a new noun.
Target authority model
Session
-> RuntimeInvocation
-> immutable run-opening fact
-> RuntimeEvent[]
-> one terminal RuntimeEvent
-> rebuildable RuntimeInvocationIndex
sessionIdidentifies the conversation.turnIdidentifies the user-semantic turn.invocationIdidentifies one physical execution attempt.- Runtime events hold immutable execution facts.
- One opening fact holds invocation-scoped metadata once; route/configuration is not copied to every event.
- The terminal RuntimeEvent is the lifecycle outcome authority.
- Any index used for enumeration or query is rebuildable and has no independent semantic writer.
The current AgentRun in-memory object may remain as the live execution owner during migration. Its eventual naming or decomposition follows responsibility; it is not a reason to retain a durable AgentRunHeader authority.
Migration workstreams
1. Define the invocation opening fact and derived index contract
- Classify every current
AgentRunHeaderfield as immutable opening metadata, RuntimeEvent-derived terminal state, dedicated control-plane authority, operational diagnostic, or legacy-only data. - Define one closed, versioned invocation-opening fact committed before provider/tool dispatch.
- Define the rebuildable
RuntimeInvocationIndexrequired for session enumeration and indexed lookups. - Prove whether
runIdandinvocationIdremain exactly one-to-one across supported current writers, recovery, continuation, copy/import, and persisted data. Do not collapse them on naming preference alone.
2. Make new executions event-first
- Commit the opening fact before the first provider/tool side effect.
- Derive route, configuration, lineage, and lifecycle reads from opening/terminal facts through the index.
- Keep compatibility reading for legacy Header-only runs behind one bounded migration seam; do not create permanent dual-write authority.
- Make index repair/rebuild deterministic and crash safe.
3. Move consumers off independent Header semantics
- Migrate replay provenance, continuation/recovery admission, session/graph inspection, copy/import, checkpoint lookup, and execution diagnostics to the canonical invocation facts plus derived index.
- Classify
AgentRunEventwriters individually. Move duplicated lifecycle/tool/permission facts to their canonical owners; retain metering, request-attempt, checkpoint, and diagnostic facts only where they have an independent operational demand. - Do not funnel unrelated accounting or control-plane state into model-history RuntimeEvents merely to reduce table count.
4. Retire the old authority
- Stop current production writers from independently creating or mutating
AgentRunHeadersemantic state. - Remove legacy Header reads after the declared compatibility window and verified migration/rebuild coverage.
- Remove the old Header storage surface and any AgentRun lifecycle events made redundant by canonical RuntimeEvents.
- If workstream 1 proves
runIdandinvocationIdare the same supported identity, converge oninvocationId; otherwise document and encode the real multiplicity before retaining both. - Rename or fold the live
AgentRunexecutor only after its durable meaning has disappeared; avoid a mechanicalSingleRunrename.
Invariants
- No provider or tool dispatch occurs before a durable invocation-opening fact when durability is required.
- Route provenance is recorded once per invocation and can be joined to every event without copying it onto each event.
- Terminal lifecycle state is derived from the terminal RuntimeEvent and cannot disagree with an independently written Header.
- Clearing the derived invocation index and rebuilding from canonical facts produces the same current-session run inventory and replay provenance.
- Continuation, recovery, compaction, overflow retry, restart, copy/branch, and inspection do not require a parallel Header authority.
- Legacy data fails closed where provenance is missing but retains portable transcript and tool evidence.
- The migration has a defined end state; no permanent old/new dual read or dual write remains.
Non-goals
- Expanding PR fix(runtime): gate provider reasoning replay by source model #4286 beyond its provider-replay correctness fix.
- Copying connection/model metadata into every RuntimeEvent or provider option.
- Rewriting
ToolRuntime, provider model loops, or AI SDK converters. - Combining all operational telemetry, accounting, and model-history facts into one untyped event catalogue.
- Renaming
AgentRuntoSingleRunwithout deleting an authority or identity.
Done
- Invocation-opening fact and rebuildable index contract are accepted.
- New executions no longer require independent Header semantic writes.
- All current consumers read canonical invocation facts or the derived index.
- Legacy migration/compatibility window is complete and verified.
- Independent
AgentRunHeaderauthority is removed. -
runIdandinvocationIdare either converged or retained with proven distinct semantics.
Activity
feat(core): define the invocation opening fact as a RuntimeEvent
feat(runtime): open every invocation with a durable opening fact
feat(storage): enumerate a Session's invocations from the event spine
feat(storage): keep a migrated invocation's opening beside the ones e…
refactor(core): record the Run Composition on the ledger instead of t…
refactor(core): make a continuation claim name its target's opening, …
refactor(core): match a hosted root against the opening's closed root…
refactor(core): retire three AgentRunEvent types nothing writes
feat(core): define the invocation opening fact as a RuntimeEvent
feat(runtime): open every invocation with a durable opening fact
feat(storage): enumerate a Session's invocations from the event spine
33 remaining items
refactor(core): record the Run Composition on the ledger instead of t…
refactor(core): make a continuation claim name its target's opening, …
refactor(core): match a hosted root against the opening's closed root…
refactor(core): retire three AgentRunEvent types nothing writes
feat(core): define the invocation opening fact as a RuntimeEvent
feat(runtime): open every invocation with a durable opening fact
feat(storage): enumerate a Session's invocations from the event spine
feat(storage): keep a migrated invocation's opening beside the ones e…
refactor(core): record the Run Composition on the ledger instead of t…
refactor(core): make a continuation claim name its target's opening, …
refactor(core): match a hosted root against the opening's closed root…
refactor(core): retire three AgentRunEvent types nothing writes
refactor(runtime): converge AgentRun metadata into the RuntimeInvocat…
docs: verify the runtime core docs against main (#3522) (#6054)