-
Notifications
You must be signed in to change notification settings - Fork 1
NAS-142189 / 27.0.0-BETA.1 / Accept a Claude Code OAuth token as the auth secret #9
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -40,6 +40,9 @@ | |
| # pull-requests: write | ||
| # secrets: | ||
| # anthropic-api-key: ${{ secrets.CLAUDE_API_KEY }} | ||
| # # or, on subscription auth instead of API billing — set exactly one | ||
| # # of the two; mapping both fails the job: | ||
|
Check notice on line 44 in .github/workflows/claude-review.yml
|
||
| # # claude-code-oauth-token: ${{ secrets.CLAUDE_CODE_OAUTH_TOKEN }} | ||
| # | ||
| # The job fails on a blocking finding. Whether that stops a merge is branch | ||
| # protection's decision, made per repo, and reversible without touching this. | ||
|
|
@@ -88,8 +91,17 @@ | |
| default: 'master' | ||
| secrets: | ||
| anthropic-api-key: | ||
| description: 'Anthropic API key. Mapped by the caller, since the secret name differs per repo.' | ||
| required: true | ||
| description: >- | ||
| Anthropic API key. Set exactly one of this and | ||
| claude-code-oauth-token; a step fails the job when both are missing, | ||
| and also when both are set. Mapped by the caller, since the secret | ||
| name differs per repo. | ||
| required: false | ||
| claude-code-oauth-token: | ||
| description: >- | ||
| Claude Code OAuth token (from `claude setup-token`) — the | ||
| subscription alternative to an API key. Same exactly-one rule. | ||
| required: false | ||
|
|
||
| # One review per PR. Rapid pushes previously started overlapping reviews that | ||
| # raced to overwrite the same sticky comment, and paid for every superseded run. | ||
|
|
@@ -178,6 +190,25 @@ | |
| echo "required status check, which would report an unreviewed PR as reviewed." | ||
| exit 1 | ||
|
|
||
| # Fail before spending a runner minute on a checkout: with neither | ||
| # secret the review step errors anyway, only later and less clearly. | ||
| # Both is also an error — which credential would win is the CLI's | ||
| # undocumented pick, and the two bill different accounts. | ||
| - name: Check exactly one auth secret is present | ||
| env: | ||
| API_KEY: ${{ secrets.anthropic-api-key }} | ||
| OAUTH_TOKEN: ${{ secrets.claude-code-oauth-token }} | ||
| run: | | ||
| if [ -z "$API_KEY" ] && [ -z "$OAUTH_TOKEN" ]; then | ||
| echo "::error::pass anthropic-api-key or claude-code-oauth-token; neither is set." | ||
| exit 1 | ||
| fi | ||
| if [ -n "$API_KEY" ] && [ -n "$OAUTH_TOKEN" ]; then | ||
| echo "::error::pass only one of anthropic-api-key and claude-code-oauth-token; both are set." | ||
| echo "They bill different accounts, so which one wins would be undocumented." | ||
| exit 1 | ||
| fi | ||
|
Check notice on line 210 in .github/workflows/claude-review.yml
|
||
|
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. LOW — This guard fails before the checkout, and the two The job still fails closed, so this is legibility only. It is also not new — |
||
|
|
||
| - name: Checkout repository | ||
| uses: actions/checkout@v4 | ||
| with: | ||
|
|
@@ -272,7 +303,10 @@ | |
| id: review | ||
| uses: anthropics/claude-code-action@v1.0.187 | ||
| with: | ||
| # Both pass through as env vars; the action treats an empty one as | ||
| # absent. The guard step above enforces exactly one is set. | ||
| anthropic_api_key: ${{ secrets.anthropic-api-key }} | ||
| claude_code_oauth_token: ${{ secrets.claude-code-oauth-token }} | ||
| # Passed so the action uses this token directly instead of exchanging | ||
| # its OIDC token for an Anthropic GitHub App token. `setupGitHubToken` | ||
| # returns early on it, and the exchange is the *only* thing that runs | ||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LOW — "mapping both fails the job" describes a mapping-based rule; the guard is value-based. It compares
$API_KEYand$OAUTH_TOKEN, and GitHub gives a mapped-but-nonexistent secret the same empty string as an unmapped one, so mapping both lines passes whenever only one of the two repo secrets actually exists. The secret descriptions below get this right ("when both are set"); these two snippets — here andREADME.md:183— do not.The gap it hides is the one this repo's own guidelines put first. A caller mapping
claude-code-oauth-token: ${{ secrets.CLAUDE_CODE_OATH_TOKEN }}— one transposed letter — resolves empty, the guard sees a single credential and passes, and the review runs on API billing while the caller believes it is on their subscription. Nothing says so. That is not fixable from here (Actions cannot distinguish "unmapped" from "mapped to nothing"), so the useful move is wording that does not promise a check the guard cannot make: "setting both fails the job" rather than "mapping both".Not a repeat of the earlier thread on this line — that one was about the snippet shipping both mappings as live YAML, which this push fixed.