fix: remove apiId from verifyKey request#3666
Conversation
|
The latest updates on your projects. Learn more about Vercel for Git ↗︎ 2 Skipped Deployments
|
|
📝 WalkthroughWalkthroughThis change removes the Changes
Sequence Diagram(s)sequenceDiagram
participant Client
participant APIHandler
participant KeyService
Client->>APIHandler: POST /v2/keys/verifyKey { key }
APIHandler->>KeyService: VerifyKey(key, options)
KeyService->>APIHandler: Permission check (before key lookup)
alt Permission denied
APIHandler-->>Client: 200 OK { code: NOTFOUND, valid: false }
else Permission granted
KeyService->>APIHandler: Lookup key
alt Key found and valid
APIHandler-->>Client: 200 OK { code: OK, valid: true }
else Key not found/invalid
APIHandler-->>Client: 200 OK { code: NOTFOUND, valid: false }
end
end
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~20 minutes Assessment against linked issues
Suggested labels
Suggested reviewers
Note ⚡️ Unit Test Generation is now available in beta!Learn more here, or try it out under "Finishing Touches" below. 📜 Recent review detailsConfiguration used: CodeRabbit UI 📒 Files selected for processing (4)
💤 Files with no reviewable changes (1)
🧰 Additional context used🧠 Learnings (4)📓 Common learningsgo/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyResponseData.yaml (4)Learnt from: chronark Learnt from: Flo4604 Learnt from: Flo4604 Learnt from: MichaelUnkey go/apps/api/openapi/openapi-generated.yaml (9)Learnt from: Flo4604 Learnt from: chronark Learnt from: Flo4604 Learnt from: chronark Learnt from: chronark Learnt from: CR Learnt from: CR Learnt from: Flo4604 Learnt from: chronark go/apps/api/routes/v2_keys_verify_key/200_test.go (7)Learnt from: MichaelUnkey Learnt from: chronark Learnt from: chronark Learnt from: Flo4604 Learnt from: MichaelUnkey Learnt from: chronark Learnt from: chronark 🧬 Code Graph Analysis (1)go/apps/api/routes/v2_keys_verify_key/200_test.go (5)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (6)
🔇 Additional comments (9)
✨ Finishing Touches
🧪 Generate unit tests
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. 🪧 TipsChatThere are 3 ways to chat with CodeRabbit:
SupportNeed help? Create a ticket on our support page for assistance with any issues or questions. Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments. CodeRabbit Commands (Invoked using PR comments)
Other keywords and placeholders
CodeRabbit Configuration File (
|
|
Thank you for following the naming conventions for pull request titles! 🙏 |
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyResponseBody.yaml
Show resolved
Hide resolved
Graphite Automations"Notify author when CI fails" took an action on this PR • (07/28/25)1 teammate was notified to this PR based on Andreas Thomas's automation. "Post a GIF when PR approved" took an action on this PR • (07/28/25)1 gif was posted to this PR based on Andreas Thomas's automation. |
There was a problem hiding this comment.
Actionable comments posted: 1
🔭 Outside diff range comments (1)
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyRequestBody.yaml (1)
4-16: Examples still include removedapiId→ schema + examples are now inconsistent
additionalProperties: falseforbids unknown fields, yet both example objects still containapiId, which was deleted from the schema. This causes OpenAPI validation failures and misleads clients reading the docs.@@ apiId: api_1234abcd key: sk_1234abcdef @@ apiId: api_1234abcd key: sk_1234abcdefRemove the two
apiIdlines (and adjust any accompanying description text) so the examples align with the new contract.
📜 Review details
Configuration used: CodeRabbit UI
Review profile: ASSERTIVE
Plan: Pro
📒 Files selected for processing (17)
go/apps/api/openapi/gen.go(2 hunks)go/apps/api/openapi/openapi-generated.yaml(4 hunks)go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyRequestBody.yaml(1 hunks)go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyResponseBody.yaml(1 hunks)go/apps/api/openapi/spec/paths/v2/keys/verifyKey/index.yaml(1 hunks)go/apps/api/routes/v2_keys_verify_key/200_test.go(14 hunks)go/apps/api/routes/v2_keys_verify_key/400_test.go(2 hunks)go/apps/api/routes/v2_keys_verify_key/401_test.go(1 hunks)go/apps/api/routes/v2_keys_verify_key/403_test.go(2 hunks)go/apps/api/routes/v2_keys_verify_key/404_test.go(2 hunks)go/apps/api/routes/v2_keys_verify_key/412_test.go(3 hunks)go/apps/api/routes/v2_keys_verify_key/handler.go(4 hunks)go/apps/api/routes/v2_keys_verify_key/multilimit_test.go(13 hunks)go/apps/api/routes/v2_keys_verify_key/ratelimit_response_test.go(3 hunks)go/internal/services/keys/options.go(0 hunks)go/internal/services/keys/status.go(1 hunks)go/internal/services/keys/verifier.go(0 hunks)
💤 Files with no reviewable changes (2)
- go/internal/services/keys/verifier.go
- go/internal/services/keys/options.go
🧰 Additional context used
🧠 Learnings (15)
📓 Common learnings
Learnt from: chronark
PR: unkeyed/unkey#3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via `\s`. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: unkeyed/unkey#2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In `apps/api/src/routes/v1_keys_updateKey.ts`, the code intentionally handles `externalId` and `ownerId` separately for clarity. The `ownerId` field will be removed in the future, simplifying the code.
Learnt from: MichaelUnkey
PR: unkeyed/unkey#2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the `v1/keys.updateKey` endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: Flo4604
PR: unkeyed/unkey#2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: Flo4604
PR: unkeyed/unkey#3421
File: go/apps/api/openapi/openapi.yaml:196-200
Timestamp: 2025-07-03T05:58:10.699Z
Learning: In the Unkey codebase, OpenAPI 3.1 is used, which allows sibling keys (such as `description`) alongside `$ref` in schema objects. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: unkeyed/unkey#3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
Learnt from: Flo4604
PR: unkeyed/unkey#3151
File: go/apps/api/openapi/gen.go:221-233
Timestamp: 2025-04-18T20:01:33.812Z
Learning: For identity deletion operations in the Unkey API, identityId takes precedence over externalId when both are provided in the request body.
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/index.yaml (3)
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
Learnt from: Flo4604
PR: #3421
File: go/apps/api/openapi/openapi.yaml:196-200
Timestamp: 2025-07-03T05:58:10.699Z
Learning: In the Unkey codebase, OpenAPI 3.1 is used, which allows sibling keys (such as description) alongside $ref in schema objects. Do not flag this as an error in future reviews.
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
go/apps/api/routes/v2_keys_verify_key/401_test.go (2)
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
go/apps/api/routes/v2_keys_verify_key/multilimit_test.go (6)
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: chronark
PR: #2126
File: apps/api/src/routes/v1_ratelimit_getOverride.happy.test.ts:36-36
Timestamp: 2024-11-13T19:06:36.786Z
Learning: In the rate limit test files (e.g., apps/api/src/routes/v1_ratelimit_getOverride.happy.test.ts), URL parameters like namespaceId and identifier do not need to be URL-encoded in the test code because the values used are always considered safe within the test environment.
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #3474
File: go/apps/api/routes/v2_keys_verify_key/200_test.go:380-380
Timestamp: 2025-07-14T08:15:56.747Z
Learning: In the Unkey codebase, there is a mechanism to set the server's time via a header for test control, which helps make ratelimit tests deterministic instead of time-dependent. This is useful for preventing flaky tests where the second request might hit a new ratelimit window.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
go/apps/api/routes/v2_keys_verify_key/412_test.go (4)
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
go/apps/api/routes/v2_keys_verify_key/404_test.go (2)
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
go/apps/api/routes/v2_keys_verify_key/ratelimit_response_test.go (5)
Learnt from: chronark
PR: #2126
File: apps/api/src/routes/v1_ratelimit_getOverride.happy.test.ts:36-36
Timestamp: 2024-11-13T19:06:36.786Z
Learning: In the rate limit test files (e.g., apps/api/src/routes/v1_ratelimit_getOverride.happy.test.ts), URL parameters like namespaceId and identifier do not need to be URL-encoded in the test code because the values used are always considered safe within the test environment.
Learnt from: chronark
PR: #3474
File: go/apps/api/routes/v2_keys_verify_key/200_test.go:380-380
Timestamp: 2025-07-14T08:15:56.747Z
Learning: In the Unkey codebase, there is a mechanism to set the server's time via a header for test control, which helps make ratelimit tests deterministic instead of time-dependent. This is useful for preventing flaky tests where the second request might hit a new ratelimit window.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
go/apps/api/routes/v2_keys_verify_key/400_test.go (5)
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
go/apps/api/routes/v2_keys_verify_key/200_test.go (6)
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: MichaelUnkey
PR: #3072
File: apps/dashboard/app/(app)/apis/[apiId]/settings/components/update-ip-whitelist.tsx:58-60
Timestamp: 2025-04-14T13:13:13.421Z
Learning: The IP address validation for the UpdateIpWhitelist component is handled in the TRPC route on the server side, not in the client-side component.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyRequestBody.yaml (7)
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: Flo4604
PR: #3151
File: go/apps/api/openapi/gen.go:221-233
Timestamp: 2025-04-18T20:01:33.812Z
Learning: For identity deletion operations in the Unkey API, identityId takes precedence over externalId when both are provided in the request body.
Learnt from: Flo4604
PR: #3421
File: go/apps/api/openapi/openapi.yaml:196-200
Timestamp: 2025-07-03T05:58:10.699Z
Learning: In the Unkey codebase, OpenAPI 3.1 is used, which allows sibling keys (such as description) alongside $ref in schema objects. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:468-581
Timestamp: 2025-07-15T14:47:20.490Z
Learning: In the Unkey codebase, role and permission names are validated at the OpenAPI schema layer with strict regex patterns: role names must match "^[a-zA-Z][a-zA-Z0-9_-]*$" (start with letter, followed by letters/numbers/underscores/hyphens) and permission names must match "^[a-zA-Z0-9_]+$" (letters, numbers, underscores only). This validation occurs during zen.BindBody call before handlers run, preventing malicious or improperly formatted names from reaching auto-creation logic.
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyResponseBody.yaml (2)
Learnt from: Flo4604
PR: #3421
File: go/apps/api/openapi/openapi.yaml:196-200
Timestamp: 2025-07-03T05:58:10.699Z
Learning: In the Unkey codebase, OpenAPI 3.1 is used, which allows sibling keys (such as description) alongside $ref in schema objects. Do not flag this as an error in future reviews.
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
go/apps/api/routes/v2_keys_verify_key/handler.go (1)
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
go/apps/api/routes/v2_keys_verify_key/403_test.go (1)
Learnt from: MichaelUnkey
PR: #2114
File: apps/api/src/routes/v1_keys_updateKey.error.test.ts:0-0
Timestamp: 2024-09-27T15:20:05.475Z
Learning: In the v1/keys.updateKey endpoint, the server validates the refill configuration before checking if the key exists. Therefore, tests can assert validation errors without needing to create the key first.
go/apps/api/openapi/openapi-generated.yaml (5)
Learnt from: Flo4604
PR: #3421
File: go/apps/api/openapi/openapi.yaml:196-200
Timestamp: 2025-07-03T05:58:10.699Z
Learning: In the Unkey codebase, OpenAPI 3.1 is used, which allows sibling keys (such as description) alongside $ref in schema objects. Do not flag this as an error in future reviews.
Learnt from: chronark
PR: #3617
File: go/apps/api/openapi/openapi.yaml:3309-3312
Timestamp: 2025-07-16T17:51:57.297Z
Learning: In the Unkey API OpenAPI schema, the permissions query regex for the verifyKey endpoint intentionally allows all whitespace characters (including tabs and newlines) via \s. Do not flag this as an error in future reviews.
Learnt from: Flo4604
PR: #2955
File: go/apps/api/routes/v2_identities_create_identity/handler.go:162-202
Timestamp: 2025-03-19T09:25:59.751Z
Learning: In the Unkey codebase, input validation for API endpoints is primarily handled through OpenAPI schema validation, which occurs before requests reach the handler code. For example, in the identities.createIdentity endpoint, minimum values for ratelimit duration and limit are defined in the OpenAPI schema rather than duplicating these checks in the handler.
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
Learnt from: chronark
PR: #3560
File: go/apps/api/routes/v2_keys_create_key/handler.go:353-466
Timestamp: 2025-07-15T14:25:05.608Z
Learning: In the Unkey codebase, input validation for API endpoints is handled at the OpenAPI schema layer, which validates request fields like permission slugs (pattern: "^[a-zA-Z0-9_]+$", length: 1-100 characters) before requests reach the handler code. This validation occurs during the zen.BindBody call in handlers.
go/apps/api/openapi/gen.go (1)
Learnt from: chronark
PR: #2693
File: apps/api/src/routes/v1_keys_updateKey.ts:350-368
Timestamp: 2024-11-29T15:15:47.308Z
Learning: In apps/api/src/routes/v1_keys_updateKey.ts, the code intentionally handles externalId and ownerId separately for clarity. The ownerId field will be removed in the future, simplifying the code.
🧬 Code Graph Analysis (1)
go/apps/api/openapi/gen.go (1)
go/pkg/codes/unkey_data.go (1)
Data(87-128)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (7)
- GitHub Check: Test Go API Local / Test
- GitHub Check: Test Agent Local / test_agent_local
- GitHub Check: Test API / API Test Local
- GitHub Check: Build / Build
- GitHub Check: Test Packages / Test
- GitHub Check: autofix
- GitHub Check: Analyze (javascript-typescript)
🔇 Additional comments (23)
go/apps/api/openapi/spec/paths/v2/keys/verifyKey/index.yaml (1)
22-23: Excellent documentation improvement for the security fix.This note clearly guides users on how to troubleshoot NOT_FOUND errors, which is especially important since the API now returns NOT_FOUND instead of other error codes to prevent key existence leakage. This aligns perfectly with the security objectives of PR #3666.
go/apps/api/routes/v2_keys_verify_key/404_test.go (1)
40-40: LGTM! Test updates correctly reflect API contract changes.The removal of
ApiIdfrom the request structures aligns with the broader refactor to remove apiId from the verifyKey endpoint. The test logic and assertions remain appropriate for the updated API schema.Also applies to: 57-57
go/apps/api/routes/v2_keys_verify_key/412_test.go (1)
59-59: LGTM! Consistent test updates across all precondition failed scenarios.The removal of
ApiIdfrom all request structures correctly reflects the updated API schema. The test coverage for ratelimit scenarios remains comprehensive and appropriate.Also applies to: 92-92, 115-115
go/apps/api/routes/v2_keys_verify_key/401_test.go (1)
35-35: LGTM! Test update aligns with API contract changes.The removal of
ApiIdfrom the request structure is consistent with the broader refactor. The unauthorized access test scenarios remain comprehensive and properly structured.go/apps/api/routes/v2_keys_verify_key/400_test.go (1)
59-59: LGTM! Comprehensive test updates maintain good coverage.The removal of
ApiIdfrom request structures and the elimination of the "missing apiId" test case correctly reflect the updated API contract. The remaining test cases provide excellent coverage for validation scenarios, including the detailed permissions query syntax testing.Also applies to: 83-83
go/apps/api/routes/v2_keys_verify_key/multilimit_test.go (1)
59-60: LGTM! Consistent removal of ApiId field from test requests.The removal of the
ApiIdfield from allhandler.Requeststruct initializations is correct and aligns with the PR objective to removeapiIdfrom the verifyKey request. The test coverage remains comprehensive while adapting to the simplified request structure.Also applies to: 94-95, 147-149, 196-198, 252-254, 266-268, 310-312, 325-327, 339-341, 370-371, 418-419, 433-434, 448-449
go/apps/api/routes/v2_keys_verify_key/200_test.go (1)
52-53: LGTM! Systematic removal of ApiId field from all test cases.The removal of the
ApiIdfield from allhandler.Requeststruct initializations is consistent and correct. The test scenarios maintain their comprehensive coverage while adapting to the simplified request structure that no longer requiresapiId. The change on line 214 to useipWhitelistApi.KeyAuthID.Stringis appropriate for the IP whitelist test scenario.Also applies to: 69-70, 94-95, 112-113, 131-132, 150-151, 172-173, 194-195, 217-218, 245-248, 269-272, 318-321, 371-373, 398-399, 430-434, 455-459, 498-502, 556-557
go/apps/api/routes/v2_keys_verify_key/ratelimit_response_test.go (1)
54-55: LGTM! Consistent ApiId field removal from rate limit tests.The removal of the
ApiIdfield from allhandler.Requeststruct initializations maintains consistency with the broader refactor. The rate limit response validation logic remains intact and comprehensive.Also applies to: 94-95, 124-125
go/internal/services/keys/status.go (1)
123-123: LGTM! Updated return type for versioned OpenAPI response codes.The update from
openapi.KeysVerifyKeyResponseDataCodetoopenapi.V2KeysVerifyKeyResponseDataCodecorrectly aligns with the migration to versioned response data types. The internal mapping logic remains unchanged, ensuring behavioral consistency while adapting to the new type system.go/apps/api/openapi/spec/paths/v2/keys/verifyKey/V2KeysVerifyKeyResponseBody.yaml (1)
9-9: LGTM! Updated schema reference for versioned response data.The update from
KeysVerifyKeyResponseData.yamltoV2KeysVerifyKeyResponseData.yamlcorrectly aligns the OpenAPI schema with the migration to versioned response data types. This ensures consistency between the API specification and the generated code.go/apps/api/openapi/openapi-generated.yaml (3)
1-5: Double-check committing generated artifacts
openapi-generated.yamlis produced bygenerate_bundle.go; committing it can cause noisy diffs and merge conflicts. Confirm that keeping the generated bundle under VCS is still the desired workflow for this repo.
1456-1460: Schema reference correctly updated to versioned typeThe response now points to
V2KeysVerifyKeyResponseData, matching the new versioned model. ✅
4963-4968: Description Formatting Verified – No ErrorsRan
npx @redocly/cli lint go/apps/api/openapi/openapi-generated.yaml; the file validates successfully (no errors, 15 non-blocking warnings). Thedescription:is correctly emitted as a single YAML scalar. No further changes required.go/apps/api/routes/v2_keys_verify_key/handler.go (4)
75-75: LGTM: Consistent response type migration to versioned API.The migration from
openapi.KeysVerifyKeyResponseDatatoopenapi.V2KeysVerifyKeyResponseDatais consistent across all response locations and follows proper API versioning conventions.Also applies to: 89-89, 116-116, 162-162
109-121: Excellent security improvement: Prevents key existence leakage.The change to return a 200 OK response with
NOTFOUNDcode instead of a direct error response effectively prevents attackers from distinguishing between "key doesn't exist" and "insufficient permissions" scenarios. This eliminates a potential information disclosure vulnerability.
123-123: LGTM: Correctly removes apiId from verification options.The removal of
keys.WithApiID(req.ApiId)from the verification options aligns with the PR objective to eliminate apiId from the verification process while preserving other relevant options.
96-107: Security model correctly preserved despite apiId removal.The permission verification logic correctly uses the key's actual API ID from the database (line 104) rather than relying on user-provided input. This maintains proper authorization while eliminating the attack vector for key existence probing.
go/apps/api/routes/v2_keys_verify_key/403_test.go (3)
36-42: LGTM: Test accurately reflects the new permission model.The test rename and restructuring correctly simulate a scenario where a root key has permissions for one API but attempts to verify a key from a different API. This provides better test coverage of the permission boundary enforcement.
44-46: LGTM: Request structure correctly updated.The removal of
ApiIdfrom the request structures aligns with the updated API contract and handler implementation.Also applies to: 62-64
54-54: LGTM: Test expectations correctly updated for security improvement.The change from expecting
FORBIDDENtoNOTFOUNDresponse codes correctly validates the new behavior that prevents key existence leakage by returning consistent responses for both non-existent keys and permission failures.Also applies to: 74-74
go/apps/api/openapi/gen.go (3)
31-42: LGTM! Well-defined response status codes.The V2KeysVerifyKeyResponseDataCode constants provide comprehensive coverage of all possible verification states. The naming is consistent and descriptive, making it clear what each status represents.
1478-1538: LGTM! Comprehensive response data structure with excellent documentation.The V2KeysVerifyKeyResponseData struct is well-designed with:
- Clear field documentation explaining the purpose and behavior of each field
- Proper use of pointer types for optional fields
- Comprehensive coverage of all verification scenarios
- Good balance between providing necessary information and avoiding key existence leakage
The structure effectively supports the PR's objective of preventing information leakage while maintaining a rich response format for legitimate verification scenarios.
1470-1476: LGTM! Proper response body structure using versioned types.The V2KeysVerifyKeyResponseBody correctly uses the new V2KeysVerifyKeyResponseData type, maintaining consistency with the versioned approach for this endpoint.
chronark
left a comment
There was a problem hiding this comment.
let's address the rabbit comment and merge

What does this PR do?
removes apiId from key verifciation and
Fixes #3538
Fixes #3611
If there is not an issue for this, please create one first. This is used to tracking purposes and also helps use understand why this PR exists
Type of change
How should this be tested?
Checklist
Required
pnpm buildpnpm fmtconsole.logsgit pull origin mainAppreciated
Summary by CodeRabbit
apiIdfield in key verification requests and updated related schemas and tests accordingly.apiIdfield and revised error codes.