Skip to content

Preserve runtime external auth snapshots#85558

Merged
clawsweeper[bot] merged 2 commits into
openclaw:mainfrom
TurboTheTurtle:fix/auth-snapshot-external-profiles-85521
May 26, 2026
Merged

Preserve runtime external auth snapshots#85558
clawsweeper[bot] merged 2 commits into
openclaw:mainfrom
TurboTheTurtle:fix/auth-snapshot-external-profiles-85521

Conversation

@TurboTheTurtle

Copy link
Copy Markdown
Contributor

Summary

  • keep saveAuthProfileStore disk persistence filtered for runtime-only external CLI OAuth profiles
  • refresh active runtime snapshots with a runtime-safe store that preserves those external OAuth profiles while still excluding inherited main OAuth credentials
  • add regression coverage for anthropic:claude-cli remaining available in-process after save while staying out of auth-profiles.json and auth-state.json

Fixes #85521

Real behavior proof

Behavior addressed: Saving an auth profile store with an active runtime snapshot no longer replaces in-process runtime state with the disk-filtered store, so runtime-only external CLI OAuth profiles such as anthropic:claude-cli remain available after save while staying out of persisted local auth files.

Real environment tested: Local OpenClaw checkout on macOS, Node via the repository test runner, using the real auth profile store implementation plus OpenClaw's external-auth runtime test hook to model a runtime-only external CLI OAuth profile.

Exact steps or command run after this patch:

node scripts/run-vitest.mjs src/agents/auth-profiles.store.save.test.ts src/agents/auth-profiles.ensureauthprofilestore.test.ts src/agents/model-provider-auth.test.ts
node --import tsx --input-type=module <<'EOF_SCRIPT'
import fs from 'node:fs/promises';
import os from 'node:os';
import path from 'node:path';
import {
  clearRuntimeAuthProfileStoreSnapshots,
  ensureAuthProfileStore,
  replaceRuntimeAuthProfileStoreSnapshots,
  saveAuthProfileStore,
} from './src/agents/auth-profiles/store.ts';
import { resolveAuthStatePath, resolveAuthStorePath } from './src/agents/auth-profiles/paths.ts';
import { testing as externalAuthTesting } from './src/agents/auth-profiles/external-auth.ts';

const agentDir = await fs.mkdtemp(path.join(os.tmpdir(), 'openclaw-85521-proof-'));
const externalProfileId = 'anthropic:claude-cli';
const localProfileId = 'openai:default';
const externalCredential = {
  type: 'oauth',
  provider: 'anthropic',
  access: 'external-access',
  refresh: 'external-refresh',
  expires: 2,
};

try {
  externalAuthTesting.setResolveExternalAuthProfilesForTest(() => [
    { profileId: externalProfileId, credential: externalCredential, persistence: 'runtime-only' },
  ]);
  replaceRuntimeAuthProfileStoreSnapshots([
    {
      agentDir,
      store: {
        version: 1,
        profiles: {
          [externalProfileId]: {
            type: 'oauth',
            provider: 'anthropic',
            access: 'stale-external-access',
            refresh: 'stale-external-refresh',
            expires: 1,
          },
        },
      },
    },
  ]);

  saveAuthProfileStore(
    {
      version: 1,
      profiles: {
        [externalProfileId]: externalCredential,
        [localProfileId]: { type: 'api_key', provider: 'openai', key: 'sk-local-proof' },
      },
      order: { anthropic: [externalProfileId], openai: [localProfileId] },
      lastGood: { anthropic: externalProfileId, openai: localProfileId },
      usageStats: { [externalProfileId]: { lastUsed: 123 }, [localProfileId]: { lastUsed: 456 } },
    },
    agentDir,
  );

  const persisted = JSON.parse(await fs.readFile(resolveAuthStorePath(agentDir), 'utf8'));
  const state = JSON.parse(await fs.readFile(resolveAuthStatePath(agentDir), 'utf8'));
  const runtime = ensureAuthProfileStore(agentDir);
  console.log(JSON.stringify({
    persistedHasExternalProfile: Object.hasOwn(persisted.profiles, externalProfileId),
    persistedHasLocalProfile: Object.hasOwn(persisted.profiles, localProfileId),
    persistedStateHasExternalOrder: Object.hasOwn(state.order ?? {}, 'anthropic'),
    runtimeHasExternalProfile: Object.hasOwn(runtime.profiles, externalProfileId),
    runtimeExternalAccess: runtime.profiles[externalProfileId]?.access,
    runtimeExternalRefresh: runtime.profiles[externalProfileId]?.refresh,
    runtimeOrderIncludesExternal: runtime.order?.anthropic?.includes(externalProfileId) ?? false,
    runtimeLastGoodExternal: runtime.lastGood?.anthropic,
  }, null, 2));
} finally {
  externalAuthTesting.resetResolveExternalAuthProfilesForTest();
  clearRuntimeAuthProfileStoreSnapshots();
  await fs.rm(agentDir, { recursive: true, force: true });
}
EOF_SCRIPT

Evidence after fix:

Test Files  6 passed (6)
Tests  92 passed (92)
{
  "persistedHasExternalProfile": false,
  "persistedHasLocalProfile": true,
  "persistedStateHasExternalOrder": false,
  "runtimeHasExternalProfile": true,
  "runtimeExternalAccess": "external-access",
  "runtimeExternalRefresh": "external-refresh",
  "runtimeOrderIncludesExternal": true,
  "runtimeLastGoodExternal": "anthropic:claude-cli"
}

Observed result after fix: The runtime-only external OAuth credential is absent from persisted auth files but still present in the active runtime snapshot immediately after saveAuthProfileStore, so subsequent snapshot-backed auth resolution can still find anthropic:claude-cli.

What was not tested: I did not launch a real Anthropic Claude CLI process or perform a live OAuth refresh against Anthropic; the proof exercises OpenClaw's auth store behavior directly with fake token material.

Author attribution

If this PR is squashed or reworked, please preserve author attribution for Andy Ye 35905412+TurboTheTurtle@users.noreply.github.com or include:

Co-authored-by: Andy Ye 35905412+TurboTheTurtle@users.noreply.github.com

@TurboTheTurtle TurboTheTurtle requested a review from a team as a code owner May 23, 2026 00:42
@openclaw-barnacle openclaw-barnacle Bot added agents Agent runtime and tooling size: S proof: supplied External PR includes structured after-fix real behavior proof. labels May 23, 2026
@clawsweeper

clawsweeper Bot commented May 23, 2026

Copy link
Copy Markdown
Contributor

Codex review: passed. Reviewed May 26, 2026, 12:41 AM ET / 04:41 UTC.

Summary
The PR adds runtime-only external OAuth provenance to auth-profile stores, updates save/merge/read paths to preserve those profiles in active snapshots while filtering disk persistence, and expands auth-profile regression tests.

PR surface: Source +381, Tests +974. Total +1355 across 8 files.

Reproducibility: yes. from source: current main writes the disk-filtered localStore into an existing runtime snapshot after save, which matches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Review metrics: none identified.

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

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

Risk before merge

  • This changes auth-provider and runtime snapshot merge semantics, so focused tests do not fully replace a live external Claude CLI OAuth smoke if maintainers want end-to-end provider proof.
  • The credential boundary is sensitive: maintainers should land only after exact-head checks confirm the runtime preservation path still keeps runtime-only external OAuth out of persisted auth files.

Maintainer options:

  1. Accept focused auth-store proof (recommended)
    Maintainers can accept the direct auth-store proof plus Testbox changed gate as sufficient because the remaining gap is live external-provider smoke coverage, not an identified patch defect.
  2. Require live external-CLI smoke
    Maintainers can pause merge until someone proves a real Claude CLI OAuth-backed gateway turn survives a saveAuthProfileStore-triggering config write.

Next step before merge
No repair lane is needed because there are no actionable patch findings; the remaining action is exact-head merge gating or maintainer choice on optional live provider proof.

Security
Cleared: No supply-chain files changed, and the credential-boundary tests assert runtime-only external OAuth stays out of persisted auth files while remaining in runtime memory.

Review details

Best possible solution:

Land the branch after exact-head CI/automerge gates if maintainers accept the supplied direct auth-store proof; request a live Claude CLI smoke only if end-to-end provider proof is required before merge.

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

Yes from source: current main writes the disk-filtered localStore into an existing runtime snapshot after save, which matches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Is this the best way to solve the issue?

Yes, the branch fixes the implicated save path while preserving disk filtering and adds boundary tests for runtime preservation, authoritative removal, and inherited main OAuth behavior. A live Claude CLI smoke would improve end-to-end confidence but is not required to identify the source-level fix.

AGENTS.md: found and applied where relevant.

Codex review notes: model gpt-5.5, reasoning high; reviewed against 7db4b3db412d.

Label changes

Label justifications:

  • P1: The linked bug breaks embedded-agent credential resolution for external CLI OAuth users after runtime auth saves.
  • merge-risk: 🚨 auth-provider: The patch changes OAuth profile persistence and runtime credential overlay behavior for external CLI auth providers.
  • merge-risk: 🚨 session-state: The patch changes active in-process auth snapshot preservation and merge semantics across save/read paths.
  • rating: 🦞 diamond lobster: Overall readiness is 🦞 diamond lobster; proof is 🦞 diamond lobster and patch quality is 🦞 diamond lobster.
  • status: 🚀 automerge armed: This PR is in ClawSweeper's automerge lane. Sufficient (terminal): The PR body includes direct post-patch command output and JSON showing persisted files exclude the external profile while runtime keeps it, with additional maintainer Testbox verification in comments.
  • proof: sufficient: Contributor real behavior proof is sufficient. The PR body includes direct post-patch command output and JSON showing persisted files exclude the external profile while runtime keeps it, with additional maintainer Testbox verification in comments.
Evidence reviewed

PR surface:

Source +381, Tests +974. Total +1355 across 8 files.

View PR surface stats
Area Files Added Removed Net
Source 5 428 47 +381
Tests 3 985 11 +974
Docs 0 0 0 0
Config 0 0 0 0
Generated 0 0 0 0
Other 0 0 0 0
Total 8 1413 58 +1355

What I checked:

  • Current main still has the clobber path: On current main, saveAuthProfileStore builds localStore for disk persistence and then installs that same localStore into the runtime snapshot when one exists. (src/agents/auth-profiles/store.ts:773, 7db4b3db412d)
  • PR separates disk and runtime save stores: The PR keeps localStore for persisted files but refreshes active runtime snapshots with buildRuntimeAuthProfileStoreForSave and mergeRuntimeExternalProfileReferences. (src/agents/auth-profiles/store.ts:1045, a73074ed45bf)
  • Regression coverage checks disk exclusion and runtime preservation: The new save test asserts the external profile stays absent from auth-profiles.json/auth-state.json while ensureAuthProfileStore and the runtime snapshot retain the external OAuth profile, order, lastGood, and usage state. (src/agents/auth-profiles.store.save.test.ts:563, a73074ed45bf)
  • Merge semantics have boundary coverage: Persisted-boundary tests cover authoritative runtime-external metadata removing stale base profiles and preserving inherited base runtime external profiles during agent-store merges. (src/agents/auth-profiles/persisted-boundary.test.ts:220, a73074ed45bf)
  • Maintainer verification is present in discussion: A maintainer comment reports focused local auth-profile tests, clean autoreview, and a passing remote changed gate on head 63bb721 before later test-only head refreshes. (63bb721c6535)
  • Auth-profile area history: The auth-profile path has recent and repeated history from Peter Steinberger and Vincent Koc around auth store, OAuth lifecycle, and performance/refactor work. (src/agents/auth-profiles/store.ts, ee51169b2063)

Likely related people:

  • steipete: Git history shows repeated auth-profile/OAuth store work, including the current main auth cache hotpath refactor that owns the present store.ts baseline. (role: recent area contributor; confidence: high; commits: ee51169b2063, a8a49d142f4a, 9afcbbec5e60; files: src/agents/auth-profiles/store.ts, src/agents/auth-profiles/persisted.ts, src/agents/auth-profiles/oauth-shared.ts)
  • vincentkoc: Git history shows auth lifecycle/auth-profile performance work, and the PR discussion includes maintainer verification of the focused tests, autoreview, and Testbox changed gate. (role: recent auth lifecycle contributor and verifier; confidence: medium; commits: 5f2e77a6e1c4, 3ed0995fa9f0, bde246e7aff8; files: src/agents/auth-profiles/store.ts, src/agents/auth-profiles/persisted.ts, src/agents/auth-profiles/external-auth.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 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. P1 High-priority user-facing bug, regression, or broken workflow. labels May 23, 2026
@clawsweeper

clawsweeper Bot commented May 23, 2026

Copy link
Copy Markdown
Contributor

ClawSweeper PR egg

✨ Hatched: 🥚 common Pearl Signal Puff

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: finds missing screenshots.
Image traits: location workflow harbor; accessory commit compass; palette moonlit blue and soft silver; mood sleepy but ready; pose nestled inside a glowing shell; shell brushed metal shell; lighting calm overcast light; background delicate sparkle particles.
Share on X: post this hatch
Copy: My PR egg hatched a 🥚 common Pearl Signal Puff 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.

@vincentkoc vincentkoc self-assigned this May 23, 2026
@TurboTheTurtle TurboTheTurtle force-pushed the fix/auth-snapshot-external-profiles-85521 branch from 5c2ddbe to 44cb41e Compare May 23, 2026 01:35
@openclaw-barnacle openclaw-barnacle Bot removed the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 23, 2026
@clawsweeper clawsweeper Bot added 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. merge-risk: 🚨 session-state 🚨 May lose, corrupt, stale, or mis-associate session, agent, or context state. merge-risk: 🚨 auth-provider 🚨 May break OAuth, tokens, provider routing, model choice, or credentials. 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 23, 2026
@TurboTheTurtle TurboTheTurtle force-pushed the fix/auth-snapshot-external-profiles-85521 branch from 44cb41e to bed8a58 Compare May 23, 2026 05:34
@TurboTheTurtle

Copy link
Copy Markdown
Contributor Author

@clawsweeper re-review

Addressed the P1 disk-only save gap:

  • saveAuthProfileStore now carries forward runtime-only external OAuth profiles from the active runtime snapshot when a disk-only/local-update save input omits them, without persisting those profiles to disk.
  • Added regression coverage for an active anthropic:claude-cli runtime snapshot plus a save input that only contains a local disk profile.

Proof run after the fix:

  • ./node_modules/.bin/oxfmt --write --threads=1 src/agents/auth-profiles/store.ts src/agents/auth-profiles.store.save.test.ts
  • node scripts/run-vitest.mjs src/agents/auth-profiles.store.save.test.ts src/agents/auth-profiles.ensureauthprofilestore.test.ts src/agents/model-provider-auth.test.ts
    • Test Files: 6 passed (6)
    • Tests: 94 passed (94)

Post-push checks:

  • git log --format='%h %an <%ae> %s' upstream/main..HEAD shows Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com> for the PR commit.\n- Raw Pulls API reports maintainer_can_modify: true.\n\nIf this PR is squashed or reworked, please preserve author attribution or include:\nCo-authored-by: Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com>

@clawsweeper

clawsweeper Bot commented May 23, 2026

Copy link
Copy Markdown
Contributor

🦞🧹
ClawSweeper re-review requested.

I asked ClawSweeper to review this item again.
Action: item re-review queued (workflow sweep.yml, event repository_dispatch).
Result: the existing ClawSweeper review comment will be edited in place when the review finishes.

Re-review progress:

@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: 🧂 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 23, 2026
@vincentkoc vincentkoc force-pushed the fix/auth-snapshot-external-profiles-85521 branch from 5574597 to 63bb721 Compare May 25, 2026 21:20
@vincentkoc

Copy link
Copy Markdown
Member

Maintainer verification for 63bb721c65355e8bcb826a5d8d7e9e65d4d747b5:

  • Local focused tests: node scripts/run-vitest.mjs src/agents/auth-profiles.store.save.test.ts src/agents/auth-profiles/persisted-boundary.test.ts src/agents/auth-profiles/oauth-shared.test.ts -- --reporter=dot -> 6 files / 50 tests passed.
  • Review: .agents/skills/autoreview/scripts/autoreview --mode branch --base origin/main clean before the final lint-only toSorted() fix; final .agents/skills/autoreview/scripts/autoreview --mode local clean after that lint fix.
  • Remote changed gate: node scripts/crabbox-wrapper.mjs run --provider blacksmith-testbox --blacksmith-org openclaw --blacksmith-workflow .github/workflows/ci-check-testbox.yml --blacksmith-job check --blacksmith-ref main --idle-timeout 90m --ttl 240m --timing-json -- CI=1 NODE_OPTIONS=--max-old-space-size=4096 OPENCLAW_TEST_PROJECTS_PARALLEL=6 OPENCLAW_VITEST_MAX_WORKERS=1 OPENCLAW_VITEST_NO_OUTPUT_TIMEOUT_MS=900000 OPENCLAW_TESTBOX=1 OPENCLAW_TESTBOX_REMOTE_RUN=1 pnpm check:changed
  • Live PR checks: relevant checks are pass or skipped for this head.

Scope notes:

  • Rebased on origin/main 5dccba7405c4ba553c68631c996b98e6a3c0b068.
  • Earlier Testbox run on the stale base failed unrelated core-test type errors; rebasing to current main cleared those. A second run then caught the .sort() lint issue in this patch; fixed with toSorted() before the passing run.

Ready for final maintainer review.

@clawsweeper clawsweeper Bot added the proof: sufficient ClawSweeper judged the real behavior proof convincing. label May 25, 2026
@Takhoffman

Copy link
Copy Markdown
Contributor

@clawsweeper ask

Create a maintainer-facing ASCII state visual for this PR.

Do not generate images. Do not use Mermaid.

Show the auth/runtime state change caused by this PR:

  • before: saveAuthProfileStore builds a disk-filtered local store and writes that same filtered store back into the active runtime snapshot, dropping runtime-only external CLI OAuth profiles like anthropic:claude-cli
  • after: disk persistence still uses the filtered local store, but the active runtime snapshot is refreshed with a runtime-safe store that preserves runtime-only external OAuth profiles
  • disk files must not persist runtime-only external CLI OAuth
  • runtime snapshots must keep those profiles available for embedded-agent credential resolution

Include:

  1. Before state picture
  2. After state picture
  3. Runtime vs disk boundary map
  4. Tradeoffs before merge
  5. Proof already shown
  6. Remaining proof gap
  7. Final maintainer ruling question

End with:
Benefit:
Risk:
Proof needed:
Recommended next action:
Question presented:

@clawsweeper

clawsweeper Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor

🦞👀
ClawSweeper assist is taking a look at your question.

I queued a lightweight read-only assist pass. It will post a separate answer comment and will not edit the durable ClawSweeper review comment or trigger close, merge, repair, label, or branch changes.

Request: Create a maintainer-facing ASCII state visual for this PR. Do not generate images. Do not use Mermaid. Show the auth/runtime state change caused by this PR: - before: saveAuthProfileStore builds a disk-filtered local store and writes that same filtered store back into the active runtime snapshot, dropping runtime-only external CLI OAuth profiles like anthropic:claude-cli - after: disk persistence still uses the filtered local store, but the active runtime snapshot is refreshed with a runtime-saf...

@clawsweeper

clawsweeper Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor

ClawSweeper assist: Here is a maintainer-facing ASCII state visual for #85558.

1. Before state picture

saveAuthProfileStore(input store)
        |
        v
buildLocalAuthProfileStoreForSave(...)
        |
        |  filters runtime-only external CLI OAuth
        |  removes: anthropic:claude-cli
        v
disk-filtered localStore
        |
        +--> auth-profiles.json / auth-state.json
        |    OK: no runtime-only external OAuth persisted
        |
        +--> active runtime snapshot
             BUG: same filtered store is installed
             result: anthropic:claude-cli disappears from memory

2. After state picture

saveAuthProfileStore(input store)
        |
        +--> disk persistence path
        |       build filtered localStore
        |       write auth-profiles.json / auth-state.json
        |       OK: runtime-only external CLI OAuth stays off disk
        |
        +--> runtime snapshot path
                build runtime-safe store
                preserve/re-overlay runtime-only external OAuth
                refresh active snapshot
                OK: anthropic:claude-cli remains available in memory

3. Runtime vs disk boundary map

                 DISK BOUNDARY
        --------------------------------
        auth-profiles.json / auth-state.json
        - local persisted profiles: yes
        - runtime-only external CLI OAuth: no
        - anthropic:claude-cli token material: no

                 RUNTIME BOUNDARY
        --------------------------------
        active auth-profile snapshot
        - local persisted profiles: yes
        - runtime-only external CLI OAuth: yes
        - anthropic:claude-cli usable by embedded agents: yes

4. Tradeoffs before merge

Benefit:
  Fixes the session-state/auth-provider bug where saveAuthProfileStore
  silently dropped external CLI OAuth from active runtime state.

Risk:
  Auth/profile merge behavior is sensitive: this PR touches runtime snapshot
  preservation, external OAuth overlay provenance, persisted boundary handling,
  and merge semantics.

Boundary requirement:
  Disk must stay filtered.
  Runtime must stay credential-complete for embedded-agent resolution.

5. Proof already shown

  • PR head: 63bb721c65355e8bcb826a5d8d7e9e65d4d747b5.
  • Author proof command passed: node scripts/run-vitest.mjs src/agents/auth-profiles.store.save.test.ts src/agents/auth-profiles.ensureauthprofilestore.test.ts src/agents/model-provider-auth.test.ts.
  • Later author proof showed 6 passed (6) files and 94 passed (94) tests.
  • Maintainer verification on 63bb721c65355e8bcb826a5d8d7e9e65d4d747b5: focused tests passed 6 files / 50 tests.
  • Remote changed gate passed: blacksmith-testbox / tbx_01ksgg6ath2c5bwbqnnjyg65ya, Actions run https://github.com/openclaw/openclaw/actions/runs/26420238850, exit 0.
  • Behavior proof showed persistedHasExternalProfile: false, persistedStateHasExternalOrder: false, runtimeHasExternalProfile: true, and runtimeLastGoodExternal: "anthropic:claude-cli".

6. Remaining proof gap

  • No live Anthropic Claude CLI process was launched.
  • No live OAuth refresh against Anthropic was performed.
  • The proof exercises OpenClaw auth-store behavior directly with fake token material.

7. Final maintainer ruling question

Does the maintainer accept the runtime/disk contract as implemented here:
disk persistence remains filtered, while active runtime snapshots preserve
runtime-only external CLI OAuth profiles for embedded-agent credential
resolution?

Benefit: Preserves anthropic:claude-cli and similar runtime-only external OAuth profiles after saveAuthProfileStore without persisting them to disk.
Risk: Auth-provider/session-state code changed across runtime snapshots, overlay metadata, and persisted merge behavior.
Proof needed: Optional live gateway or real Claude CLI OAuth smoke remains the main uncovered proof gap.
Recommended next action: Maintainer should decide whether the supplied focused tests plus remote changed gate are enough, or request a live external-CLI smoke before ruling.
Question presented: Should #85558 be accepted on the current proof, or held for a live external Claude CLI OAuth smoke?


Source: #85558 (comment)
Assist model: gpt-5.5, reasoning low.

@Takhoffman

Copy link
Copy Markdown
Contributor

@clawsweeper automerge

@clawsweeper

clawsweeper Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor

🦞🧹
ClawSweeper automerge is enabled.

  • Head: a73074ed45bf
  • Label: clawsweeper:automerge
  • Action: exact-head review queued (workflow sweep.yml, event repository_dispatch).
  • Flow: review this head, repair/rebase only if needed, then re-review the exact repaired head before merge.

Draft PRs stay fix-only until GitHub marks them ready for review. Pause with /clawsweeper stop.

Automerge progress:

  • 2026-05-26 04:23:23 UTC review passed 38dff32dbb28 (structured ClawSweeper verdict: pass (sha=38dff32dbb28b58d37192f7696182ba435905...)
  • 2026-05-26 04:35:10 UTC review queued a73074ed45bf (after repair)
  • 2026-05-26 04:41:50 UTC review passed a73074ed45bf (structured ClawSweeper verdict: pass (sha=a73074ed45bf4d7663c6cca4b7751c5f3ee65...)
  • 2026-05-26 04:42:02 UTC merged a73074ed45bf (merged by ClawSweeper automerge)
  • 2026-05-26 04:42:06 UTC review queued a73074ed45bf (queued)

@clawsweeper clawsweeper Bot added clawsweeper:automerge Maintainer opted this PR into bounded ClawSweeper-reviewed automerge rating: 🦞 diamond lobster Very strong PR readiness with only minor maintainer review expected. status: 🚀 automerge armed This PR is in ClawSweeper's automerge lane. 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 25, 2026
@clawsweeper clawsweeper Bot force-pushed the fix/auth-snapshot-external-profiles-85521 branch 2 times, most recently from a4523f5 to 1fe1f50 Compare May 26, 2026 00:15
@clawsweeper clawsweeper Bot added rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. and removed rating: 🦞 diamond lobster Very strong PR readiness with only minor maintainer review expected. labels May 26, 2026
@TurboTheTurtle TurboTheTurtle force-pushed the fix/auth-snapshot-external-profiles-85521 branch from 1fe1f50 to 38dff32 Compare May 26, 2026 04:16
@clawsweeper clawsweeper Bot added rating: 🦞 diamond lobster Very strong PR readiness with only minor maintainer review expected. and removed rating: 🧂 unranked krab Not merge-ready due to missing proof or serious correctness/safety concerns. labels May 26, 2026
@clawsweeper clawsweeper Bot force-pushed the fix/auth-snapshot-external-profiles-85521 branch from 38dff32 to a73074e Compare May 26, 2026 04:35
@clawsweeper clawsweeper Bot merged commit 711e963 into openclaw:main May 26, 2026
97 checks passed
@TurboTheTurtle TurboTheTurtle deleted the fix/auth-snapshot-external-profiles-85521 branch May 26, 2026 04:46
github-actions Bot pushed a commit to Desicool/openclaw that referenced this pull request May 26, 2026
Summary:
- The PR adds runtime-only external OAuth provenance to auth-profile stores, updates save/merge/read paths to  ... e profiles in active snapshots while filtering disk persistence, and expands auth-profile regression tests.
- PR surface: Source +381, Tests +974. Total +1355 across 8 files.
- Reproducibility: yes. from source: current main writes the disk-filtered localStore into an existing runtime ... tches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Automerge notes:
- PR branch already contained follow-up commit before automerge: Preserve runtime external auth snapshots

Validation:
- ClawSweeper review passed for head a73074e.
- Required merge gates passed before the squash merge.

Prepared head SHA: a73074e
Review: openclaw#85558 (comment)

Co-authored-by: Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com>
Co-authored-by: clawsweeper <274271284+clawsweeper[bot]@users.noreply.github.com>
Co-authored-by: clawsweeper[bot] <274271284+clawsweeper[bot]@users.noreply.github.com>
Approved-by: takhoffman
Co-authored-by: takhoffman <781889+takhoffman@users.noreply.github.com>
jameslcowan pushed a commit to jameslcowan/openclaw that referenced this pull request Jun 2, 2026
Summary:
- The PR adds runtime-only external OAuth provenance to auth-profile stores, updates save/merge/read paths to  ... e profiles in active snapshots while filtering disk persistence, and expands auth-profile regression tests.
- PR surface: Source +381, Tests +974. Total +1355 across 8 files.
- Reproducibility: yes. from source: current main writes the disk-filtered localStore into an existing runtime ... tches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Automerge notes:
- PR branch already contained follow-up commit before automerge: Preserve runtime external auth snapshots

Validation:
- ClawSweeper review passed for head a73074e.
- Required merge gates passed before the squash merge.

Prepared head SHA: a73074e
Review: openclaw#85558 (comment)

Co-authored-by: Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com>
Co-authored-by: clawsweeper <274271284+clawsweeper[bot]@users.noreply.github.com>
Co-authored-by: clawsweeper[bot] <274271284+clawsweeper[bot]@users.noreply.github.com>
Approved-by: takhoffman
Co-authored-by: takhoffman <781889+takhoffman@users.noreply.github.com>
SYU8384 pushed a commit to SYU8384/openclaw that referenced this pull request Jun 3, 2026
Summary:
- The PR adds runtime-only external OAuth provenance to auth-profile stores, updates save/merge/read paths to  ... e profiles in active snapshots while filtering disk persistence, and expands auth-profile regression tests.
- PR surface: Source +381, Tests +974. Total +1355 across 8 files.
- Reproducibility: yes. from source: current main writes the disk-filtered localStore into an existing runtime ... tches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Automerge notes:
- PR branch already contained follow-up commit before automerge: Preserve runtime external auth snapshots

Validation:
- ClawSweeper review passed for head a73074e.
- Required merge gates passed before the squash merge.

Prepared head SHA: a73074e
Review: openclaw#85558 (comment)

Co-authored-by: Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com>
Co-authored-by: clawsweeper <274271284+clawsweeper[bot]@users.noreply.github.com>
Co-authored-by: clawsweeper[bot] <274271284+clawsweeper[bot]@users.noreply.github.com>
Approved-by: takhoffman
Co-authored-by: takhoffman <781889+takhoffman@users.noreply.github.com>
sablehead pushed a commit to sablehead/openclaw that referenced this pull request Jun 10, 2026
Summary:
- The PR adds runtime-only external OAuth provenance to auth-profile stores, updates save/merge/read paths to  ... e profiles in active snapshots while filtering disk persistence, and expands auth-profile regression tests.
- PR surface: Source +381, Tests +974. Total +1355 across 8 files.
- Reproducibility: yes. from source: current main writes the disk-filtered localStore into an existing runtime ... tches the reported credential drop path. I did not run a failing current-main repro in this read-only pass.

Automerge notes:
- PR branch already contained follow-up commit before automerge: Preserve runtime external auth snapshots

Validation:
- ClawSweeper review passed for head a73074e.
- Required merge gates passed before the squash merge.

Prepared head SHA: a73074e
Review: openclaw#85558 (comment)

Co-authored-by: Andy Ye <35905412+TurboTheTurtle@users.noreply.github.com>
Co-authored-by: clawsweeper <274271284+clawsweeper[bot]@users.noreply.github.com>
Co-authored-by: clawsweeper[bot] <274271284+clawsweeper[bot]@users.noreply.github.com>
Approved-by: takhoffman
Co-authored-by: takhoffman <781889+takhoffman@users.noreply.github.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

agents Agent runtime and tooling clawsweeper:automerge Maintainer opted this PR into bounded ClawSweeper-reviewed automerge merge-risk: 🚨 auth-provider 🚨 May break OAuth, tokens, provider routing, model choice, or credentials. 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. proof: sufficient ClawSweeper judged the real behavior proof convincing. proof: supplied External PR includes structured after-fix real behavior proof. rating: 🦞 diamond lobster Very strong PR readiness with only minor maintainer review expected. size: XL status: 🚀 automerge armed This PR is in ClawSweeper's automerge lane.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[Bug]: saveAuthProfileStore overwrites runtime auth-profile snapshot with external-CLI-filtered view, dropping OAuth credentials from in-process state

3 participants