Project and local settings additively merge their permissions with whatever
allowed_tools a workflow specifies. A workflow author writing a restrictive
allowlist reasonably expects it to be the complete allow-set, but
.claude/settings.json can silently expand it.
Changes:
- Add setting_sources as a first-class input to both actions (previously
only reachable via --setting-sources in claude_args)
- base-action now defaults to settingSources: ['user'] — workflows that want
project/local settings must opt in explicitly
- Main action defaults to 'user,project,local' since .claude/ is restored
from the PR base branch before execution, so project settings are
maintainer-trusted in that context
- Precedence: setting_sources input > --setting-sources in claude_args > default
Breaking change for base-action: workflows relying on .claude/settings.json
being loaded automatically need to add setting_sources: 'user,project,local'.
🏠 Remote-Dev: homespace
shell-quote treats # as a shell comment character, swallowing all
subsequent content including flags on new lines. Strip comment lines
(lines starting with #) before passing input to shell-quote.
Fixes#802
Co-authored-by: VoidChecksum <Admin@CyberNord>
When id-token: write permission is enabled, ACTIONS_ID_TOKEN_REQUEST_URL
and ACTIONS_ID_TOKEN_REQUEST_TOKEN are passed to the Claude session via
the process.env spread in parseSdkOptions(). This allows Claude to mint
new OIDC tokens, which is an unintended capability.
This commit deletes these two variables from the env object before passing
it to the Claude SDK. The OIDC flow in token.ts reads directly from
process.env and runs before parseSdkOptions(), so it is unaffected.
Fixes#1010
Previously, the SDK path would result in the CLI setting the entrypoint
to 'sdk-ts' internally, while the non-SDK (CLI) path would correctly
set it to 'claude-code-github-action' based on the CLAUDE_CODE_ACTION
env var.
This change explicitly sets CLAUDE_CODE_ENTRYPOINT in both:
1. The action.yml env block (for consistency)
2. The SDK options env (to override the CLI's internal default)
The CLI respects pre-set entrypoint values, so this ensures consistent
user agent reporting for both execution paths.
🤖 Generated with [Claude Code](https://claude.ai/code)
Co-authored-by: Claude <noreply@anthropic.com>
When users specify --setting-sources in claude_args (e.g., '--setting-sources user'),
the action now respects that value instead of overriding it with all three sources.
This fixes an issue where users who wanted to avoid in-repo configs would still
have them loaded because the settingSources was hardcoded to ['user', 'project', 'local'].
Fixes#749
Co-authored-by: Ashwin Bhat <ashwin-ant@users.noreply.github.com>
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-authored-by: claude[bot] <41898282+claude[bot]@users.noreply.github.com>
* fix: merge multiple --mcp-config flags instead of overwriting
When users provide their own --mcp-config in claude_args, the action's
built-in MCP servers (github_comment, github_ci, etc.) were being lost
because multiple --mcp-config flags were overwriting each other.
This fix:
- Adds mcp-config to ACCUMULATING_FLAGS to collect all values
- Changes delimiter to null character to avoid conflicts with JSON
- Adds mergeMcpConfigs() to combine mcpServers objects from multiple configs
- Merges inline JSON configs while preserving file path configs
Fixes#745🤖 Generated with [Claude Code](https://claude.ai/code)
Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: Ashwin Bhat <ashwin-ant@users.noreply.github.com>
* fix: support hyphenated --allowed-tools flag and multiple values
The --allowed-tools flag was not being parsed correctly when:
1. Using the hyphenated form (--allowed-tools) instead of camelCase (--allowedTools)
2. Passing multiple space-separated values after a single flag
(e.g., --allowed-tools "Tool1" "Tool2" "Tool3")
This fix:
- Adds hyphenated variants (allowed-tools, disallowed-tools) to ACCUMULATING_FLAGS
- Updates parsing to consume all consecutive non-flag values for accumulating flags
- Merges values from both camelCase and hyphenated variants
Fixes#746🤖 Generated with [Claude Code](https://claude.ai/code)
Co-Authored-By: Claude <noreply@anthropic.com>
---------
Co-authored-by: claude[bot] <41898282+claude[bot]@users.noreply.github.com>
Co-authored-by: Claude <noreply@anthropic.com>
Co-authored-by: Ashwin Bhat <ashwin-ant@users.noreply.github.com>
Two fixes for the Agent SDK path (USE_AGENT_SDK=true):
1. Add settingSources to load filesystem settings
- Without this, CLI-installed plugins aren't available to the SDK
- Also needed to load CLAUDE.md files from the project
2. Default systemPrompt to claude_code preset
- Without an explicit systemPrompt, the SDK would use no system prompt
- Now defaults to { type: "preset", preset: "claude_code" } to match CLI behavior
Also adds logging of SDK options (excluding env) for debugging.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-authored-by: Claude <noreply@anthropic.com>
* fix: merge allowedTools from claudeArgs when using Agent SDK
When USE_AGENT_SDK=true, the allowedTools from claudeArgs (which contains
tag mode's required tools like mcp__github_comment__update_claude_comment)
were being lost because parseClaudeArgsToExtraArgs converts args to a
Record<string, string>, and the SDK was using sdkOptions.allowedTools
(from direct options) instead of merging with extraArgs.allowedTools.
This fix:
- Extracts allowedTools/disallowedTools from extraArgs after parsing
- Merges them with any direct options.allowedTools/disallowedTools
- Removes them from extraArgs to prevent duplicate CLI flags
- Passes the merged list as sdkOptions.allowedTools
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
* fix: accumulate multiple --allowedTools flags in claudeArgs
When tag mode adds its --allowedTools (with MCP tools) and the user also
provides --allowedTools in their claude_args, the parseClaudeArgsToExtraArgs
function was only keeping the last value. This caused tag mode's required
tools like mcp__github_comment__update_claude_comment to be lost.
Now allowedTools and disallowedTools flags accumulate their values when
they appear multiple times in claudeArgs, so both tag mode's tools and
user's tools are preserved.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
---------
Co-authored-by: Claude <noreply@anthropic.com>
* feat: add Agent SDK support with USE_AGENT_SDK feature flag
Add a feature-flagged code path that uses the Agent SDK instead of
spawning the CLI as a subprocess. When USE_AGENT_SDK=true is set,
the new SDK path is used; otherwise, existing CLI behavior is unchanged.
Changes:
- Add parse-sdk-options.ts for parsing ClaudeOptions into SDK format
- Add run-claude-sdk.ts for SDK execution with query() function
- Update run-claude.ts with feature flag check at entry point
- Update update-comment-link.ts to handle both cost_usd and total_cost_usd
- Add @anthropic-ai/claude-agent-sdk dependency
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
* refactor: simplify SDK types by using @anthropic-ai/claude-agent-sdk types directly
- Remove duplicate SdkRunOptions and McpStdioServerConfig types
- Use SDK's Options and McpStdioServerConfig types directly
- Return { sdkOptions, showFullOutput, hasJsonSchema } from parseSdkOptions
- Remove unnecessary convertMcpServers function
- Net reduction of ~70 lines
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
* refactor: use extraArgs for claudeArgs pass-through to CLI
Simplify option parsing by converting claudeArgs to extraArgs record
and letting the SDK/CLI handle --mcp-config, --json-schema, etc.
- Remove extractJsonSchema and parseMcpConfigs functions
- Add parseClaudeArgsToExtraArgs for simple flag parsing
- CLI handles complex args like --mcp-config directly
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
* ci
* refactor: remove hardcoded permission bypass flags
The SDK path should match CLI path behavior - permissions are handled
by the CLI itself, not hardcoded in the action.
🤖 Generated with [Claude Code](https://claude.com/claude-code)
Co-Authored-By: Claude <noreply@anthropic.com>
* chore: add logging for SDK vs CLI path selection
---------
Co-authored-by: Claude <noreply@anthropic.com>