OAuth Protected Resource Metadata with RFC 9728
How RFC 9728 binds a protected resource to authorization servers, scopes, token methods, and OAuth discovery used by MCP clients.
An OAuth client needs configuration from both sides of a protected exchange. RFC 8414 describes the authorization server that issues tokens. RFC 9728 describes the protected resource that accepts them.
That second document answers questions an authorization-server document cannot answer alone: Which issuer may authorize access to this resource? Which scopes does the resource disclose? How can a token be presented? Where should a client read resource policy?
For remote MCP, this separation supplies the discovery path from a protected MCP endpoint to its permitted authorization server.
The resource identifier anchors the document
RFC 9728 defines a resource identifier as an HTTPS URL without a fragment. It should usually omit a query. The identifier names the protected resource and determines where its metadata is retrieved.
For a root resource identifier, the metadata URL is straightforward:
Resource: https://resource.example
Metadata: https://resource.example/.well-known/oauth-protected-resource
When the resource identifier has a path, the well-known suffix is inserted before that path:
Resource: https://resource.example/tenant-a/mcp
Metadata: https://resource.example/.well-known/oauth-protected-resource/tenant-a/mcp
This transformation lets one resource server publish separate documents for distinct protected resources. It also prevents an unrelated host from becoming authoritative merely by claiming another resource's URL.
The returned JSON has a required resource member. A client must confirm that value is identical to the resource identifier used to form the metadata request. If it differs, stop. Following authorization servers from mismatched metadata removes the origin binding the well-known derivation was designed to provide.
Use a real URI parser and preserve encoded path components. Hand-built concatenation is likely to mishandle a trailing slash, escaped character, port, or path boundary.
Authorization servers and scopes describe the relationship
The authorization_servers member is an array of issuer identifiers for authorization servers that may be used with the resource. A client selects an issuer allowed by its application profile, retrieves that issuer's RFC 8414 metadata, validates the issuer exactly, and follows the supported OAuth flow.
An array is not a trust shortcut. If several issuers appear, the client still needs a selection policy. An attacker who can alter the resource document could steer a client toward a different issuer, so HTTPS validation, exact resource matching, redirect controls, and local issuer policy all remain important.
scopes_supported lists scopes the resource is willing to disclose. RFC 9728 warns that the list is not an instruction to request every scope. A client should ask for the minimum permission needed for the selected operation, following the least-privilege guidance in RFC 9700.
The authorization server may publish a reciprocal protected_resources list. Where an application profile expects both lists, compare them for consistency. A resource that points to an issuer while the issuer explicitly lists a different resource needs operator review before token exchange.
Other registered metadata can describe bearer-token presentation methods, a resource JWK Set, signing algorithms, mutual TLS or DPoP capabilities, documentation, policy, and terms. Each value describes capability or location. It does not override token audience checks or application authorization.
RFC 9728 also permits signed_metadata represented as a JWT. The JWT must be digitally signed or MACed with JWS and contain an iss claim identifying the party attesting to its claims. A client that supports this feature validates the signature or MAC under an explicit trust policy for that attesting issuer. Accepted values from signed_metadata take precedence over corresponding plain JSON values; a client that does not support the feature may ignore it. This integrity protection does not remove the need to compare the resource identifier or validate network retrieval.
Resource JWKs have scoped purposes. A jwks_uri in this document can support specifications that verify resource-signed responses. It should not be confused with the authorization server's keys or used to validate tokens unless the selected OAuth profile assigns that role.
A challenge can direct the client to current metadata
RFC 9728 adds the resource_metadata authentication parameter. A protected resource may include it in WWW-Authenticate:
HTTP/1.1 401 Unauthorized
WWW-Authenticate: Bearer resource_metadata="https://resource.example/.well-known/oauth-protected-resource"
The flow can then proceed in a defined order. The client requests the protected resource, receives the challenge, retrieves and validates resource metadata, chooses an allowed authorization server, retrieves and validates its metadata, obtains a token, and retries the original request.
The parameter can be used with schemes beyond Bearer when their specifications allow it. Keep the challenge parser standards-compliant; commas and quoted values make ad hoc splitting unsafe.
A resource may send a later challenge to indicate that metadata changed. Clients should refresh the document after that instruction rather than relying indefinitely on a cached authorization-server list. Operators should set HTTP cache directives that balance availability with their revocation and migration needs.
How MCP authorization uses RFC 9728
The current MCP authorization specification makes authorization optional for MCP implementations. When authorization is supported with an HTTP-based transport, implementations should follow that profile; within it, MCP servers must implement Protected Resource Metadata and clients must use it for authorization-server discovery. An HTTP MCP server that does not support authorization is not required by this optional profile to publish OAuth metadata. In the authorization model, the remote MCP server is the protected resource and its authorization server issues access tokens for that resource.
This role split prevents a client from assuming that the MCP endpoint and token issuer share a host. It also lets a protected MCP server identify more than one permitted issuer when its profile supports that configuration.
The metadata does not enumerate MCP tools or grant their use. After a client obtains a token, the MCP server must validate the token audience or resource, scopes, expiry, issuer, and sender constraint where applicable. Tool-level and tenant-level authorization still run for every operation. Runtime MCP capability listing remains separate from OAuth discovery.
Clients should treat metadata retrieval as untrusted network activity. Permit HTTPS, limit redirects and total bytes, reject private or local addresses in server-side fetchers, recheck resolved addresses after redirects, enforce JSON media expectations, and cache by validated resource identifier. Log failures without recording tokens.
Why TKOResearch publishes no resource metadata
The current TKOResearch site doesn't expose a public OAuth-protected API or remote MCP server. Its contact form accepts validated submissions for a web workflow; it isn't a token-protected developer resource.
Publishing /.well-known/oauth-protected-resource would imply a resource identifier, permitted authorization server, scope model, and bearer challenge flow that don't exist. A fabricated document could cause clients to attempt authorization against unrelated endpoints.
TARE should publish RFC 9728 metadata when a real protected resource ships with an accountable owner. The release gate should include a canonical resource identifier, allowed issuer policy, minimal scopes, challenge behavior, token audience validation, key and revocation operations, tenant authorization, monitoring, cache policy, and interoperability tests.
Until that gate is met, no protected-resource document is the accurate security posture. Discovery should describe deployed authority, never manufacture it.
