fix(oauth): remove base64 obfuscation from public OAuth client IDs#96537
Conversation
|
Codex review: needs maintainer review before merge. Reviewed June 25, 2026, 2:47 PM ET / 18:47 UTC. Summary PR surface: Source -2. Total -2 across 2 files. Reproducibility: yes. Current main source shows the atob-based CLIENT_ID derivation in both OAuth helpers, and a focused decode check proves the proposed literals match the existing Base64 payloads exactly. Review metrics: 1 noteworthy metric.
Root-cause cluster Members:
Proposal only: this assessment does not dispatch repair, suppress jobs, mutate sibling items, close, or merge anything. Merge readiness Overall follows the weaker of proof and patch quality, so missing proof can cap an otherwise strong patch. Rank-up moves:
Risk before merge
Maintainer options:
Next step before merge
Security Review detailsBest possible solution: Merge the scoped constant cleanup after maintainers accept the exact-value and build-artifact proof, leaving OAuth request construction and config surfaces unchanged. Do we have a high-confidence way to reproduce the issue? Yes. Current main source shows the atob-based CLIENT_ID derivation in both OAuth helpers, and a focused decode check proves the proposed literals match the existing Base64 payloads exactly. Is this the best way to solve the issue? Yes. Replacing only the two constant initializers is the narrowest maintainable fix because the OAuth request call sites, provider ids, config, token handling, and refresh flows remain unchanged. AGENTS.md: found and applied where relevant. Codex review notes: model internal, reasoning high; reviewed against 66e2fcc6f83e. Label changesLabel justifications:
Evidence reviewedPR surface: Source -2. Total -2 across 2 files. View PR surface stats
What I checked:
Likely related people:
What the crustacean ranks mean
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
|
|
🦞🧹 I asked ClawSweeper to review this item again. |
|
@clawsweeper re-review |
|
@clawsweeper re-review |
|
@clawsweeper re-review |
2f312a8 to
e64267a
Compare
|
Maintainer proof for prepared head
This is a public OAuth client identifier, not a client secret; see RFC 6749 section 2.2. |
|
Merged via squash.
|
Closes #96490
What Problem This Solves
Fixes an issue where Anthropic and GitHub Copilot OAuth client IDs were stored as Base64-encoded strings via
atob(), creating a false impression that these public values are sensitive secrets. This security theatre misleads maintainers into treating them as credentials and adds unnecessary runtime indirection.Why This Change Was Made
OAuth client IDs are public identifiers per RFC 6749 — they are sent in cleartext to authorization endpoints on every OAuth flow. The
const decode = (s: string) => atob(s)wrapper provides zero security benefit while implying the values should be treated as confidential. This pattern was introduced unintentionally during a large-scale refactor (PR #85341) and was inconsistently applied: the siblingopenai-codex.tsfile already stores its client ID as a plain string literal in the same directory.The fix removes the
decodehelper and replaces both Base64 literals with their decoded plaintext equivalents, matching the convention used by the rest of the OAuth module.User Impact
No user-visible behavior change. Code is simpler, more transparent, and no longer misrepresents public OAuth identifiers as obfuscated values.
Evidence
All OAuth tests pass: 4 test files, 24 tests passed.
All four OAuth request paths (
anthropic.ts:306,anthropic.ts:259,github-copilot.ts:206,github-copilot.ts:300) inject the plaintextCLIENT_IDcorrectly — the only change frommainis removing theatobwrapper, the request construction code is untouched.The URL construction above uses the same code pattern as
src/llm/utils/oauth/anthropic.ts:304-316andgithub-copilot.ts:205-208— theCLIENT_IDis injected at runtime by the OpenClaw OAuth module. The built artifact confirms that both values exist as plaintext literals in the compiled output and noatobdecode path remains.Ported from issue #96490 with AI-assisted implementation.