OIDC endpoints
AgentKeychain conforms to OIDC discovery. If your auth library supports a discovery URL, this is the only thing you need to configure.
Discovery
GET https://agentkeychain.com/.well-known/openid-configurationExample response:
{
"issuer": "https://agentkeychain.com",
"authorization_endpoint": "https://agentkeychain.com/authorize",
"token_endpoint": "https://api.agentkeychain.com/v1/token",
"userinfo_endpoint": "https://api.agentkeychain.com/v1/userinfo",
"introspection_endpoint": "https://api.agentkeychain.com/v1/token/introspect",
"jwks_uri": "https://agentkeychain.com/.well-known/jwks.json",
"registration_endpoint": "https://api.agentkeychain.com/v1/clients/register",
"scopes_supported": ["openid", "profile", "agent_identity"],
"response_types_supported": ["code"],
"grant_types_supported": ["authorization_code", "refresh_token"],
"code_challenge_methods_supported": ["S256"],
"subject_types_supported": ["pairwise"],
"id_token_signing_alg_values_supported": ["ES256"],
"token_endpoint_auth_methods_supported": [
"client_secret_basic", "client_secret_post"
]
}Endpoints
| Endpoint | Purpose |
|---|---|
GET /authorize | Authorization Code + PKCE entry point. The agent authenticates here; the browser is redirected back to your redirect_uri with a code. |
POST /v1/token | Exchange an authorization code for an access token, refresh token, and signed ID token. Also handles refresh grants. |
GET /v1/userinfo | Returns the same claims as the ID token, in JSON form, for libraries that prefer userinfo to JWT parsing. |
GET /.well-known/jwks.json | ES256 public keys for verifying ID token signatures. Cache for up to 24 hours. |
POST /v1/token/introspect | Check whether a previously issued token is still active. Revoked tokens return active: false. |
Authorization request
A standard OIDC authorization request. Your library builds this automatically — included here for reference.
GET https://agentkeychain.com/authorize?
response_type=code&
client_id=akc_client_wiki123&
redirect_uri=https://yourapp.com/api/auth/callback/agentkeychain&
scope=openid+profile&
state=s-abc...&
nonce=n-xyz...&
code_challenge=E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM&
code_challenge_method=S256Token exchange
POST https://api.agentkeychain.com/v1/token
Content-Type: application/x-www-form-urlencoded
Authorization: Basic base64(client_id:client_secret)
grant_type=authorization_code&
code=<auth_code>&
redirect_uri=https://yourapp.com/api/auth/callback/agentkeychain&
code_verifier=<pkce_verifier>Response:
{
"access_token": "at_...",
"refresh_token": "rt_...",
"id_token": "<signed JWT>",
"token_type": "Bearer",
"expires_in": 3600,
"scope": "openid profile"
}The scope field echoes the scopes actually granted, which may be narrower than what you requested if the owner’s permission settings restrict them.
Branded button (optional)
If you’re letting your auth library drive the flow, you can still render the official “Sign in with AgentKeychain” button by importing it from @agentkeychain/web/react and passing an onClick handler that triggers your library’s sign-in. No client prop needed.
import { AgentKeychainButton } from "@agentkeychain/web/react";
import { signIn } from "next-auth/react";
export function LoginButton() {
return (
<AgentKeychainButton
onClick={() => signIn("agentkeychain")}
/>
);
}The same works with Auth0, Clerk, WorkOS, or any library that exposes a sign-in function — wire it into onClick. The button handles branding; your library handles the protocol.
/.well-known/jwks.json, find the key matching the JWT’s kid, and verify the ES256 signature.