Exchange credentials for an access token
const url = 'https://api.adversarial.com/api/v1/oauth/token';const options = { method: 'POST', headers: {'Content-Type': 'application/x-www-form-urlencoded'}, body: new URLSearchParams({ client_id: 'example', client_secret: 'example', code: 'example', code_verifier: 'example', grant_type: 'example', redirect_uri: 'example', refresh_token: 'example', resource: 'example' })};
try { const response = await fetch(url, options); const data = await response.json(); console.log(data);} catch (error) { console.error(error);}curl --request POST \ --url https://api.adversarial.com/api/v1/oauth/token \ --header 'Content-Type: application/x-www-form-urlencoded' \ --data client_id=example \ --data client_secret=example \ --data code=example \ --data code_verifier=example \ --data grant_type=example \ --data redirect_uri=example \ --data refresh_token=example \ --data resource=exampleOAuth 2.1 token endpoint. The grant_type field selects the exchange:
client_credentials: a service account exchanges itsclient_idandclient_secretfor an access and refresh token pair. This is the path API keys use.authorization_code: exchange an approved authorization code and its PKCE verifier for an access token and a refresh token.refresh_token: exchange a refresh token for a new pair. Refresh tokens issued to public clients rotate on each use, and replaying an already-used one revokes the whole chain.
Errors follow RFC 6749 §5.2 — an error code and error_description with
the matching HTTP status — so standard OAuth clients can parse them. A
malformed or wrongly-typed request body returns that same error shape
rather than a generic validation failure.
Request Bodyrequired
Section titled “Request Bodyrequired”The request body for the token endpoint.
grant_type accepts any string rather than a fixed set. RFC 6749 §1.3
treats it as a URI extension point, so an unrecognized grant is reported as
unsupported_grant_type — distinct from the invalid_request a malformed
body gets.
object
Authorization code (from the redirect after consent).
PKCE verifier — plaintext string whose S256 hash must match the code_challenge stored at authorize time.
One of client_credentials, authorization_code, refresh_token.
Other values are rejected with RFC 6749 §5.2 unsupported_grant_type.
Redirect URI presented at authorize time. Must match exactly per RFC 6749 §4.1.3.
RFC 8707 resource indicator. For client_credentials, lets a machine
client bind its token to a specific MCP resource (e.g. <origin>/mcp)
so it satisfies that resource’s audience check at use time. The
authorization_code path takes the resource from the authorize request
via the stored code row instead, so this field is read only for
client_credentials.
Examplegenerated
client_id=example&client_secret=example&code=example&code_verifier=example&grant_type=example&redirect_uri=example&refresh_token=example&resource=exampleResponses
Section titled “Responses”Token pair generated successfully
object
Examplegenerated
{ "access_token": "example", "expires_in": 1, "refresh_token": "example", "scope": "example", "token_type": "example"}Invalid request
Invalid credentials