feat(auth): accept x-api-key header so Anthropic-native clients work (fixes #253)#315
feat(auth): accept x-api-key header so Anthropic-native clients work (fixes #253)#315AloysJehwin wants to merge 2 commits into
Conversation
Anthropic SDK clients send credentials as a bare x-api-key header with no Bearer prefix. Previously _extract_bearer_token only read Otari-Key, AnyLLM-Key/X-AnyLLM-Key aliases, and Authorization: Bearer <token>, so those requests got a 401 at the on-ramp. Changes: - Add X_API_KEY_HEADER = "x-api-key" constant in config.py - _extract_bearer_token falls back to x-api-key (raw, no Bearer prefix) after all existing header checks, before raising 401 — Authorization wins if both are present - CORS allow_headers includes x-api-key for browser clients - OpenAPI spec adds XApiKeyAuth security scheme alongside ApiKeyAuth - 4 new tests in test_extract_bearer_token.py covering raw token extraction, precedence over x-api-key, and no-Bearer-prefix path Closes mozilla-ai#253 Signed-off-by: Aloys Jehwin <aloysjehwin@gmail.com>
|
This PR appears to be missing required sections from the PR template. Please edit your PR description to include the PR Type, Checklist, and AI Usage sections. The template helps maintainers review your contribution. This PR will be automatically closed in 24 hours if the template is not restored. If you're using an AI coding tool, please ensure it preserves the PR template. |
|
No actionable comments were generated in the recent review. 🎉 ℹ️ Recent review info⚙️ Run configurationConfiguration used: Path: .coderabbit.yaml Review profile: CHILL Plan: Pro Run ID: 📒 Files selected for processing (1)
WalkthroughThe gateway adds Changesx-api-key authentication
Estimated code review effort: 2 (Simple) | ~10 minutes Possibly related issues
Possibly related PRs
Suggested reviewers: 🚥 Pre-merge checks | ✅ 3 | ❌ 2❌ Failed checks (2 warnings)
✅ Passed checks (3 passed)
✨ Finishing Touches🧪 Generate unit tests (beta)
✨ Simplify code
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
Avoids GitGuardian false-positive on sk-ant-api03- prefix pattern.
There was a problem hiding this comment.
🧹 Nitpick comments (1)
src/gateway/api/deps.py (1)
100-108: 📐 Maintainability & Code Quality | 🔵 Trivial | ⚡ Quick winUpdate the error message to include the new header.
Hi there! Great work adding the fallback for Anthropic clients. Just a small detail: since we now support the
x-api-keyheader, we should probably mention it in this 401 error message so that clients know it's a valid authentication option. As per coding guidelines, we should raise explicitHTTPExceptioninstances with clear detail messages.✨ Proposed tweak
raw_token = request.headers.get(X_API_KEY_HEADER) if raw_token: return raw_token record_auth_failure("missing_credentials") raise HTTPException( status_code=status.HTTP_401_UNAUTHORIZED, - detail=f"Missing {API_KEY_HEADER} or Authorization header", + detail=f"Missing {API_KEY_HEADER}, Authorization, or {X_API_KEY_HEADER} header", )🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the rest with a brief reason, keep changes minimal, and validate. In `@src/gateway/api/deps.py` around lines 100 - 108, Update the HTTPException detail in the authentication fallback around raw_token to mention X_API_KEY_HEADER alongside API_KEY_HEADER and Authorization, while preserving the existing 401 status and failure-recording behavior.Source: Coding guidelines
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.
Nitpick comments:
In `@src/gateway/api/deps.py`:
- Around line 100-108: Update the HTTPException detail in the authentication
fallback around raw_token to mention X_API_KEY_HEADER alongside API_KEY_HEADER
and Authorization, while preserving the existing 401 status and
failure-recording behavior.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: 532bdbca-8af1-4195-a4e4-45d9ad6d56dd
📒 Files selected for processing (4)
src/gateway/api/deps.pysrc/gateway/core/config.pysrc/gateway/main.pytests/unit/test_extract_bearer_token.py
Summary
Anthropic SDK clients configured with
ANTHROPIC_API_KEYsend credentials as a barex-api-keyheader (noBearerprefix). Against otari these requests got a 401 on every route, makingx-api-keythe only thing standing between an Anthropic-native client and a working setup.This PR adds
x-api-keyas a final fallback in_extract_bearer_token, after all existing header checks.Changes
config.py— addsX_API_KEY_HEADER = "x-api-key"constantdeps.py—_extract_bearer_tokenfalls back tox-api-key(raw token, noBearerprefix) before raising 401;Authorization: Bearerwins if both are presentmain.py—x-api-keyadded to CORSallow_headers;XApiKeyAuthOpenAPI security scheme added alongsideApiKeyAuthtests/unit/test_extract_bearer_token.py— 4 new cases: raw token extraction,Authorizationprecedence overx-api-key, canonicalOtari-Keyprecedence, no-Bearer-prefix succeedsPrecedence (unchanged headers win)
Otari-Key>AnyLLM-Key/X-AnyLLM-Key>Authorization: Bearer>x-api-keyDecisions from issue #253
Bearerpath; no prefix stripping neededAuthorizationwins overx-api-keyif both are presentChecklist
make lint) passesmake typecheck) passes — 219 files cleantests/unit/test_extract_bearer_token.py)AI Usage
Drafted with Claude Code assistance; logic and test cases reviewed manually.
Summary
x-api-keyheader (for Anthropic-native clients), including a new shared constant for the header name.x-api-keyused as the final fallback (afterOtari-Key,AnyLLM-Key/X-AnyLLM-Key, andAuthorization: Bearer).x-api-key.Bearer-prefixed) values, using obviously fake tokens to avoid false positives.