You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
{{ message }}
Repository navigation
Validate clientMetadataUrl at construction time rather than during auth flow (SEP-991/CIMD) #1159
The clientMetadataUrl property in OAuthClientProvider is currently only validated during the auth() flow (specifically in authInternal() at src/client/auth.ts:404-407). This means that an invalid URL-based client ID won't be caught until runtime when authentication is attempted.
The current validation:
if(clientMetadataUrl&&!isHttpsUrl(clientMetadataUrl)){thrownewInvalidClientMetadataError(`clientMetadataUrl must be a valid HTTPS URL with a non-root pathname, got: ${clientMetadataUrl}`);}
Suggested Improvement
Move the URL validation to occur earlier - ideally at construction time when the OAuthClientProvider is created. This provides:
Fail-fast behavior: Developers discover configuration errors immediately rather than at runtime
Better debugging: Errors are caught closer to the source of the problem
Clearer error messages: The stack trace points to where the provider was configured, not deep in the auth flow
Possible Approaches
Add validation in a factory function or builder that creates OAuthClientProvider implementations
Document that implementations should validate in their constructor
Provide a utility validation function that can be called at construction time
Related
SEP-991: URL-based Client IDs (CIMD)
isHttpsUrl() helper function already exists and can be reused
Added validateClientMetadataUrl() — a thin wrapper around the existing isHttpsUrl() helper that throws OAuthError(InvalidClientMetadata) for invalid URLs
Called at all SDK-controlled entry points: StreamableHTTPClientTransport constructor, SSEClientTransport constructor, auth() function, and withOAuth middleware factory
Exported as a public utility so consumers implementing OAuthClientProvider directly can call it in their own constructors
Existing validation in authInternal() is preserved as defense-in-depth
This covers approach (1) from the issue (validation at SDK entry points) and approach (3) (exported utility function). Since OAuthClientProvider is an interface, the SDK can't enforce constructor-time validation on external implementations, but the exported utility makes it trivial.
Hi @rechedev9 , thanks for your PR. It addresses (3), but I don't think it works well for (1). I'd want to catch it at OAuth provider construction time, so just the uitility function is sufficient, and calling it in example implementations.
If you can remove the various checks at all entry points, that PR would work otherwise.
@pcarleton Thanks for the feedback — you're right. I've reworked the PR to match what you described:
What changed:
KeptvalidateClientMetadataUrl() as an exported utility (approach 3)
Added the call in InMemoryOAuthClientProvider's constructor as a usage example (approach 1 done correctly — at provider construction time)
Removed all entry-point checks from StreamableHTTPClientTransport, SSEClientTransport, auth(), and withOAuth
Preserved the existing defense-in-depth validation in authInternal()
The PR is now much smaller (+113/−2 across 5 files vs the previous +318/−7 across 9). The branch has been rebased on main so the merge conflicts are resolved.
Activity
fix: validate clientMetadataUrl at construction time for fail-fast be…
rechedev9 commentedon Mar 9, 2026
I've submitted a fix for this in #1653.
What changed:
validateClientMetadataUrl()— a thin wrapper around the existingisHttpsUrl()helper that throwsOAuthError(InvalidClientMetadata)for invalid URLsStreamableHTTPClientTransportconstructor,SSEClientTransportconstructor,auth()function, andwithOAuthmiddleware factoryOAuthClientProviderdirectly can call it in their own constructorsauthInternal()is preserved as defense-in-depthThis covers approach (1) from the issue (validation at SDK entry points) and approach (3) (exported utility function). Since
OAuthClientProvideris an interface, the SDK can't enforce constructor-time validation on external implementations, but the exported utility makes it trivial.fix: validate clientMetadataUrl at construction time for fail-fast be…
pcarleton commentedon Mar 30, 2026
Hi @rechedev9 , thanks for your PR. It addresses (3), but I don't think it works well for (1). I'd want to catch it at OAuth provider construction time, so just the uitility function is sufficient, and calling it in example implementations.
If you can remove the various checks at all entry points, that PR would work otherwise.
fix(auth): add validateClientMetadataUrl utility for fail-fast valida…
rechedev9 commentedon Mar 30, 2026
@pcarleton Thanks for the feedback — you're right. I've reworked the PR to match what you described:
What changed:
validateClientMetadataUrl()as an exported utility (approach 3)InMemoryOAuthClientProvider's constructor as a usage example (approach 1 done correctly — at provider construction time)StreamableHTTPClientTransport,SSEClientTransport,auth(), andwithOAuthauthInternal()The PR is now much smaller (+113/−2 across 5 files vs the previous +318/−7 across 9). The branch has been rebased on main so the merge conflicts are resolved.