Skip to content

fix(agents): serialize new-session resolution per session key#85404

Open
openperf wants to merge 1 commit into
openclaw:mainfrom
openperf:fix/openai-compat-session-key-serialization-84575
Open

fix(agents): serialize new-session resolution per session key#85404
openperf wants to merge 1 commit into
openclaw:mainfrom
openperf:fix/openai-compat-session-key-serialization-84575

Conversation

@openperf
Copy link
Copy Markdown
Member

@openperf openperf commented May 22, 2026

Summary

  • Problem: Issue [Bug] /v1/chat/completions: second request with same x-openclaw-session-key during in-flight turn runs in isolated session, loses memory scope #84575 reports that two requests carrying the same x-openclaw-session-key at the OpenAI-compatible endpoints (/v1/chat/completions, /v1/responses) can run in separate sessions when the second arrives while the first is still in flight (e.g. a follow-up message sent before the first turn finishes). The later request starts from an empty session — session_status reports Context: 0/... and memory tools (memory_search) return nothing — so the agent loses all conversation/recall scope for that turn. Multi-user / multi-tab setups and any client that fires a quick follow-up before the previous turn finishes are exposed. Reporter juergenvh added gateway-side evidence on 2026-05-21 confirming the same shape against an embedded runtime.
  • Root Cause: Session identity is resolved by resolveSession (src/agents/command/session.ts) before the per-session execution lane is entered. When a session key has no fresh stored entry, resolveSession mints a brand-new sessionId via crypto.randomUUID(). Two commands for the same key that both reach this point before either persists the key→sessionId mapping each mint their own id. The per-session execution lane is keyed by session key, but it only serializes execution, not identity — so the second command runs against a different transcript and an empty memory scope. The WebChat chat.send path already guards concurrent sends; the agent-command path used by the OpenAI-compatible endpoints had no equivalent, leaving the resolve-then-mint step racy. resolveSession is intentionally synchronous (used by many sync callers), so the lock has to live one layer up at the agent-command async caller.
  • Fix: Add resolveSessionWithReservation (src/agents/command/session-resolution-reservation.ts) and call it from the agent-command pipeline (src/agents/agent-command.ts) in place of resolveSession. It serializes only the brand-new-session path, per session key: the first command persists the key→sessionId mapping inside a short critical section; any concurrent command re-resolves inside the lock, sees the reserved entry, and adopts the same sessionId instead of forking. This enforces the invariant "same session key ⇒ one session id" at the layer that owns session identity (so all ingress surfaces routed through agent-command benefit, not just one endpoint). Established sessions and explicit-sessionId runs skip the lock entirely (no added latency on the steady-state hot path); the critical section is independent of the per-session execution lane and completes before execution, so it cannot deadlock with it; the reserved entry is the same minimal mapping the command already persists moments later, so no new orphaning behavior; and internal handoffs (sessionEffects === "internal") also bypass the lock so they never write a visible store row, preserving the suppressVisibleSessionEffects contract.
  • What changed:
    • src/agents/command/session-resolution-reservation.ts: new resolveSessionWithReservation helper plus a per-session-key serialization queue. ResolveSessionInput declares clone?: boolean (forwarded to resolveSession) and suppressVisibleSessionEffects?: boolean (internal-handoff opt-out).
    • src/agents/command/session-resolution-reservation.test.ts: regression coverage — pre-fix race repro, concurrent-same-key convergence, follow-up reuse, explicit-sessionId passthrough, and the internal-handoff no-visible-row contract.
    • src/agents/agent-command.ts: resolve through resolveSessionWithReservation (one-line replace at prepareAgentCommandExecution); pass clone: false and suppressVisibleSessionEffects: opts.sessionEffects === "internal".
  • What did NOT change (scope boundary):
    • resolveSession semantics, the per-session execution lane, and the session-store schema are untouched. The helper composes existing primitives (resolveSession + persistSessionEntry) inside a per-key async mutex.
    • The explicit-sessionId path, ordinary single requests, established (already-persisted, fresh) sessions, and internal handoffs all bypass the reservation lock entirely.
    • Other prepareAgentCommandExecution regions touched by sibling PRs [Fix] Deliver restart recovery replies #86089 / fix(agents): persist user turn before attempt failures #86764 are in different regions of the function; this PR rebases cleanly on current origin/main with zero conflicts.
    • No config keys, gateway protocol, streaming/delivery behavior, plugin SDK, or session-store schema change.
    • No CHANGELOG.md edit (release-owned); no package.json / lockfile / shrinkwrap edit (Dependency Guard not applicable).

Reproduction

  1. Configure an agent reachable through the OpenAI-compatible endpoint with a stable x-openclaw-session-key.
  2. Send a long, multi-tool request for that session key.
  3. While it is still streaming, send a second request with the same x-openclaw-session-key.
  • Before: the second turn runs in an isolated session (session_status shows Context: 0/...); it has no recall of the in-flight conversation. On-disk session store ends up with two agent:main:<key> entries pointing at different sessionIds, and the sessions directory has two transcript files.
  • After: both turns share one session — the second adopts the first request's sessionId and retains conversation/recall scope. On-disk session store has a single agent:main:<key> entry; the sessions directory has exactly one transcript file.

Real behavior proof

  • Behavior addressed: concurrent commands carrying the same x-openclaw-session-key must converge on one sessionId and one transcript; once the first command persists the key→sessionId mapping, any concurrent same-key command re-resolves inside the lock and adopts the same id instead of forking an isolated, memory-less session.
  • Real environment tested: Linux x64, Node 22.22, OpenClaw Gateway built from this branch serving POST /v1/chat/completions, routed to a local OpenAI-compatible model endpoint with an isolated on-disk session store. Real curl requests, real on-disk session-store JSON, real session transcript files.
  • Exact steps or command run after this patch: launched openclaw gateway run (this branch) bound to the OpenAI-compatible endpoints; fired two concurrent curl calls to /v1/chat/completions carrying an identical x-openclaw-session-key: final-1779465436; inspected the on-disk session store and the per-session transcript files. Unit-level regression: node scripts/run-vitest.mjs src/agents/command/session-resolution-reservation.test.ts.
  • Evidence after fix (verbatim live console output):
two concurrent requests, identical x-openclaw-session-key=final-1779465436 (23:57:16 start -> 23:57:32 done)
$ curl .../v1/chat/completions -H 'x-openclaw-session-key: final-1779465436' -d '{"model":"openclaw","messages":[{"role":"user","content":"first turn"}]}' &
$ curl .../v1/chat/completions -H 'x-openclaw-session-key: final-1779465436' -d '{"model":"openclaw","messages":[{"role":"user","content":"second turn concurrent"}]}' &
A: {"id":"chatcmpl_189760ea-7315-4873-a704-bd3bc6b51fa7", ... "choices":[{"message":{"role":"assistant","content":"ok"},"finish_reason":"stop"}]}
B: {"id":"chatcmpl_9408b3a5-f114-45ba-aa49-f8d5e8ff3940", ... "choices":[{"message":{"role":"assistant","content":"ok"},"finish_reason":"stop"}]}

resolved session for that key (single store entry, single id):
agent:main:final-1779465436 -> sessionId bc472c1b-9cbb-4a8e-b337-51a53d3e2aef

session transcripts for that id (exactly one, so no fork):
bc472c1b-9cbb-4a8e-b337-51a53d3e2aef.jsonl
  • Observed result after fix: two distinct concurrent runs against one session key converged on one sessionId and one transcript file — the second request joined the in-flight session instead of forking an isolated, memory-less one. The on-disk session store recorded a single reservation-shaped entry { sessionId, updatedAt, sessionStartedAt } written by resolveSessionWithReservation. The explicit-sessionId path and steady-state established-session path are visibly unchanged (no lock entered).
  • Code-path coverage: node scripts/run-vitest.mjs src/agents/command/session-resolution-reservation.test.ts (10 passed across 2 files) covers the pre-fix race repro (two resolveSession calls fork distinct sessionIds), concurrent same-key convergence, follow-up reuse of the reserved id, explicit-sessionId passthrough, and the new internal-handoff contract (suppressVisibleSessionEffects: true does not write a visible session-store row).
  • What was not tested: a multi-hour production deployment and a third-party hosted model provider were not exercised; the live run used a local OpenAI-compatible model endpoint and an isolated session store. Cross-PR merge order with [Fix] Deliver restart recovery replies #86089 / fix(agents): persist user turn before attempt failures #86764 was not simulated end-to-end, but the branch rebases cleanly on current origin/main with zero conflicts.

Risk / Mitigation

  • Risk: per-key serialization could add latency or deadlock with the per-session execution lane. Mitigation: only the brand-new-session path takes the lock; established sessions, explicit-sessionId runs, and internal handoffs bypass it, so the steady-state hot path is unchanged. The critical section is resolveSession (sync) + one store write and completes before the execution lane is entered, so it cannot deadlock with it.
  • Risk: an early-reserved entry could orphan if the run aborts immediately after reservation. Mitigation: the reserved entry is the same minimal sessionId mapping the command persists moments later anyway; the orphan window matches the pre-fix crypto.randomUUID() + persistSessionEntry window — no new orphaning shape.
  • Risk: cross-PR conflict with [Fix] Deliver restart recovery replies #86089 (restart recovery) and fix(agents): persist user turn before attempt failures #86764 (persist user turn) inside prepareAgentCommandExecution. Mitigation: codegraph reports function-level overlap; actual diff regions do not collide. This PR rebases cleanly onto current origin/main (zero conflict). Merge order is independent.
  • Risk: ClawSweeper's prior P1 blockers — (1) ResolveSessionInput omitted clone, which the call site still passes; (2) reservation wrote a visible session-store row before agentCommandInternal derived suppressVisibleSessionEffects from opts.sessionEffects === "internal", breaking the documented internal-handoff contract. Mitigation: both addressed — clone?: boolean added to ResolveSessionInput and forwarded to resolveSession; suppressVisibleSessionEffects?: boolean added and short-circuits the lock+persist for internal runs; the call site computes the flag inline from opts.sessionEffects; a new test asserts internal handoffs do not write a visible row.

Change Type (select all)

  • Bug fix

Scope (select all touched areas)

  • Gateway / orchestration
  • Sessions / storage

Linked Issue/PR

Fixes #84575

@openclaw-barnacle openclaw-barnacle Bot added agents Agent runtime and tooling size: S triage: mock-only-proof Candidate: PR proof only shows tests, mocks, snapshots, lint, typecheck, or CI. labels May 22, 2026
@clawsweeper
Copy link
Copy Markdown
Contributor

clawsweeper Bot commented May 22, 2026

Codex review: needs maintainer review before merge. Reviewed May 29, 2026, 10:06 AM ET / 14:06 UTC.

Summary
The PR replaces direct resolveSession use in prepareAgentCommandExecution with a per-session-key reservation helper and adds regression tests for concurrent same-key session convergence and internal handoff behavior.

PR surface: Source +87, Tests +92. Total +179 across 3 files.

Reproducibility: yes. Current main resolves a session id before the execution lane and resolveSession can mint two UUIDs for the same fresh key; the PR also includes a focused regression test that demonstrates the fork and convergence after the helper.

Review metrics: none identified.

Merge readiness
Overall: 🐚 platinum hermit
Proof: 🦞 diamond lobster
Patch quality: 🐚 platinum hermit
Result: ready for maintainer review.

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

Rank-up moves:

  • Wait for the current head's in-progress checks to finish before landing.
  • Confirm merge order with the related agent-command session PRs if any of them lands first.

Risk before merge

Maintainer options:

  1. Land After Session-State Review (recommended)
    A maintainer can land this once the in-progress checks finish and the overlapping agent-command PR order is confirmed not to undo the reservation path.
  2. Refresh If Overlap Lands First
    If a related prepareAgentCommandExecution PR lands first, rebase this branch and re-check that same-key reservation, internal handoff suppression, and later session-entry persistence still compose.
  3. Pause Only If A Canonical Session Refactor Replaces It
    Pause or close this PR only if maintainers choose a broader canonical session identity refactor that directly covers the same concurrent session-key race.

Next step before merge

  • [P2] Maintainer review and landing coordination are the remaining actions; I did not find a narrow ClawSweeper repair task for this branch.

Security
Cleared: The diff adds an in-process session-key queue and tests only; it does not change workflows, dependencies, secrets, auth, package metadata, or external code execution paths.

Review details

Best possible solution:

Land the focused reservation helper after maintainer review, current CI completion, and overlap refresh, then let the linked bug close from the merged fix.

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

Yes. Current main resolves a session id before the execution lane and resolveSession can mint two UUIDs for the same fresh key; the PR also includes a focused regression test that demonstrates the fork and convergence after the helper.

Is this the best way to solve the issue?

Yes. The proposed layer is narrow because resolveSession stays synchronous, the async caller owns reservation, and the patch avoids schema, config, and protocol changes; the main remaining concern is merge-order coordination with adjacent agent-command work.

AGENTS.md: found and applied where relevant.

Codex review notes: model gpt-5.5, reasoning high; reviewed against 4925f84219ff.

Label changes

Label changes:

  • add rating: 🐚 platinum hermit: Overall readiness is 🐚 platinum hermit; proof is 🦞 diamond lobster and patch quality is 🐚 platinum hermit.
  • add status: 👀 ready for maintainer look: ClawSweeper has no concrete contributor-facing blocker left for this PR. Not applicable: The external-contributor proof gate does not apply to a member-authored PR, but the body includes useful live curl/session-store output and targeted regression test output for maintainer review.
  • remove rating: 🌊 off-meta tidepool: Current PR rating is rating: 🐚 platinum hermit, so this older rating label is no longer current.

Label justifications:

  • P2: This is a normal-priority session-state bug fix with user-visible memory/context loss but a bounded OpenAI-compatible agent-command surface.
  • merge-risk: 🚨 session-state: Merging changes when a new session-key mapping is reserved and could affect session identity, transcript association, or overlapping session-state fixes if composed incorrectly.
  • rating: 🐚 platinum hermit: Overall readiness is 🐚 platinum hermit; proof is 🦞 diamond lobster and patch quality is 🐚 platinum hermit.
  • status: 👀 ready for maintainer look: ClawSweeper has no concrete contributor-facing blocker left for this PR. Not applicable: The external-contributor proof gate does not apply to a member-authored PR, but the body includes useful live curl/session-store output and targeted regression test output for maintainer review.
Evidence reviewed

PR surface:

Source +87, Tests +92. Total +179 across 3 files.

View PR surface stats
Area Files Added Removed Net
Source 2 89 2 +87
Tests 1 92 0 +92
Docs 0 0 0 0
Config 0 0 0 0
Generated 0 0 0 0
Other 0 0 0 0
Total 3 181 2 +179

What I checked:

  • Repository policy read: Root AGENTS.md and scoped src/agents/AGENTS.md were read fully; their session-state, compatibility, scoped testing, and agents performance guidance shaped the review. (AGENTS.md:1, 4925f84219ff)
  • Current-main race source: Current resolveSession mints a new random session id whenever the resolved store entry is not fresh and no explicit session id was provided, before any agent-command execution lane is entered. (src/agents/command/session.ts:347, 4925f84219ff)
  • Current-main call site: On current main, prepareAgentCommandExecution resolves session identity synchronously with resolveSession before the later execution path persists the session entry. (src/agents/agent-command.ts:452, 4925f84219ff)
  • PR implementation: The proposed helper serializes only brand-new session reservation per storePath and sessionKey, re-resolves inside the critical section, persists the first mapping, and bypasses explicit session ids and internal visible-effect suppression. (src/agents/command/session-resolution-reservation.ts:52, 3b1a3b264368)
  • Regression coverage: The added test covers the pre-fix double-resolveSession fork, concurrent same-key convergence, later reuse of the reserved id, explicit session id passthrough, and no visible store row for internal handoffs. (src/agents/command/session-resolution-reservation.test.ts:32, 3b1a3b264368)
  • PR head and CI state: Live PR metadata shows head 3b1a3b26436818271ba19f4273b1b5bd05ca198c, mergeable: true, mergeable_state: unstable, Dependency Guard success, and several broader checks still in progress at inspection time. (3b1a3b264368)

Likely related people:

  • steipete: Current blame for resolveSession and the agent-command session resolution call site points to commit 150296261e11afa2692fbf86422a0258b7192835, and commit 00b57145ff01bce2324043369c841bbd1bb82780 created the extracted agents-layer files now being changed. (role: recent area contributor; confidence: high; commits: 150296261e11, 00b57145ff01, 0d938748a54d; files: src/agents/agent-command.ts, src/agents/command/session.ts)
  • Takhoffman: Commit df58b4f5fb62b39d65685fbaf958c5224ce67c38 is recent adjacent work on deterministic session-id resume targets in the same session-resolution area. (role: adjacent session-resolution contributor; confidence: medium; commits: df58b4f5fb62; files: src/agents/command/session.ts)
  • vincentkoc: Commit ce1fffa97e247e501f3f027403f079eca6c10af5 recently narrowed session helper imports in src/agents/command/session.ts, making this a relevant adjacent owner signal. (role: recent session helper contributor; confidence: medium; commits: ce1fffa97e24; files: src/agents/command/session.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.

@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. labels May 22, 2026
@clawsweeper
Copy link
Copy Markdown
Contributor

clawsweeper Bot commented May 22, 2026

ClawSweeper PR egg

✨ Hatched: 🥚 common Clockwork Shellbean

Hatch command

Comment @clawsweeper hatch when this PR is hatchable.

Hatchability rules:

  • Merged PRs are hatchable.
  • Open PRs are hatchable when they are status: 👀 ready for maintainer look, status: 🚀 automerge armed, or labeled clawsweeper:automerge.
  • Closed unmerged PRs are hatchable only when one of those hatchable labels is still present in the durable record.

Rarity: 🥚 common.
Trait: sleeps inside passing CI.
Image traits: location proof lagoon; accessory tiny test log scroll; palette cobalt, lime, and pearl; mood mischievous; pose peeking out from the egg shell; shell smooth pearl shell; lighting subtle sparkle highlights; background soft code-shaped tiles.
Share on X: post this hatch
Copy: My PR egg hatched a 🥚 common Clockwork Shellbean in ClawSweeper.

What is this egg doing here?
  • Eggs appear after the PR passes real-behavior proof. It is here for vibes, not verdicts: it does not change labels, ratings, merge decisions, or automation.
  • The shell reacts to review momentum: open follow-up work warms it up, re-review makes it wobble, and a clean final review lets it hatch.
  • Hatchability usually comes from sufficient real-behavior proof, no blocking P0/P1/P2 findings, no security attention needed, and clean correctness. A merged PR is already final, so merge makes the egg hatchable independently.
  • The hatch is seeded from this repository and PR number, so the same PR keeps the same creature; the reviewed head SHA can only change safe visual details.
  • Rarity is just collectible sparkle: 🥚 common, 🌱 uncommon, 💎 rare, ✨ glimmer, and 🌈 legendary.

@openclaw-barnacle openclaw-barnacle Bot added proof: supplied External PR includes structured after-fix real behavior proof. triage: needs-real-behavior-proof Candidate: external PR needs after-fix proof from a real setup. and removed triage: mock-only-proof Candidate: PR proof only shows tests, mocks, snapshots, lint, typecheck, or CI. proof: supplied External PR includes structured after-fix real behavior proof. labels May 22, 2026
@clawsweeper clawsweeper Bot added proof: sufficient ClawSweeper judged the real behavior proof convincing. rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR. P2 Normal backlog priority with limited blast radius. merge-risk: 🚨 session-state 🚨 May lose, corrupt, stale, or mis-associate session, agent, or context state. and removed 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. labels May 22, 2026
@openclaw-barnacle openclaw-barnacle Bot added proof: supplied External PR includes structured after-fix real behavior proof. and removed triage: needs-real-behavior-proof Candidate: external PR needs after-fix proof from a real setup. labels May 22, 2026
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 3d89040 to 5d6b9ca Compare May 22, 2026 16:50
@openclaw-barnacle openclaw-barnacle Bot removed the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 22, 2026
@clawsweeper clawsweeper Bot added the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 22, 2026
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 5d6b9ca to 8fde49f Compare May 23, 2026 00:54
@openclaw-barnacle openclaw-barnacle Bot removed the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 23, 2026
@clawsweeper clawsweeper Bot added the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 23, 2026
@osolmaz osolmaz self-assigned this May 28, 2026
@BingqingLyu

This comment was marked as spam.

@RomneyDa
Copy link
Copy Markdown
Member

Heads up: this PR needs to be updated against current main before the new required Dependency Guard check can pass.

@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 8fde49f to 005ffbb Compare May 29, 2026 06:29
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 005ffbb to cf81e99 Compare May 29, 2026 06:56
@clawsweeper clawsweeper Bot added rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. status: ⏳ waiting on author ClawSweeper has contributor-facing work open and is waiting for author action. and removed rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR. labels May 29, 2026
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from cf81e99 to 60bce25 Compare May 29, 2026 07:35
@clawsweeper clawsweeper Bot added rating: 🌊 off-meta tidepool PR readiness rating does not apply to this item. and removed proof: sufficient ClawSweeper judged the real behavior proof convincing. rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. status: ⏳ waiting on author ClawSweeper has contributor-facing work open and is waiting for author action. labels May 29, 2026
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 60bce25 to 573096e Compare May 29, 2026 13:17
Concurrent commands for the same session key minted separate sessionIds
because resolveSession ran before the per-session execution lane, so a
second OpenAI-compatible request that arrived mid-turn forked an isolated,
memory-less session. Reserve the brand-new-session path per session key so
concurrent commands adopt one sessionId.

Fixes openclaw#84575
@openperf openperf force-pushed the fix/openai-compat-session-key-serialization-84575 branch from 573096e to 3b1a3b2 Compare May 29, 2026 13:59
@clawsweeper clawsweeper Bot added rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR. and removed rating: 🌊 off-meta tidepool PR readiness rating does not apply to this item. labels May 29, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

agents Agent runtime and tooling merge-risk: 🚨 session-state 🚨 May lose, corrupt, stale, or mis-associate session, agent, or context state. P2 Normal backlog priority with limited blast radius. proof: supplied External PR includes structured after-fix real behavior proof. rating: 🐚 platinum hermit Good normal PR readiness with ordinary maintainer review expected. size: S status: 👀 ready for maintainer look ClawSweeper has no concrete contributor-facing blocker left for this PR.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug] /v1/chat/completions: second request with same x-openclaw-session-key during in-flight turn runs in isolated session, loses memory scope

4 participants