Skip to content

fix: isolate sandboxed homes from macOS Keychain - #1138

Open
1jehuang wants to merge 1 commit into
masterfrom
fix/1132-sandbox-keychain
Open

fix: isolate sandboxed homes from macOS Keychain#1138
1jehuang wants to merge 1 commit into
masterfrom
fix/1132-sandbox-keychain

Conversation

@1jehuang

@1jehuang 1jehuang commented Sep 1, 2026

Copy link
Copy Markdown
Owner

Summary

  • detect when JCODE_HOME redirects away from the real ~/.jcode
  • skip ambient macOS Keychain discovery in sandboxed runs
  • continue honoring an explicitly supplied CLAUDE_CODE_OAUTH_TOKEN

Verification

  • sandbox detection and real-home control tests pass
  • explicit env-token precedence test passes
  • reported login_openai_phase_is_default_when_no_imports onboarding regression passes
  • jcode-storage, jcode-base, jcode-app-core, and jcode-tui check successfully

Fixes #1132

--- — Jcode agent (automated triage), on behalf of @1jehuang

@greptile-apps

greptile-apps Bot commented Sep 1, 2026

Copy link
Copy Markdown

Greptile Summary

This change detects redirected JCode homes and hides ambient Claude Keychain credentials from discovery while retaining explicitly configured OAuth tokens. The runtime and import loader still falls back to the macOS Keychain for a redirected home when no environment token is set, so the intended credential isolation is incomplete.

Confidence Score: 3/5

Not safe to merge until native credential loading applies the same sandbox boundary as credential discovery.

An executed instrumented harness confirmed that the redirected-home path still reaches and returns the Keychain credential when no explicit environment token is available.

Files Needing Attention: crates/jcode-base/src/auth/claude.rs needs the sandbox check on the Keychain fallback in load_native_credentials().

Security Review

A redirected JCode home can still read the machine-global Claude Keychain credential during native credential loading or import. This crosses the sandbox boundary that the change is intended to enforce.

T-Rex T-Rex Logs

What T-Rex did

  • T-Rex produced a proof for a posted P1 finding and linked it to the review comment.
  • T-Rex produced a second proof for a posted P1 finding.
  • T-Rex summarized a general-contract-validation-proof showing that sandbox isolation is bypassed in load_native_credentials, with the Before and After states described.

View all artifacts

T-Rex Ran code and verified through T-Rex

Comments Outside Diff (2)

  1. crates/jcode-base/src/auth/claude.rs, line 823 (link)

    P1 security Sandboxed home still loads Keychain credentials

    load_native_credentials() checks only for an explicit environment token before calling load_claude_code_keychain_credentials(). It does not check running_with_sandboxed_home(), so on macOS a process with redirected JCODE_HOME and no CLAUDE_CODE_OAUTH_TOKEN can still read the machine-global Claude Code-credentials item during runtime loading or approved import. Apply the sandbox check after the environment-token path and before this Keychain fallback.

    Artifacts

    Instrumented validation source

    • Python validation harness executed against the parent and PR source revisions; it extracts the actual Rust loader ordering and instruments the Keychain boundary, showing the sandboxed load fallback remains reachable.

    Before validation output

    • Captured execution of the harness against `HEAD^`; with a sandboxed home and absent env token, the call trace reaches the instrumented Keychain loader.

    After validation output

    • Captured execution of the harness against PR `HEAD`; it confirms the new detector guard exists but the same sandboxed load trace still reaches and returns the instrumented Keychain credential.

    View artifacts

    T-Rex Ran code and verified through T-Rex

    Prompt To Fix With AI
    This is a comment left during a code review.
    Path: crates/jcode-base/src/auth/claude.rs
    Line: 823
    
    Comment:
    **Sandboxed home still loads Keychain credentials**
    
    `load_native_credentials()` checks only for an explicit environment token before calling `load_claude_code_keychain_credentials()`. It does not check `running_with_sandboxed_home()`, so on macOS a process with redirected `JCODE_HOME` and no `CLAUDE_CODE_OAUTH_TOKEN` can still read the machine-global `Claude Code-credentials` item during runtime loading or approved import. Apply the sandbox check after the environment-token path and before this Keychain fallback.
    
    ---
    
    For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.
  2. General comment

    P1 Sandboxed home still loads macOS Keychain credentials

    • Bug
      • load_native_credentials() checks only for an environment credential before calling load_claude_code_keychain_credentials() at crates/jcode-base/src/auth/claude.rs:823. It never checks running_with_sandboxed_home(). Consequently, on macOS a process using a redirected/sandboxed JCODE_HOME, with no CLAUDE_CODE_OAUTH_TOKEN, can read the machine-global Claude Code-credentials Keychain entry during runtime loading or an approved import flow despite native_credentials_present() returning false.
    • Cause
      • The sandbox guard introduced by this PR is limited to the discovery function (native_credentials_present()), while the independently callable native credential load function retains its unconditional fallback to the Keychain loader.
    • Fix
      • Add running_with_sandboxed_home() handling after the env-token attempt and before line 823's Keychain fallback, returning the existing no-native-credentials error or otherwise preventing the Keychain fallback. Add a macOS-gated test asserting the Keychain loader is not called when JCODE_HOME is sandboxed.

    T-Rex Ran code and verified through T-Rex

Prompt To Fix All With AI
### Issue 1
crates/jcode-base/src/auth/claude.rs:823
**Sandboxed home still loads Keychain credentials**

`load_native_credentials()` checks only for an explicit environment token before calling `load_claude_code_keychain_credentials()`. It does not check `running_with_sandboxed_home()`, so on macOS a process with redirected `JCODE_HOME` and no `CLAUDE_CODE_OAUTH_TOKEN` can still read the machine-global `Claude Code-credentials` item during runtime loading or approved import. Apply the sandbox check after the environment-token path and before this Keychain fallback.

---

For each issue above, determine whether it is valid and should be fixed. If so, fix it directly.

Reviews (1): Last reviewed commit: "fix: isolate sandboxed homes from Keycha..." | Re-trigger Greptile

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

macOS: a sandboxed $JCODE_HOME still reads the real user's Keychain, changing onboarding and leaking real credential state into tests

1 participant