Skip to content

CRE Gateway: Checks on json request id size to prevent abuse#21019

Merged
prashantkumar1982 merged 9 commits intodevelopfrom
vault_reqid_check
Feb 5, 2026
Merged

CRE Gateway: Checks on json request id size to prevent abuse#21019
prashantkumar1982 merged 9 commits intodevelopfrom
vault_reqid_check

Conversation

@prashantkumar1982
Copy link
Contributor

  • Put a fixed size limit on json request id in gateway, to prevent abuses.
  • Vault Get public key endpoint is unauthenticated, so made its fetching of cached entries efficient and cheap, to prevent potential dos.

@github-actions
Copy link
Contributor

github-actions bot commented Feb 3, 2026

I see you updated files related to core. Please run pnpm changeset in the root directory to add a changeset as well as in the text include at least one of the following tags:

  • #added For any new functionality added.
  • #breaking_change For any functionality that requires manual action for the node to boot.
  • #bugfix For bug fixes.
  • #changed For any change to the existing functionality.
  • #db_update For any feature that introduces updates to database schema.
  • #deprecation_notice For any upcoming deprecation functionality.
  • #internal For changesets that need to be excluded from the final changelog.
  • #nops For any feature that is NOP facing and needs to be in the official Release Notes for the release.
  • #removed For any functionality/config that is removed.
  • #updated For any functionality that is updated.
  • #wip For any change that is not ready yet and external communication about it should be held off till it is feature complete.

return errors.New("request ID cannot be empty")
}
if len(req.ID) > 200 {
// Arbitrary limit to prevent abuse
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

are requestIDs well formed? i'm surprised we can't lock in a known limit of the size of the request ID here

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Here's the spec: https://www.jsonrpc.org/specification
It just needs a unique id that could be a string.
So there's no fixed locked size.

I just think 200 is a safe enough buffer for anyone using any funky way for associating this id to their internal ids.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@prashantkumar1982 sure, but my understanding is the gateway isn't a domain agnostic rpc proxy. We use it for particular domains, and those domains should have our request patterns well mapped. What is that for the Vault DON? @MStreet3 do you know the max expected request.ID size for HTTP Triggers?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

For Vault, we don't have any restriction.
All we enforce, is that ids should be unique strings.

@trunk-io
Copy link

trunk-io bot commented Feb 4, 2026

Static BadgeStatic BadgeStatic BadgeStatic Badge

View Full Report ↗︎Docs

@prashantkumar1982 prashantkumar1982 marked this pull request as ready for review February 4, 2026 02:43
@prashantkumar1982 prashantkumar1982 requested review from a team as code owners February 4, 2026 02:43
Copilot AI review requested due to automatic review settings February 4, 2026 02:43
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Adds request ID length limits to mitigate abuse and refactors Vault public key handling to rely on cached responses for cheaper unauthenticated access.

Changes:

  • Enforce a max length (200 chars) on JSON-RPC request IDs in the gateway and Vault handler.
  • Refactor Vault PublicKeyGet to return a cached response directly (and adjust periodic cache refresh to use internal handler methods).
  • Add/adjust tests for the new request ID limit and the public key caching path.

Reviewed changes

Copilot reviewed 4 out of 4 changed files in this pull request and generated 3 comments.

File Description
core/services/gateway/handlers/vault/handler.go Adds request ID length validation; changes PublicKeyGet to serve cached responses directly; updates periodic cache refresh helper to return errors.
core/services/gateway/handlers/vault/handler_test.go Updates public key test flow to seed cache via internal methods before asserting cached behavior.
core/services/gateway/gateway.go Adds request ID length validation at the gateway layer.
core/services/gateway/gateway_test.go Adds coverage for gateway rejection of overly long request IDs.
Comments suppressed due to low confidence (2)

core/services/gateway/handlers/vault/handler_test.go:764

  • This test seeds the public key cache by calling private methods directly, but it no longer covers the cold-cache behavior for a user request (HandleJSONRPCUserMessage with MethodPublicKeyGet). Given the handler change, it would be valuable to add an assertion that the first user request still succeeds (or returns a well-defined error) when the cache is empty.
		"d6da96fe596705b32bc3a0e11cdefad77feaad79000000000000000000000000",
		"327aa349c9718cd36c877d1e90458fe1929768ad000000000000000000000000",
		"e9bf394856d73402b30e160d0e05c847796f0e29000000000000000000000000",
		"efd5bdb6c3256f04489a6ca32654d547297f48b9000000000000000000000000",

core/services/gateway/handlers/vault/handler_test.go:795

  • Grammar in this comment is a bit unclear ("make HandleJSONRPCUserMessage request"). Consider rephrasing to something like "make another request via HandleJSONRPCUserMessage" for readability.
		ID:     "request_id",

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

case <-tickerVaultPublicKeyRefresh.Chan():
// periodically, fetch vault public key, so we can cache it
h.fetchVaultPublicKey(ctx)
_ = h.fetchVaultPublicKey(ctx)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Nit: maybe handle the error here and log it? I see we do a lot of logging of errors inside fetchVaultPublicKey so we can move that out maybe?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I had changed signature of this to call it from tests. But later didn't use it. Reverting it back to old logging.

@prashantkumar1982 prashantkumar1982 changed the title Checks on json request id size CRE Gateway: Checks on json request id size to prevent abuse Feb 4, 2026
Copy link
Contributor

Copilot AI left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 4 out of 4 changed files in this pull request and generated 4 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +305 to +308
if len(jsonRequest.ID) > 200 {
// Arbitrary limit to prevent abuse
return newError(jsonRequest.ID, api.UserMessageParseError, "request ID is too long: "+strconv.Itoa(len(jsonRequest.ID))+". max is 200 characters")
}
Copy link

Copilot AI Feb 4, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The magic number 200 for maximum request ID length is duplicated across multiple files (gateway.go and vault/handler.go). Consider defining a constant like MaxRequestIDLength to ensure consistency and make future changes easier to maintain. This constant could be defined in a shared package like core/services/gateway/api/constants.go.

Copilot uses AI. Check for mistakes.
Comment on lines +338 to +341
if len(req.ID) > 200 {
// Arbitrary limit to prevent abuse
return errors.New("request ID is too long: " + strconv.Itoa(len(req.ID)) + ". max is 200 characters")
}
Copy link

Copilot AI Feb 4, 2026

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The request ID length validation logic is duplicated between gateway.go and vault/handler.go. This creates a maintenance burden and risk of inconsistency if the limit needs to be changed. Consider extracting this validation into a shared function or performing it only at the gateway layer to follow the DRY principle.

Suggested change
if len(req.ID) > 200 {
// Arbitrary limit to prevent abuse
return errors.New("request ID is too long: " + strconv.Itoa(len(req.ID)) + ". max is 200 characters")
}

Copilot uses AI. Check for mistakes.
@cl-sonarqube-production
Copy link

Copy link
Contributor

@patrickhuie19 patrickhuie19 left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

approved. please circle back to my comment on request.id size @prashantkumar1982

@prashantkumar1982 prashantkumar1982 added this pull request to the merge queue Feb 5, 2026
Merged via the queue into develop with commit 84001b2 Feb 5, 2026
223 checks passed
@prashantkumar1982 prashantkumar1982 deleted the vault_reqid_check branch February 5, 2026 10:19
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

3 participants