| Internet-Draft | Token Exchange Target Service Discovery | June 2026 |
| McGuinness & Parecki | Expires 20 December 2026 | [Page] |
This specification defines a method for OAuth 2.0 clients to discover the set of available Token Exchange Targets (such as audiences, resources, scopes, and token types) for a given subject token when performing OAuth 2.0 Token Exchange. The discovery endpoint accepts a subject token of any type the authorization server supports, identified by a token type URI, and returns values that are valid inputs to subsequent Token Exchange requests, supporting advanced use cases such as identity chaining and cross-domain delegation.¶
This note is to be removed before publishing as an RFC.¶
The latest revision of this draft can be found at https://mcguinness.github.io/draft-mcguinness-token-xchg-target-svc-disco/draft-mcguinness-token-xchg-target-svc-disco.html. Status information for this document may be found at https://datatracker.ietf.org/doc/draft-mcguinness-token-xchg-target-svc-disco/.¶
Discussion of this document takes place on the Web Authorization Protocol Working Group mailing list (mailto:oauth@ietf.org), which is archived at https://mailarchive.ietf.org/arch/browse/oauth/. Subscribe at https://www.ietf.org/mailman/listinfo/oauth/.¶
Source for this draft and an issue tracker can be found at https://github.com/mcguinness/draft-mcguinness-token-xchg-target-svc-disco.¶
This Internet-Draft is submitted in full conformance with the provisions of BCP 78 and BCP 79.¶
Internet-Drafts are working documents of the Internet Engineering Task Force (IETF). Note that other groups may also distribute working documents as Internet-Drafts. The list of current Internet-Drafts is at https://datatracker.ietf.org/drafts/current/.¶
Internet-Drafts are draft documents valid for a maximum of six months and may be updated, replaced, or obsoleted by other documents at any time. It is inappropriate to use Internet-Drafts as reference material or to cite them other than as "work in progress."¶
This Internet-Draft will expire on 20 December 2026.¶
Copyright (c) 2026 IETF Trust and the persons identified as the document authors. All rights reserved.¶
This document is subject to BCP 78 and the IETF Trust's Legal Provisions Relating to IETF Documents (https://trustee.ietf.org/license-info) in effect on the date of publication of this document. Please review these documents carefully, as they describe your rights and restrictions with respect to this document. Code Components extracted from this document must include Revised BSD License text as described in Section 4.e of the Trust Legal Provisions and are provided without warranty as described in the Revised BSD License.¶
OAuth 2.0 Token Exchange [RFC8693] enables a client to present a token issued in one security domain to an authorization server and securely trade it for a new token issued for another domain. The exchanged token is minted with the Target Service's token requirements, including its own audience, resource indicators, and scopes, so it becomes valid and enforceable for the desired downstream service. This enables controlled cross-domain access, removes the confused-deputy problem by ensuring tokens are explicitly targeted to the correct service, and avoids requiring direct trust between the original token issuer and the Target Service.¶
Authorization Servers may be capable of issuing tokens to multiple services for a given subject token and client, but the client must already know which values it may request. Today, this knowledge is typically provided through static configuration, proprietary APIs, or informal documentation, leading to brittle integrations and unnecessary Token Exchange failures, particularly when subjects are authorized to access only a subset of available services.¶
This specification defines the OAuth 2.0 Token Exchange Target Service Discovery Endpoint, a standardized mechanism that enables clients to dynamically discover the set of available Token Exchange Targets (such as audiences, resources, scopes, and token types) for a given subject token. The authorization server evaluates both the subject token and the client's permissions and returns only the values the client is authorized to request.¶
This extension is especially valuable in scenarios requiring identity chaining and cross-domain authorization:¶
Progressive token exchange across service boundaries, such as multi-tier microservices architectures and delegated flows where tokens are exchanged with narrower or transformed permissions at each hop. The set of downstream services a client may target, and their required permissions, varies with the subject token's context and the client's authorization, so static configuration cannot anticipate these per-subject and per-client variations and clients attempt exchanges the subject is not authorized to perform.¶
Cross-boundary deployments where downstream services exist in separate administrative, organizational, or cloud domains with independently managed authorization policies. Unlike progressive token exchange, which transforms permissions within a single domain, this scenario spans distinct trust boundaries whose policies and authorized targets change dynamically, so a client must discover them at runtime rather than rely on fixed configuration.¶
Single Sign-On (SSO) to API flows, such as those enabled by the Identity Assertion Authorization Grant (ID-JAG) [I-D.oauth-identity-assertion-authz-grant], where a client needs to seamlessly connect to cross-domain resources and act on behalf of the user to access APIs.¶
Multi-tenant Target Services that share the same authorization server and/or resource across tenants, where the tenant is identified by a claim in the issued token. In these scenarios, the resource indicator alone cannot distinguish the tenants, so discovery enables a client to learn the distinct Target Services available per tenant and to present a tenant selection to the end user.¶
This specification provides the following benefits:¶
Dynamic Discovery: Eliminates static configuration requirements by enabling clients to discover available Token Exchange Targets at runtime, reducing integration failures and improving developer experience.¶
Standardization: Provides a standardized discovery mechanism, replacing proprietary APIs and improving interoperability across OAuth 2.0 implementations.¶
Real-Time Authorization: Returns Token Exchange Targets based on real-time policy evaluation, client permissions, and subject token context, ensuring accurate and up-to-date authorization information. This enables per-subject and per-client results, which is essential when the set of available targets varies by user or client.¶
The key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "NOT RECOMMENDED", "MAY", and "OPTIONAL" in this document are to be interpreted as described in BCP 14 [RFC2119] [RFC8174] when, and only when, they appear in all capitals, as shown here.¶
This document uses the following terms:¶
A downstream service that a client accesses using a token obtained through OAuth 2.0 Token Exchange [RFC8693]. A Target Service may be multi-tenant (see Section 3.4).¶
A combination of Token Exchange request parameters (an audience and, where applicable, resource, scope, and requested token type(s)) that the authorization server has authorized for a given subject token and requesting client. A Token Exchange Target is returned by the discovery endpoint as an element of the supported_targets array; it identifies how a client may obtain a token for a Target Service and does not assert that the service is reachable or operational.¶
This specification defines a new endpoint for OAuth 2.0 authorization servers that enables clients to discover the set of available Token Exchange Targets (such as audiences, resources, scopes, and token types) for a given subject token when performing OAuth 2.0 Token Exchange [RFC8693].¶
The endpoint is identified by the authorization server metadata parameter token_exchange_target_service_discovery_endpoint, as defined in Section 3.1.¶
The client makes a request to the token exchange target service discovery endpoint by sending an HTTP POST request to the endpoint URL. The client MUST use TLS as specified in Section 1.6 of [RFC6749].¶
The endpoint URL MUST be obtained from the authorization server's metadata document [RFC8414] using the token_exchange_target_service_discovery_endpoint parameter. The endpoint URL is an absolute URL.¶
The client sends the parameters using the application/x-www-form-urlencoded format per Appendix B of [RFC6749]. Character encoding MUST be UTF-8 as specified in Appendix B of [RFC6749]. If a parameter is included more than once in the request, the authorization server MUST return an error response with the error code invalid_request as described in Section 3.5.¶
The following parameters are used in the request:¶
REQUIRED. The subject token used as input to discovery. The token type is indicated by the subject_token_type parameter.¶
REQUIRED. A string value containing a URI, as described in Section 3 of [RFC8693], that indicates the type of the subject_token parameter. This identifier MUST be a valid URI, and SHOULD be registered in the "OAuth URI Registry" as established by [RFC6755].¶
The client MAY include additional parameters as defined by extensions, and the authorization server MUST ignore parameters it does not understand. The parameters of the client authentication method in use (for example, client_id, client_secret, or client_assertion and client_assertion_type) are part of that method and are not treated as unknown parameters.¶
The authorization server identifies the requesting client in order to evaluate its permissions (Section 5.3). Client authentication MAY be required by the authorization server. The means of client authentication are defined by the authorization server and MAY include any method supported by the authorization server, including those defined in Section 2.3 of [RFC6749] and extensions. If client authentication is required by the authorization server but not provided in the request, the authorization server MUST return an error response with the error code invalid_client as described in Section 3.5. A public client that does not authenticate MAY identify itself with the client_id parameter; the authorization server determines the trust it places in such an unauthenticated identifier, and MAY base its results on the subject token alone when no client identity is established.¶
The authorization server MUST process the subject_token parameter according to the following rules:¶
The authorization server MUST validate that the subject_token and subject_token_type parameters are not empty strings. If either parameter is an empty string, the authorization server MUST return an error response with the error code invalid_request as described in Section 3.5.¶
The authorization server MUST validate that the subject_token_type parameter is a valid URI. If the format is invalid (e.g., not a valid absolute URI or URN), the authorization server MUST return an error response with the error code invalid_request as described in Section 3.5.¶
The authorization server MUST determine whether it supports the indicated token type. This determination is an implementation decision and MAY be based on the authorization server's capabilities, the subject_token value, the authenticated client, or any combination thereof. If the subject_token_type is not supported by the authorization server for the given context, the authorization server MUST return an error response with the error code unsupported_token_type as described in Section 3.5.¶
The authorization server MUST validate the subject_token according to the rules for the indicated token type. The validation process MUST verify:¶
The token is properly formatted for the indicated token type¶
The token's signature (if applicable) is valid and can be verified using the appropriate cryptographic keys¶
The token was issued by a trusted issuer¶
The token has not expired¶
The token has not been revoked, where revocation status is applicable and available for the token type; a token known to be revoked MUST be rejected¶
The token is associated with the authenticated client, if client authentication is required¶
If the subject_token is invalid for any reason (e.g., malformed, expired, revoked, or does not match the subject_token_type), the authorization server MUST return an error response with the error code invalid_request as described in Section 3.5.¶
The authorization server MUST evaluate the subject_token in conjunction with the requesting client's permissions (the authenticated client, when client authentication is used) to determine which Token Exchange Targets are available for discovery. The specific authorization policy evaluation mechanism is implementation-specific and MAY be based on scopes, claims, resource-based access control, or other authorization models.¶
The following is an example of a discovery request:¶
POST /target-discovery HTTP/1.1 Host: as.example.com Content-Type: application/x-www-form-urlencoded client_id=client-A &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer &client_assertion=eyJhbGciOi... &subject_token=SlAV32hkKG...ACCESSTOKEN... &subject_token_type=urn:ietf:params:oauth:token-type:access_token¶
The authorization server validates the request and returns a response with the discovery results. The Content-Type header of the response MUST be set to application/json.¶
Because the response contains sensitive, per-subject and per-client authorization information, the authorization server SHOULD set Cache-Control: no-store by default. A deployment that accepts the associated risk MAY instead permit bounded private caching; in that case the cache directives MUST mark the response as private (for example, Cache-Control: private) and shared caches MUST NOT store it. The authorization server MAY include cache validators (such as ETag or Last-Modified headers) to enable conditional requests by the client, as specified in [RFC9111].¶
If the request is valid and authorized, the authorization server returns a JSON [RFC8259] object containing a supported_targets property: an array of the Token Exchange Targets (see Section 2) available to the client. To perform a token exchange, the client selects one target and uses its values as the corresponding request parameters.¶
Empty and null values are not valid property values. The authorization server MUST NOT include an optional property whose value would be null, an empty string, an empty array, or an array containing an empty string; it MUST omit the property instead. A REQUIRED property MUST have a non-empty value.¶
Each target object contains the following properties:¶
REQUIRED. The value the client uses, verbatim, as the audience parameter in a subsequent token exchange request, identifying the Target Service as defined in Section 2.1 of [RFC8693]. Its syntax is authorization-server-defined unless constrained by a profile of this specification; the client MUST treat it as opaque and MUST NOT assume it is a URI. If the value is a URI that does not itself provide a usable location (for example, a URN), the authorization server SHOULD also return a resource property that provides one. A multi-tenant Target Service returns a distinct audience value per tenant; see Section 3.4.¶
OPTIONAL. A machine-readable identifier for the tenant of a multi-tenant Target Service. The issued token represents this tenant using the claim defined by the token format and Target Service (for example, the aud_tenant claim when the Identity Assertion Authorization Grant [I-D.oauth-identity-assertion-authz-grant] is used); the specific claim name and encoding are outside the scope of this specification. This property is included only when the Target Service is multi-tenant and the authorization server knows the tenant identifier. It is descriptive: it lets the client correlate a Target Service with the tenant context of the resulting issued token, and is not used as a selector in the token exchange request (the audience value selects the tenant).¶
OPTIONAL. A single resource indicator value or an array of resource indicator values, as defined in Section 2 of [RFC8707], available for this target. Each value MUST be an absolute URI and MUST NOT include a fragment component, per Section 2 of [RFC8707]. If present as an array, the array entries correspond to repeated resource parameters in the subsequent token exchange request.¶
OPTIONAL. A string value containing a space-delimited list of OAuth 2.0 scope values, as defined in Section 3.3 of [RFC6749], that are available for this target. Each scope value MUST conform to the scope syntax defined in Section 3.3 of [RFC6749]. If present, the value MUST contain at least one scope value. The authorization server determines which scopes to return based on its authorization policy evaluation, which is implementation-specific. The scopes returned SHOULD be those that would be authorized in a subsequent token exchange request per Section 2.1 of [RFC8693].¶
OPTIONAL. An array of strings indicating the token types that may be requested for this target in a subsequent token exchange operation. Each string MUST be a valid absolute URI. A token type identifier MAY be any URI, as permitted by Section 3 of [RFC8693], when that URI identifies the requested token type or token usage profile understood by the authorization server and client. For example, urn:ietf:params:oauth:grant-type:jwt-bearer identifies a JWT intended to be presented as a JWT bearer authorization grant as defined by [RFC7523]; this specification intentionally permits the RFC 7523 grant-type URI to be used in this role, which the generic urn:ietf:params:oauth:token-type:jwt identifier does not convey. If omitted, the client may use any token type supported by the authorization server.¶
OPTIONAL. A human-readable name for the Target Service, suitable for display to an end user (for example, in a service picker). This value is intended for presentation only and MUST NOT be used as a token exchange parameter.¶
OPTIONAL. The OAuth 2.0 client identifier that the client uses with the Target Service when presenting the issued token (see Section 3.4). This property supports multi-tenant Target Services that require a distinct client registration for each tenant. The client is expected to possess credentials for the indicated client identifier where client authentication applies. If omitted, the client uses a client identity it determines is appropriate by other means.¶
Extensions to this specification MAY define additional properties for the response object or for target objects. Clients MUST ignore any properties they do not understand.¶
A target is identified by its audience together with its resource set (the complete set of resource values, or their absence). This key MUST be unique within the supported_targets array: no two targets may share both the same audience and the same resource set (when comparing sets, element order does not matter, but the membership must match). Multiple targets with the same audience MAY therefore be returned only when they differ in their resource set. Because each key appears at most once, a target's scope is the aggregate set of scopes authorized for that key, rather than one of several alternative scope bundles. A multi-tenant Target Service is represented as one target per tenant, each with a distinct audience (see Section 3.4), so the audience distinguishes the tenants.¶
If no Token Exchange Targets are available for the given subject token and client, the authorization server returns a JSON object with an empty supported_targets array: {"supported_targets": []}.¶
Discovery results reflect authorization at the time of the request and are not a guarantee. The authorization server re-evaluates authorization when the subsequent token exchange is performed, and that exchange might still fail (for example, if policy changed, the subject token expired, or the target became unavailable in the interim). A client MUST handle errors from the token exchange request [RFC8693] rather than assuming a discovered target will succeed.¶
The following is an example of a successful discovery response:¶
HTTP/1.1 200 OK
Content-Type: application/json
{
"supported_targets": [
{
"audience": "https://api.example.com",
"resource": ["https://api.example.com/orders", "https://api.example.com/inventory"],
"scope": "orders.read inventory.read",
"supported_token_types": [
"urn:ietf:params:oauth:token-type:access_token"
]
},
{
"audience": "https://billing.provider.example",
"scope": "customer.read customer.write",
"supported_token_types": [
"urn:ietf:params:oauth:grant-type:jwt-bearer"
]
},
{
"audience": "https://backend-audit-service.example.com",
"scope": "audit.read audit.write",
"supported_token_types": [
"urn:ietf:params:oauth:token-type:access_token"
]
}
]
}
¶
A Target Service may be multi-tenant, sharing the same authorization server and/or the same resource across two or more tenants, where the tenant is identified by a claim in the issued token. For example, an authorization server as.saas.example may host two tenants, dev and staging, that share the resource https://api.saas.example. Because the resource (and authorization server) is shared, the resource indicator alone cannot distinguish the tenants.¶
To support this case without changing the OAuth 2.0 Token Exchange [RFC8693] request contract, the authorization server represents each tenant of a multi-tenant Target Service as a separate target object with a distinct audience value. As described for the audience property, the client uses the discovered value verbatim as the audience parameter in the subsequent token exchange request, and the authorization server resolves it to the tenant-specific audience and tenant context in the issued token. The claim that conveys the tenant in the issued token is determined by the token format and Target Service (for example, the aud_tenant claim when the Identity Assertion Authorization Grant [I-D.oauth-identity-assertion-authz-grant] is used) and is outside the scope of this specification.¶
When a Target Service is multi-tenant, the authorization server SHOULD include the tenant property so that the client can correlate the Target Service with the tenant context of the resulting issued token, and SHOULD include the display_name property so that a client can present a tenant picker to an end user.¶
If a multi-tenant Target Service requires a distinct client registration for each tenant, the authorization server MAY include the client_id property in each target object to indicate the client identifier the client uses with that tenant when presenting the issued token. The issued token is not necessarily presented through token exchange: depending on the Target Service, it may be an authorization grant, such as an ID-JAG [I-D.oauth-identity-assertion-authz-grant], that the client redeems at the Target Service's authorization server (where this client_id is used for client authentication), or an access token that the client presents directly to a resource server. If a shared client registration is used across tenants, the client_id property is omitted.¶
The following is a non-normative example of a discovery response for a multi-tenant Target Service with two tenants that share the same resource:¶
HTTP/1.1 200 OK
Content-Type: application/json
{
"supported_targets": [
{
"audience": "urn:saas:tenant:dev",
"tenant": "dev",
"resource": "https://api.saas.example",
"scope": "orders.read orders.write",
"supported_token_types": [
"urn:ietf:params:oauth:grant-type:jwt-bearer"
],
"display_name": "SaaS Example Dev",
"client_id": "client-dev"
},
{
"audience": "urn:saas:tenant:staging",
"tenant": "staging",
"resource": "https://api.saas.example",
"scope": "orders.read orders.write",
"supported_token_types": [
"urn:ietf:params:oauth:grant-type:jwt-bearer"
],
"display_name": "SaaS Example Staging",
"client_id": "client-staging"
}
]
}
¶
The client presents the two tenants to the end user using the display_name values (for example, "SaaS Example Dev" and "SaaS Example Staging"). Once the user selects a tenant, the client performs the token exchange using the corresponding audience value (for example, urn:saas:tenant:dev). When the resulting issued token is later presented at the Target Service, the client uses the corresponding client_id, if present and where client authentication applies.¶
If the request failed, the authorization server returns an error response as defined in Section 5.2 of [RFC6749]. The response MUST use the application/json media type, and the Content-Type header MUST be set to application/json. In addition to the error codes specified in Section 5.2 of [RFC6749], the following error codes may be returned:¶
The authorization server does not support the subject token type indicated by the subject_token_type parameter.¶
The HTTP status code is determined as specified in Section 5.2 of [RFC6749]. In particular, when the error is invalid_client and the client attempted to authenticate via the Authorization request header field, the authorization server responds with HTTP 401 (Unauthorized) and includes a WWW-Authenticate response header field; otherwise it responds with HTTP 400 (Bad Request).¶
When the authorization server rate-limits a client (see Section 5.4), it MAY respond with HTTP 429 (Too Many Requests) [RFC6585] and SHOULD include a Retry-After header field [RFC9110].¶
The following is an example of an error response:¶
HTTP/1.1 400 Bad Request
Content-Type: application/json
{
"error": "invalid_request",
"error_description": "The subject token is invalid or expired"
}
¶
This example demonstrates a complete cross-domain identity chaining workflow described in [I-D.ietf-oauth-identity-chaining] with the addition of the token exchange target service discovery endpoint.¶
The client begins with a subject access token issued by Domain A and calls the target service discovery endpoint to learn which Token Exchange Targets are available.¶
POST https://as.domainA.example/target-discovery HTTP/1.1 Host: as.domainA.example Content-Type: application/x-www-form-urlencoded client_id=client-A &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer &client_assertion=eyJhbGciOi... &subject_token=SlAV32hkKG...ACCESSTOKEN... &subject_token_type=urn:ietf:params:oauth:token-type:access_token¶
HTTP/1.1 200 OK
Content-Type: application/json
{
"supported_targets": [
{
"audience": "https://api.domainB.example",
"resource": ["https://api.domainB.example/orders", "https://api.domainB.example/inventory"],
"scope": "orders.read inventory.read",
"supported_token_types": [
"urn:ietf:params:oauth:grant-type:jwt-bearer"
]
}
]
}
¶
From this response, the client learns that it may request a token exchange for the audience https://api.domainB.example with the resources https://api.domainB.example/orders and https://api.domainB.example/inventory and the scopes orders.read and inventory.read. The supported_token_types value tells the client that, in the subsequent token exchange, it may request a JWT to be presented to the Target Service as a jwt-bearer authorization grant [RFC7523].¶
The discovery response's supported_token_types property indicates the token types the client may request for the target. In this example it listed urn:ietf:params:oauth:grant-type:jwt-bearer, so the client proceeds directly to the token exchange. When a discovery response omits supported_token_types, the client determines the requestable token types from the Target Service's documentation or other out-of-band configuration.¶
The client now performs a token exchange with Domain A's token endpoint, requesting a JWT for Domain B using the values discovered in the previous steps.¶
POST https://as.domainA.example/token HTTP/1.1 Host: as.domainA.example Content-Type: application/x-www-form-urlencoded grant_type=urn:ietf:params:oauth:grant-type:token-exchange &client_id=client-A &client_assertion_type=urn:ietf:params:oauth:client-assertion-type:jwt-bearer &client_assertion=eyJhbGciOi... &subject_token=SlAV32hkKG...ACCESSTOKEN... &subject_token_type=urn:ietf:params:oauth:token-type:access_token &requested_token_type=urn:ietf:params:oauth:grant-type:jwt-bearer &audience=https://api.domainB.example &resource=https://api.domainB.example/orders &resource=https://api.domainB.example/inventory &scope=orders.read inventory.read¶
HTTP/1.1 200 OK
Content-Type: application/json
{
"access_token": "eyJraWQiOi...DOMAINB.JWT...",
"issued_token_type": "urn:ietf:params:oauth:grant-type:jwt-bearer",
"token_type": "N_A",
"expires_in": 3600,
"scope": "orders.read inventory.read"
}
¶
The client now holds a Domain-B-scoped JWT token that can be used to access the Target Service, derived from Domain A's access token through the token exchange process.¶
The authorization server MUST validate the subject token as specified in Section 3.2.2. In particular, it MUST verify that the token is well-formed for the indicated type, is correctly signed by a trusted issuer, has not expired, has not been revoked (where revocation status is applicable and available), and, where client authentication is required, is associated with the authenticated client. A token that fails validation MUST be rejected as described in Section 3.2.2.¶
The authorization server SHOULD require client authentication for the discovery endpoint to prevent unauthorized access to authorization information. The authorization server MUST support at least one of the client authentication methods defined in Section 2.3 of [RFC6749]. If client authentication is required but not provided, the authorization server MUST return an error response with the error code invalid_client as described in Section 3.5.¶
The discovery endpoint reveals information about which Target Services are available for a given subject token and client. This information could be used by an attacker to enumerate authorization relationships. To mitigate this risk:¶
The authorization server SHOULD require client authentication¶
The authorization server SHOULD apply rate limiting to prevent enumeration attacks¶
The authorization server MAY return different results based on the authenticated client to limit information disclosure¶
The authorization server SHOULD log access to the discovery endpoint for security monitoring¶
For multi-tenant Target Services, the tenant, display_name, and client_id properties reveal the existence of specific tenants and, where present, the per-tenant client registration topology of the authorization server. This information could be used by an attacker to enumerate tenants or client registrations. The authorization server MUST only return target objects, including their tenant and client registration properties, that the authenticated client is authorized to discover, applying the same authorization policy enforcement and information disclosure mitigations described in this section. The authorization server SHOULD NOT include a client_id value that the authenticated client is not authorized to use.¶
The subject token is transmitted in the request. The authorization server MUST require the use of TLS as specified in Section 1.6 of [RFC6749] to protect the token in transit. Because the request body carries a live credential, the authorization server MUST NOT record the subject_token (or other equally sensitive request content) in logs, audit records, or error reports, and SHOULD avoid emitting it where it could be retained by intermediaries.¶
The authorization server MUST NOT provide detailed error messages that could aid an attacker in understanding the authorization server's internal state or policies. Error responses SHOULD be generic and not reveal specific information about why a request failed beyond what is necessary for the client to correct the request.¶
The discovery endpoint returns information about authorization relationships between subjects, clients, and Target Services. This information may be considered privacy-sensitive, as it reveals:¶
Which Target Services a subject is authorized to access¶
The scope of permissions available for each Target Service¶
The existence of authorization relationships¶
For multi-tenant Target Services, the specific tenants a subject is associated with or authorized to access, as conveyed by the tenant, display_name, and client_id properties¶
To protect privacy:¶
The authorization server SHOULD only return information that the authenticated client is authorized to know¶
The authorization server SHOULD apply the principle of least privilege when determining which Token Exchange Targets to return¶
The authorization server SHOULD only disclose tenant-identifying properties (tenant, display_name, and client_id) for the tenants that both the subject and the authenticated client are authorized to access¶
The authorization server SHOULD log access to the discovery endpoint in accordance with applicable privacy regulations¶
The authorization server MAY provide mechanisms for subjects to control or limit the information returned by the discovery endpoint¶
This specification registers the following error in the IANA "OAuth Extensions Error Registry" established by [RFC6749], adding a usage location for the token exchange target service discovery endpoint. The error name unsupported_token_type is also registered for other usage locations (for example, the token revocation endpoint); this registration adds a distinct usage location and does not change the existing entries.¶
Error Name: unsupported_token_type¶
Error Usage Location: Token exchange target service discovery endpoint response¶
Related Protocol Extension: OAuth 2.0 Token Exchange Target Service Discovery¶
Change Controller: IETF¶
Specification Document(s): [[ This document ]]¶
The authors would like to thank the following individuals who contributed ideas, feedback, and wording that helped shape this specification: Max Gerber¶
-02¶
Added optional support for multi-tenant Target Services that share an authorization server and/or resource across tenants, introducing the optional tenant, display_name, and client_id properties and defining the audience property as the exact value to use in Token Exchange, with authorization-server-defined syntax (per Section 2.1 of [RFC8693]), so that a distinct audience value per tenant selects the tenant without changing the OAuth 2.0 Token Exchange request contract.¶
Replaced the obsolete JSON reference RFC 7159 with RFC 8259 and corrected the abbrev value.¶
Required discovery responses to be marked private and not stored by shared caches.¶
Clarified that discovery results are point-in-time and not a guarantee: the subsequent token exchange is re-evaluated and may still fail.¶
Added HTTP 429 with Retry-After for rate limiting.¶
Replaced the invalid urn:ietf:params:oauth:token-type:jwt-bearer token type identifier; examples now use urn:ietf:params:oauth:grant-type:jwt-bearer as the token type value to denote a JWT presented as a jwt-bearer authorization grant [RFC7523], and supported_token_types notes that any URI may be a token type identifier per Section 3 of [RFC8693].¶
Clarified the client identity model (client authentication parameters versus unknown parameters, public-client identification) and that the requesting client's permissions are evaluated.¶
Registered a usage location for the unsupported_token_type error in the OAuth Extensions Error Registry.¶
Aligned the resource property with RFC 8707 (absolute URI, no fragment, repeated parameters); made scope the aggregate available set per audience and resource.¶
Softened the subject-token revocation check to where revocation status is applicable and available.¶
Switched the caching reference to RFC 9111 (normative) and made no-store the default with bounded private caching as an opt-in.¶
Narrowed the abstract's claim about accepted subject token types.¶
Editorial: consolidated the empty-string handling into a single response-construction rule, removed repeated multi-tenant audience and subject-token-validation text, moved the Authorization Server Metadata section ahead of the worked example, and aligned IANA change controllers.¶
Extended the empty-value rule to cover null and arrays containing empty strings; restored the requirement that a present scope contain at least one value; specified that invalid_client uses HTTP 401 per Section 5.2 of [RFC6749]; and promoted Multi-Tenant Target Services to a top-level subsection of the endpoint section.¶
Clarified in the example that a discovered urn:ietf:params:oauth:grant-type:jwt-bearer value is requested via token exchange and later presented to the Target Service as a jwt-bearer authorization grant.¶
Editorial: relocated Authorization Server Metadata to a subsection of the endpoint section so the endpoint URL is discovered before it is used; reworded summary text from "Target Services" to "Token Exchange Targets" to avoid implying the endpoint discovers live service availability; tightened the introduction; and added client authentication to the discovery and token exchange examples consistently.¶
Resolved the conflicting audience syntax language: the property is now defined once as the exact, opaque value the client uses in Token Exchange, with authorization-server-defined syntax unless profiled, and the duplicate description in the multi-tenant section was removed.¶
Clarified the discovery model: added formal definitions of "Target Service" (the real downstream service) and "Token Exchange Target" (a pre-authorized combination of Token Exchange request parameters, not a live service) to Conventions and Definitions, renamed each response element from "target service object" to "target object", and restated the uniqueness rule in terms of a target's (audience, resource set) key. No wire identifiers changed.¶
Pre-publication cleanup: referenced [RFC6585] and [RFC9110] for the HTTP 429 / Retry-After guidance; added a requirement that the authorization server not log the subject_token; kept [RFC6755] informative (consistent with [RFC8693]); and made the capitalization of "authorization server" consistent.¶
Tightened the supported_token_types language so a token type identifier MUST identify the requested token type or token usage profile understood by the authorization server and client, and promoted [RFC7523] to normative, since the draft now relies on it to define the protocol-significant urn:ietf:params:oauth:grant-type:jwt-bearer token type value.¶
-01¶
Changed discovery response to an object for extensibility with supported_targets param¶
Updated references¶
-00¶
Initial revision¶