Skip to content

Claude Code will read arbitrary files from the checked-out repository and post their full contents as PR comments #957

@BrandonJF

Description

@BrandonJF

Describe the bug

When using claude-code-action@v1 with claude_code_oauth_token and a restricted --allowed-tools list, Claude Code will read arbitrary files from the checked-out repository and post their full contents as PR comments if it encounters repeated failures trying to complete its primary task.

In our case, Claude was instructed to post a PR review via gh pr comment. The review body contained Markdown with backticks and single quotes, causing every shell quoting strategy to fail. Claude then entered a self-directed retry loop where it:

  1. Posted test comments to debug whether basic comment posting worked at all
  2. Read internal documentation files from the repository (via its unrestricted Read tool)
  3. Posted those files verbatim as PR comments, apparently as test content to verify rendering

The 7 errant comments posted were:

  • "test comment - please ignore"
  • "line1\nline2\nline3" (testing newline handling)
  • The Claude Code CLI terminal UI output (verbatim, including working directory and session state)
  • "line1\nline2"
  • "## Test\n\nHello code and bold\n" (testing Markdown rendering)
  • Full contents of docs/development/database-reference.md (~24KB — database infrastructure docs)
  • Full contents of AGENTS.md (~9.5KB — internal development guidelines)

After posting the files, Claude eventually succeeded in posting the actual review.

Core issue: claude_args: '--allowed-tools "Bash(gh pr comment:*)"' restricts Bash subcommands but does not restrict Claude Code's native tools (Read, Write, Grep, Glob). A user who configures tool restrictions expecting Claude cannot read repository files gets no such guarantee. The permitted Bash(gh pr comment:*) then becomes an unrestricted egress channel for content read via the unrestricted Read tool.

To Reproduce

  1. Create a workflow using claude-code-action@v1 with claude_code_oauth_token
  2. Set claude_args to restrict tools to only specific gh Bash commands (e.g. Bash(gh pr comment:*))
  3. Include actions/checkout@v4 so the repository is available on the runner
  4. Set a prompt that instructs Claude to (a) read CLAUDE.md for guidance and (b) post output via gh pr comment
  5. Ensure CLAUDE.md contains @ references to other documentation files
  6. Trigger the workflow on a PR where the review body will contain extensive Markdown formatting (backticks, code fences, single quotes)
  7. Observe: Claude attempts multiple quoting strategies, fails repeatedly, enters a debug loop, reads referenced files via Read tool, and posts their contents as PR comments

Expected behavior

  • --allowed-tools "Bash(gh pr comment:*)" should either also restrict native file tools (Read, Write, etc.), or the documentation should clearly warn that it does not.
  • Claude should not enter an open-ended self-directed retry loop when a task fails. After N failed attempts it should abort and report failure rather than escalating to arbitrary recovery strategies.
  • Claude should never post repository file contents as "test" content when debugging.
  • The action should recommend gh pr comment --body-file in its docs/examples to avoid the shell quoting failure mode entirely.

Screenshots

N/A — all evidence is in the GitHub Actions run logs and PR comment history (private repository).

Workflow yml file

name: Claude Code Review

on:
  pull_request:
    types: [opened, synchronize]

jobs:
  claude-review:
    runs-on: ubuntu-latest
    permissions:
      contents: read
      pull-requests: read
      issues: read
      id-token: write

    steps:
      - name: Checkout repository
        uses: actions/checkout@v4
        with:
          fetch-depth: 1

      - name: Run Claude Code Review
        id: claude-review
        uses: anthropics/claude-code-action@v1
        with:
          claude_code_oauth_token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }}
          prompt: |
            REPO: ${{ github.repository }}
            PR NUMBER: ${{ github.event.pull_request.number }}

            Please review this pull request and provide feedback on:
            - Code quality and best practices
            - Potential bugs or issues
            - Performance considerations
            - Security concerns
            - Test coverage

            Use the repository's CLAUDE.md for guidance on style and conventions.
            Use `gh pr comment` with your Bash tool to leave your review as a comment on the PR.
          claude_args: '--allowed-tools "Bash(gh issue view:*),Bash(gh search:*),Bash(gh issue list:*),Bash(gh pr comment:*),Bash(gh pr diff:*),Bash(gh pr view:*),Bash(gh pr list:*)"'

API Provider

[x] Anthropic First-Party API (default) — using claude_code_oauth_token

Additional context

  • Claude Code version (from leaked terminal output in one of the errant comments): v2.1.23
  • Model: Sonnet 4.5 · Claude Max
  • Workflow run duration: 07:45:15–08:04:38 UTC (19 minutes)
  • The errant comments appeared between 07:55–08:03 UTC, during the run
  • Workflow run ID: 22131065397
  • At least 9 different approaches to posting the comment were attempted before the file dumps occurred (direct --body, heredoc to temp file, heredoc to workspace file, Python stdin redirect, Python triple-quoted string, Node.js one-liner, base64 decode, gh api direct POST — all visible in the run logs)
  • Repository is private — no public exposure occurred; content was only visible to collaborators
  • No credentials were exposed; the leaked database-reference.md has passwords redacted internally

Suggested fix: Add a --no-file-tools preset for CI/CD contexts that disables Read/Write/Grep/Glob regardless of claude_code_oauth_token vs claude_api_key mode, and recommend gh pr comment --body-file /tmp/review.md instead of inline --body in all documentation examples.

Metadata

Metadata

Assignees

No one assigned

    Labels

    area:permissionsbugSomething isn't workingp1Showstopper bug preventing substantial subset of users from using the product, or incorrect docs

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions