fix(mcp/oauth): coerce client_id_issued_at to number for Postgres - #381
Open
10x-smitty wants to merge 1 commit into
Open
fix(mcp/oauth): coerce client_id_issued_at to number for Postgres#38110x-smitty wants to merge 1 commit into
10x-smitty wants to merge 1 commit into
Conversation
ai_mcp_oauth_clients.client_id_issued_at is `bigint` in the Postgres
schema, and the driver returns int8 as a string to avoid precision loss.
OAuthClientRow typed the field as `number`, so rowToClient passed the raw
string straight through to the dynamic client registration response.
RFC 7591 requires client_id_issued_at to be a number, so strict clients
reject the payload. Claude Code fails to add the connector with:
SDK auth failed: expected number, received string
path: ["client_id_issued_at"]
SQLite declares the column as `integer` and returns a real number, so
this only affects Postgres deployments.
Matches the existing convention for bigint columns elsewhere in the
codebase, e.g. mediaAssetMapping.ts and ai/conversations/store.ts, which
type the row field as `number | string` and coerce in the mapper.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Problem
Adding the Instatic MCP connector to a client that validates the RFC 7591 registration response fails on Postgres deployments:
The registration endpoint returns the timestamp quoted:
{"client_id":"imcp_client_...","client_id_issued_at":"1786813381", ...}Cause
ai_mcp_oauth_clients.client_id_issued_atis declaredbigint(server/db/migrations-pg.ts:1085), and the driver returnsint8as a string to avoid precision loss.OAuthClientRowtyped the field asnumber, sorowToClientpassed the raw string through to the registration response unchanged.SQLite declares the same column as
integer(server/db/migrations-sqlite.ts:1149) and hands back a real number, so this is invisible in the default SQLite deployment — only Postgres installs are affected.Fix
Type the row field as
number | stringand coerce in the mapper. This matches the existing convention forbigintcolumns elsewhere in the codebase:server/repositories/mediaAssetMapping.ts:59,154—size_bytes: number | string→Number(row.size_bytes)server/ai/conversations/store.ts:41,82—prompt_tokens_total: number | string→toNumber(...)Testing
Added a case to
server/ai/mcp/oauth/store.test.ts. The existing harness is in-memory SQLite and therefore cannot reproduce a Postgres-only bug, so the test stubs aDbClientreturning a Postgres-shaped row and assertsfindOAuthClientreads it back as a number.Verified it fails without the fix:
and passes with it.
bun test server/ai/mcp/is green (79 pass, 0 fail), as aretsc -bandeslinton the changed files.Reproduced and verified against a Postgres deployment built from
compose.prod.yml+compose.build.yml.