Skip to content

fix: stabilize claude-cli extraSystemPromptHash across group turns (#69118)#91157

Open
sumitaich1998 wants to merge 1 commit into
openclaw:mainfrom
sumitaich1998:fix/issue-69118-cli-groupintro-hash
Open

fix: stabilize claude-cli extraSystemPromptHash across group turns (#69118)#91157
sumitaich1998 wants to merge 1 commit into
openclaw:mainfrom
sumitaich1998:fix/issue-69118-cli-groupintro-hash

Conversation

@sumitaich1998

Copy link
Copy Markdown

Summary

On the claude-cli backend, agent sessions reset on every turn transition in
group-style channels (Discord channels, Telegram groups, etc.). Turn 2 is generated
against a fresh claude -p with no memory of turn 1, so the agent appears to have
"amnesia within seconds." This is independent of gateway restarts and is the companion
to #64386 (which covered mcpConfigHash drift on restart).

Root cause

claude-cli session reuse is gated by a fingerprint (extraSystemPromptHash) computed
in src/agents/cli-runner/prepare.ts over the static extra system prompt
(extraSystemPromptStatic). When the stored hash differs from the freshly computed one,
resolveCliSessionReuse() (src/agents/cli-session.ts) returns
invalidatedReason: "system-prompt", logged as:

cli session reset: provider=claude-cli reason=system-prompt

In src/auto-reply/reply/get-reply-run.ts runPreparedReply(), the hash input
extraSystemPromptStaticParts included groupIntro. But groupIntro is intentionally
first-turn-only:

const shouldInjectGroupIntro = Boolean(
  isGroupChat && (isFirstTurnInSession || sessionEntry?.groupActivationNeedsSystemIntro),
);

So the intro is present in the hash input on turn 1 and absent on turn 2 → the fingerprint
drifts between turns → claude-cli resets the session on every group turn.

The fix

Exclude the volatile, first-turn-only groupIntro from extraSystemPromptStaticParts
(the session-reuse hash input), while still injecting groupIntro into the live prompt
(extraSystemPromptParts) when appropriate. The static fingerprint is now identical across
turn 1 (intro present in the prompt) and turn 2 (intro absent), so the session is reused and
memory is preserved — consistent with how #64386 stabilized mcpConfigHash.

  • src/auto-reply/reply/get-reply-run.ts: drop groupIntro from extraSystemPromptStaticParts;
    the live extraSystemPromptParts still includes it. Added an inline comment documenting the invariant.

This also removes spurious resets on legitimate re-intros (groupActivationNeedsSystemIntro):
the re-intro text is still injected into the prompt but no longer forces a session reset.

Verification

Work was done in an isolated linked git worktree on fix/issue-69118-cli-groupintro-hash
(based on latest upstream/main).

Added a focused colocated regression test in
src/auto-reply/reply/get-reply-run.media-only.test.ts that drives runPreparedReply for a
first turn (groupIntro injected) and a later turn (groupIntro absent), asserting that:

  • the live prompt contains the intro on turn 1 only, and
  • extraSystemPromptStatic is identical across turns and never contains the intro.

Command (run from inside the worktree):

node scripts/run-vitest.mjs src/auto-reply/reply/get-reply-run.media-only.test.ts

Results:

  • With the fix: Test Files 1 passed (1) / Tests 81 passed (81), including the new test.
  • With the one-line fix reverted (groupIntro re-added to the static parts), the new test fails with
    expected 'GROUP-CHAT-CONTEXT\n\nGROUP-INTRO' not to contain 'GROUP-INTRO', confirming it is a
    true regression test.

Honest scope of testing:

  • Unit tests pass locally (Vitest).
  • I did not run OpenClaw locally (no gateway/CLI/pnpm dev/openclaw); the live claude-cli
    group-channel path was not exercised end-to-end.
  • No version bumps and no CHANGELOG.md edits.

Fixes #69118

@openclaw-barnacle openclaw-barnacle Bot added size: S triage: needs-real-behavior-proof Candidate: external PR needs after-fix proof from a real setup. labels Jun 7, 2026
@clawsweeper

clawsweeper Bot commented Jun 7, 2026

Copy link
Copy Markdown
Contributor

Codex review: needs real behavior proof before merge. Reviewed June 30, 2026, 2:31 PM ET / 18:31 UTC.

Summary
The PR removes first-turn-only group intro text from the static extra system prompt hash used for claude-cli session reuse and adds a focused regression test.

PR surface: Source +1, Tests +65. Total +66 across 2 files.

Reproducibility: yes. at source level: current main builds groupIntro only for first or re-intro group turns while including it in the static hash input, and CLI reuse invalidates on stored/current hash mismatch. This read-only review did not run a live claude-cli group-channel reproduction.

Review metrics: 1 noteworthy metric.

  • Closing references: 1 closing issue reference. Merging as written can automatically close a broader canonical issue before sibling false-invalidation variants are split or resolved.

Root-cause cluster
Relationship: fixed_by_candidate
Canonical: #69118
Summary: This PR is the open candidate fix for the groupIntro trigger in the canonical Claude CLI extraSystemPromptHash false-invalidation issue; related reports cover adjacent triggers in the same family.

Members:

Proposal only: this assessment does not dispatch repair, suppress jobs, mutate sibling items, close, or merge anything.

Merge readiness
Overall: 🧂 unranked krab
Proof: 🧂 unranked krab
Patch quality: 🦞 diamond lobster
Result: blocked until real behavior proof is added.

Overall follows the weaker of proof and patch quality, so missing proof can cap an otherwise strong patch.

Rank-up moves:

  • [P1] Add redacted live claude-cli Discord or Telegram group proof showing two consecutive turns reuse context after the patch.
  • Change the PR body closing reference to a non-closing reference unless maintainers split or resolve the remaining canonical issue variants.

Proof guidance:

  • [P1] Needs real behavior proof before merge: The PR body reports focused Vitest output and explicitly says no live gateway, CLI, or claude-cli group-channel path was exercised after the patch. After adding proof, update the PR body; ClawSweeper should re-review automatically. If it does not, the PR author or someone with repository write access can comment @clawsweeper re-review.

Mantis proof suggestion
A live Telegram group transcript plus redacted reset/reuse logs would materially prove the changed session-continuity behavior. A maintainer can ask Mantis to capture proof by posting this exact PR comment:

@openclaw-mantis telegram live proof: verify two consecutive claude-cli replies in a Telegram group reuse context after this PR, with redacted reset/reuse logs.

Risk before merge

Maintainer options:

  1. Add Proof And Keep The Tracker Open (recommended)
    Before merge, add redacted live claude-cli group proof and replace the closing reference with a non-closing link unless sibling variants are split or resolved.
  2. Accept Broad Closure Deliberately
    Maintainers may keep the closing reference only if they intentionally decide the remaining false-invalidation variants are already tracked elsewhere or out of scope.
  3. Pause For Scope Split
    Pause this PR if maintainers want the groupIntro trigger split from the broader false-invalidation class before any merge can close the canonical issue.

Next step before merge

  • [P1] Contributor or maintainer action is needed to add real behavior proof and decide whether the broad closing reference should remain; there is no narrow branch code repair indicated.

Security
Cleared: The diff only changes prompt-composition logic and a colocated Vitest test; it does not touch dependencies, workflows, package metadata, permissions, or secrets.

Review details

Best possible solution:

Land the narrow groupIntro static-hash fix after redacted live group-channel proof, and keep or split the canonical false-invalidation tracker so sibling variants remain visible.

Do we have a high-confidence way to reproduce the issue?

Yes at source level: current main builds groupIntro only for first or re-intro group turns while including it in the static hash input, and CLI reuse invalidates on stored/current hash mismatch. This read-only review did not run a live claude-cli group-channel reproduction.

Is this the best way to solve the issue?

Yes for the groupIntro trigger: excluding first-turn-only intro text from durable reuse identity is the narrowest maintainable fix while preserving the live prompt. It is not a complete solution for the broader false-invalidation class, so the canonical issue should remain open or be split before merge.

AGENTS.md: found and applied where relevant.

Codex review notes: model internal, reasoning high; reviewed against 5e0652f284a8.

Label changes

Label justifications:

  • P1: The PR targets a user-facing claude-cli session-state regression where group-channel follow-up turns can lose prior conversation context.
  • merge-risk: 🚨 automation: The closing reference can trigger GitHub issue-closing automation for a broader canonical tracker before remaining variants are handled.
  • merge-risk: 🚨 session-state: The diff changes the durable prompt identity used for CLI session reuse, so a wrong fix could reset or reuse session context incorrectly.
  • rating: 🧂 unranked krab: Overall readiness is 🧂 unranked krab; proof is 🧂 unranked krab and patch quality is 🦞 diamond lobster.
  • status: 📣 needs proof: The PR needs real behavior proof before ClawSweeper can clear the contributor ask. Needs real behavior proof before merge: The PR body reports focused Vitest output and explicitly says no live gateway, CLI, or claude-cli group-channel path was exercised after the patch. After adding proof, update the PR body; ClawSweeper should re-review automatically. If it does not, the PR author or someone with repository write access can comment @clawsweeper re-review.
  • mantis: telegram-visible-proof: Mantis should capture Telegram visible proof. The fix affects visible Telegram group conversation continuity and can be demonstrated in a short Telegram proof run with redacted transcript and reset/reuse logs.
Evidence reviewed

PR surface:

Source +1, Tests +65. Total +66 across 2 files.

View PR surface stats
Area Files Added Removed Net
Source 1 3 2 +1
Tests 1 65 0 +65
Docs 0 0 0 0
Config 0 0 0 0
Generated 0 0 0 0
Other 0 0 0 0
Total 2 68 2 +66

What I checked:

Likely related people:

  • Vincent Koc: Current blame for the affected prompt assembly, hash preparation, and comparator lines points to the recent carry-forward commit that touched these files. (role: recent current-main carrier; confidence: medium; commits: 18b2ff683fd3; files: src/auto-reply/reply/get-reply-run.ts, src/agents/cli-runner/prepare.ts, src/agents/cli-session.ts)
  • Peter Steinberger: The feature-history search shows the get-reply-run module was introduced in the reply pipeline split, which is the current owner boundary for this prompt assembly. (role: reply-pipeline split author; confidence: medium; commits: ea018a68ccb9; files: src/auto-reply/reply/get-reply-run.ts)
What the crustacean ranks mean
  • 🦀 challenger crab: rare, exceptional readiness with strong proof, clean implementation, and convincing validation.
  • 🦞 diamond lobster: very strong readiness with only minor maintainer review expected.
  • 🐚 platinum hermit: good normal PR, likely mergeable with ordinary maintainer review.
  • 🦐 gold shrimp: useful signal, but proof or patch confidence is still limited.
  • 🦪 silver shellfish: thin signal; proof, validation, or implementation needs work.
  • 🧂 unranked krab: not merge-ready because proof is missing/unusable or there are serious correctness or safety concerns.
  • 🌊 off-meta tidepool: rating does not apply to this item.

Shiny media proof means a screenshot, video, or linked artifact directly shows the changed behavior. Runtime, network, CSP, and security claims still need visible diagnostics.

How this review workflow works
  • ClawSweeper keeps one durable marker-backed review comment per issue or PR.
  • Re-runs edit this comment so the latest verdict, findings, and automation markers stay together instead of adding duplicate bot comments.
  • A fresh review can be triggered by eligible @clawsweeper re-review comments, exact-item GitHub events, scheduled/background review runs, or manual workflow dispatch.
  • PR/issue authors and users with repository write access can comment @clawsweeper re-review or @clawsweeper re-run on an open PR or issue to request a fresh review only.
  • Maintainers can also comment @clawsweeper review to request a fresh review only.
  • Fresh-review commands do not start repair, autofix, rebase, CI repair, or automerge.
  • Maintainer-only repair and merge flows require explicit commands such as @clawsweeper autofix, @clawsweeper automerge, @clawsweeper fix ci, or @clawsweeper address review.
  • Maintainers can comment @clawsweeper explain to ask for more context, or @clawsweeper stop to stop active automation.
Review history (1 earlier review cycle)
  • reviewed 2026-06-21T15:54:40.124Z sha 85acdd4 :: needs real behavior proof before merge. :: none

@clawsweeper clawsweeper Bot added rating: 🦪 silver shellfish Thin PR readiness signal; proof, validation, or implementation needs work. status: 📣 needs proof The PR needs real behavior proof before ClawSweeper can clear the contributor ask. mantis: telegram-visible-proof Mantis should capture Telegram visible proof. P1 High-priority user-facing bug, regression, or broken workflow. merge-risk: 🚨 automation 🚨 May affect CI, automerge, proof capture, label sync, or maintainer automation. labels Jun 7, 2026
@clawsweeper clawsweeper Bot added rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. and removed rating: 🦪 silver shellfish Thin PR readiness signal; proof, validation, or implementation needs work. labels Jun 15, 2026
@clawsweeper clawsweeper Bot added the merge-risk: 🚨 session-state 🚨 May lose, corrupt, stale, or mis-associate session, agent, or context state. label Jun 21, 2026
@openclaw-barnacle openclaw-barnacle Bot added the triage: needs-pr-context Candidate: external PR body lacks required problem context or evidence. label Jun 21, 2026
@openclaw-barnacle

Copy link
Copy Markdown

This pull request has been automatically marked as stale due to inactivity.
Please add updates or it will be closed.

@openclaw-barnacle openclaw-barnacle Bot added the stale Marked as stale due to inactivity label Jul 21, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

mantis: telegram-visible-proof Mantis should capture Telegram visible proof. merge-risk: 🚨 automation 🚨 May affect CI, automerge, proof capture, label sync, or maintainer automation. merge-risk: 🚨 session-state 🚨 May lose, corrupt, stale, or mis-associate session, agent, or context state. P1 High-priority user-facing bug, regression, or broken workflow. rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. size: S stale Marked as stale due to inactivity status: 📣 needs proof The PR needs real behavior proof before ClawSweeper can clear the contributor ask. triage: needs-pr-context Candidate: external PR body lacks required problem context or evidence. triage: needs-real-behavior-proof Candidate: external PR needs after-fix proof from a real setup.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Claude CLI sessions reset on every turn in group channels due to groupIntro drift in extraSystemPromptHash

1 participant