claude-code - 💡(How to fix) Fix Sandbox crashes when auto-denied file paths traverse symlinks [1 participants]

Official PRs (…)
ON THIS PAGE

Recommended Tools

×6

Utilities matched from this issue’s tags and category — try them while you read without losing context.

GitHub issue graph ai analysis

Paste a GitHub issue URL. We fetch that issue, discover linked issues from bodies/comments/timeline, collect linked pull requests, and produce a structured English report.

The report is written in English Markdown for sharing and archival.

Helpful · Quick feedback

Loading…
GitHub stats
anthropics/claude-code#45451Fetched 2026-04-09 08:05:07
View on GitHub
Comments
0
Participants
1
Timeline
4
Reactions
0
Author
Participants
Timeline (top)
labeled ×4

Claude Code's sandbox (bwrap) becomes completely non-functional when auto-detected "secret" files exist behind a symlink. bwrap cannot mkdir -p through symlinks to set up deny bind mounts, so all sandboxed commands fail — not just those accessing denied paths.

Root Cause

Two issues compound:

Fix Action

Workaround

Use dangerouslyDisableSandbox: true for all commands. This defeats the purpose of sandboxing entirely.

Code Example

$ echo "hello"
bwrap: Can't mkdir parents for /home/lucas/matx/bazel-matx/ops/terraform/buildbarn-db/secrets.tf: No such file or directory
RAW_BUFFERClick to expand / collapse

Summary

Claude Code's sandbox (bwrap) becomes completely non-functional when auto-detected "secret" files exist behind a symlink. bwrap cannot mkdir -p through symlinks to set up deny bind mounts, so all sandboxed commands fail — not just those accessing denied paths.

Environment

  • Claude Code CLI on Linux (Debian 13, kernel 6.12.74)
  • Working directory: a Bazel monorepo at /home/lucas/matx
  • Bazel creates a convenience symlink: bazel-matx/home/lucas/.cache/bazel/_bazel_lucas/.../execroot/_main

Reproduction

  1. Have a Bazel project (or any project with a symlink in the workspace root)
  2. Behind the symlink, have any file with "secret" or "credential" in the name (e.g., secrets.tf, secrets.py, gcredentials.h)
  3. Run any sandboxed command — even echo "hello"
$ echo "hello"
bwrap: Can't mkdir parents for /home/lucas/matx/bazel-matx/ops/terraform/buildbarn-db/secrets.tf: No such file or directory

Root cause

Two issues compound:

1. Auto-deny heuristic adds paths through symlinks

The sandbox auto-detects files with "secret" or "credential" in the name and adds them to the filesystem deny list. It finds these files through the bazel-matx symlink and adds the symlink-relative path (e.g., /home/lucas/matx/bazel-matx/.../secrets.tf) rather than the resolved real path.

2. bwrap can't create deny bind mounts through symlinks

bwrap tries to mkdir -p the parent directories of each deny path to set up bind mounts. It cannot create directories through a symlink, so it fails. Since this happens during sandbox setup, every sandboxed command fails, not just commands that would touch the denied files.

Additional issue: over-broad auto-deny heuristic

The auto-deny heuristic matches any file with "secret" or "credential" in the name. In practice this catches many non-sensitive files:

  • secrets.py — Python's stdlib module for generating cryptographically strong random numbers
  • gcredentials.h / gunixcredentialsmessage.h — GLib/GIO system headers
  • BUILD.gix-credentials-0.27.0.bazel — Rust crate universe build file
  • secrets.tf — matched through a Bazel symlink to a cached copy, not the original

In this repo, the deny list had 70+ entries, almost all false positives from Python stdlib, system headers, and Bazel runfiles/output directories containing copies of secrets.py.

Workaround

Use dangerouslyDisableSandbox: true for all commands. This defeats the purpose of sandboxing entirely.

Suggested fixes

  1. Resolve symlinks before adding paths to the deny list, or skip paths that traverse symlinks.
  2. Scope the heuristic more narrowly — e.g., only match .env, .env.*, and files in well-known secret locations, rather than any filename containing "secret" or "credential" as a substring.
  3. Make auto-deny configurable — allow users to see and override the auto-generated deny list.

extent analysis

TL;DR

The most likely fix is to resolve symlinks before adding paths to the deny list or scope the heuristic more narrowly to avoid false positives.

Guidance

  • Identify and review the auto-deny heuristic to understand how it's currently implemented and how it can be modified to either resolve symlinks or narrow its scope.
  • Consider implementing a configuration option to allow users to override the auto-generated deny list to handle false positives.
  • Evaluate the impact of disabling sandboxing as a temporary workaround and assess the security implications.
  • Review the list of denied files to identify patterns or common locations that could help in scoping the heuristic more effectively.

Example

No specific code example can be provided without knowing the exact implementation of the auto-deny heuristic, but a potential approach could involve using a function to resolve symlinks before adding paths to the deny list:

import os

def resolve_symlink(path):
    return os.path.realpath(path)

# Before adding a path to the deny list, resolve any symlinks
resolved_path = resolve_symlink(path)

Notes

The provided guidance assumes that modifying the auto-deny heuristic is feasible and that the sandboxing mechanism can be adjusted without significant rearchitecture. The effectiveness of these suggestions may depend on the specific implementation details of the Claude Code CLI and its sandboxing feature.

Recommendation

Apply a workaround by scoping the heuristic more narrowly, as this approach balances security with the need to avoid false positives, allowing for more targeted denial of access to sensitive files without overly broad restrictions.

Vote matrix · Quick signals

Works
Did the solution work? Tap to confirm.
Easy Fix
Was it a quick fix?
Time Saver
Did it save you time?
Blocking
Was it severely blocking?
Common Issue
Are others likely hitting this too?
Flaky / Intermittent
Is it intermittent?
Verified / Reproducible
Can you reproduce it reliably?
Loading…

Still need to ship something?

×6

Another batch ranked right after the header list — different links, same matching logic.

Back to top recommendations

TRENDING