-
-
Notifications
You must be signed in to change notification settings - Fork 80.7k
Inbound routing and restart-sentinel resume reattach to status:done sessions #86593
Copy link
Copy link
Closed
Closed
Copy link
Labels
P1High-priority user-facing bug, regression, or broken workflow.High-priority user-facing bug, regression, or broken workflow.clawsweeper:fix-shape-clearClawSweeper found a clear likely implementation shape for this issue.ClawSweeper found a clear likely implementation shape for this issue.clawsweeper:needs-maintainer-reviewClawSweeper marked this issue as needing maintainer review before automation.ClawSweeper marked this issue as needing maintainer review before automation.clawsweeper:needs-product-decisionClawSweeper marked this issue as needing a product or behavior decision.ClawSweeper marked this issue as needing a product or behavior decision.clawsweeper:no-new-fix-prClawSweeper does not recommend queueing a new automated fix PR for this issue.ClawSweeper does not recommend queueing a new automated fix PR for this issue.clawsweeper:source-reproClawSweeper found a high-confidence source-level issue reproduction.ClawSweeper found a high-confidence source-level issue reproduction.impact:message-lossChannel message delivery can be lost, duplicated, or misrouted.Channel message delivery can be lost, duplicated, or misrouted.impact:session-stateSession, memory, transcript, context, or agent state can drift or corrupt.Session, memory, transcript, context, or agent state can drift or corrupt.issue-rating: 🦞 diamond lobsterVery strong issue quality with high-confidence source-level or clear reproduction.Very strong issue quality with high-confidence source-level or clear reproduction.
Description
Metadata
Metadata
Assignees
Labels
P1High-priority user-facing bug, regression, or broken workflow.High-priority user-facing bug, regression, or broken workflow.clawsweeper:fix-shape-clearClawSweeper found a clear likely implementation shape for this issue.ClawSweeper found a clear likely implementation shape for this issue.clawsweeper:needs-maintainer-reviewClawSweeper marked this issue as needing maintainer review before automation.ClawSweeper marked this issue as needing maintainer review before automation.clawsweeper:needs-product-decisionClawSweeper marked this issue as needing a product or behavior decision.ClawSweeper marked this issue as needing a product or behavior decision.clawsweeper:no-new-fix-prClawSweeper does not recommend queueing a new automated fix PR for this issue.ClawSweeper does not recommend queueing a new automated fix PR for this issue.clawsweeper:source-reproClawSweeper found a high-confidence source-level issue reproduction.ClawSweeper found a high-confidence source-level issue reproduction.impact:message-lossChannel message delivery can be lost, duplicated, or misrouted.Channel message delivery can be lost, duplicated, or misrouted.impact:session-stateSession, memory, transcript, context, or agent state can drift or corrupt.Session, memory, transcript, context, or agent state can drift or corrupt.issue-rating: 🦞 diamond lobsterVery strong issue quality with high-confidence source-level or clear reproduction.Very strong issue quality with high-confidence source-level or clear reproduction.
Type
Fields
Priority
None yet
Summary
After
/newis issued, the session is markedstatus: "done"withendedAtset, but the entry remains insessions.jsonunder the original routing key. If a gateway restart occurs while acontinuationMessageis queued — or any subsequent inbound arrives — the samedoneentry is reused instead of a new session being spawned. The restart-sentinel resume path also writes to the done session directly, refreshingupdatedAtand effectively "resurrecting" it. Downstream this triggers preflight-compaction failures and channel-visible "Something went wrong" errors that persist until the session entry is manually removed.Evidence (Telegram group, topic 17)
commands.log:/newissued at2026-05-25T16:19:05ZagainstsessionKey=agent:openclaw-admin:telegram:group:<id>:topic:17.sessions.jsonsnapshot for same key:status: "done",endedAt: 1779726659123(13:30:59 SP) — set 11 min after/new.Preflight compaction required but failed: no real conversation messages.cliSessionIdand nocontinuationMessagefield at read time (sentinel had already been consumed and cleared).Root cause (two defects)
1.
evaluateSessionFreshnessignores terminal statusdist/session-DUinUmLM.js:188calls it viaresolveSession; the function (dist/reset-B0OJOtNI.js:35-48) consults onlyupdatedAt/sessionStartedAt/lastInteractionAt. Adone/failed/killed/timeoutentry whose timestamps are inside the daily/idle window is treated as fresh.Note:
isTerminalSessionStatusexists indist/session-utils-CRKr-5AU.js:170returning true fordone|failed|killed|timeout— but it is not consulted by routing.2. Restart-sentinel startup task re-binds to a done session without a status guard
loadRestartSentinelStartupTaskindist/server-restart-sentinel-zgIzZ1w7.js:582-720:```js
const { cfg, entry, canonicalKey } = loadSessionEntry(sessionKey);
…
continuationQueueId = await enqueueSessionDelivery(buildQueuedRestartContinuation({
sessionKey: canonicalKey,
continuation: payload.continuation, …
}));
```
There is no check that
entry.status !== 'done'orentry.endedAt == nullbefore enqueueing the continuation. This both delivers anagentTurncontinuation against the closed session and bumpsupdatedAt, which then defeats freshness checks for later inbounds.3.
/newonly flips status; the routing key is not unlinkedSee e.g.
dist/get-reply-DOTqK3jN.js:2642-2644, 3338, 4516and thethis.status = "done"site indist/server-methods-90LGtoqF.js:16227. The key continues to satisfyresolveSessionKey(scope, ctx, mainKey, storeAgentId)indist/session-DUinUmLM.js:130.Reproduce
/newto a Telegram topic session.endedAtis set on that entry, trigger (or wait for) a gateway restart whose sentinel payload includes the samesessionKeywith acontinuation.updatedAtadvance and a continuation delivered against it.sessionId.Suggested fix
resolveSession(dist/session-DUinUmLM.js), treat any entry whereisTerminalSessionStatus(entry.status)ortypeof entry.endedAt === 'number'as not fresh, regardless of timestamps. ForceisNewSession=trueand a newsessionId.loadRestartSentinelStartupTask(dist/server-restart-sentinel-zgIzZ1w7.js), before enqueueing thecontinuation, check the loadedentry; if terminal, either drop the continuation, route it via a freshly spawned session, or route it as a system notice only (noagentTurnresume)./new(or/reset) marks a session terminal, also rotate the routing index entry (e.g. archive under a sessionId-suffixed key) so the canonicalto-keyed lookup misses on the next inbound.Affected symbols
dist/session-DUinUmLM.js—resolveSession,resolveSessionKeyForRequest(no terminal-status guard).dist/reset-B0OJOtNI.js—evaluateSessionFreshness(timestamps only).dist/server-restart-sentinel-zgIzZ1w7.js—loadRestartSentinelStartupTask,recoverPendingRestartContinuationDeliveries(re-binds to a done session without status check).dist/restart-sentinel-BDtpdKoy.js—buildRestartSuccessContinuation,writeRestartSentinel.dist/session-utils-CRKr-5AU.js:170—isTerminalSessionStatusexists but is unused by routing.dist/get-reply-DOTqK3jN.js:2642-2644,3338,4516—/newhandling: marks done but does not unlink/rename the routing key.dist/server-methods-90LGtoqF.js:16227—this.status = "done".Related
Filed alongside a separate issue for inbound user messages not persisting to session JSONL when the agent attempt throws. That bug + this one combine to permanently wedge the session: throw → empty jsonl → over-cap → preflight fails forever because routing won't release the key.