Auth OIDC
The Auth service is an OpenID Connect (OIDC) provider backed by Solidus decentralized identities. Applications use standard OIDC flows to authenticate users, receiving JWT tokens with DID-based subject identifiers.
Base URL: https://auth.solidus.network
Discovery
OpenID Configuration
Returns the OIDC Discovery document with all supported endpoints and features.
GET /.well-known/openid-configuration
Auth: None
curl https://auth.solidus.network/.well-known/openid-configuration// Response 200
{
"issuer": "https://auth.solidus.network",
"authorization_endpoint": "https://auth.solidus.network/authorize",
"token_endpoint": "https://auth.solidus.network/token",
"userinfo_endpoint": "https://auth.solidus.network/userinfo",
"introspection_endpoint": "https://auth.solidus.network/introspect",
"revocation_endpoint": "https://auth.solidus.network/revoke",
"jwks_uri": "https://auth.solidus.network/.well-known/jwks.json",
"scopes_supported": ["openid", "profile", "email", "did"],
"response_types_supported": ["code"],
"grant_types_supported": ["authorization_code", "refresh_token"],
"subject_types_supported": ["public"],
"id_token_signing_alg_values_supported": ["EdDSA"],
"code_challenge_methods_supported": ["S256"],
"token_endpoint_auth_methods_supported": ["client_secret_post", "client_secret_basic"]
}JSON Web Key Set
Returns the public keys used to verify ID tokens. Solidus uses EdDSA (Ed25519) for token signing.
GET /.well-known/jwks.json
Auth: None
// Response 200
{
"keys": [
{
"kty": "OKP",
"crv": "Ed25519",
"x": "7Hk3mRtQZvXp2nBw9Lj4KxYm8...",
"kid": "solidus-auth-key-1",
"use": "sig",
"alg": "EdDSA"
}
]
}Authorization
Authorize
Start an authorization code flow. Redirect the user’s browser to this endpoint. After the user authenticates and consents (or auto-approves for first-party apps), they are redirected back to your redirect_uri with an authorization code.
GET /authorize
Auth: None (browser redirect)
| Query Param | Type | Required | Description |
|---|---|---|---|
response_type | string | Yes | Must be code |
client_id | string | Yes | Your registered client ID |
redirect_uri | string | Yes | URL to redirect after authorization |
scope | string | Yes | Space-separated scopes: openid, profile, email, did |
state | string | Yes | Opaque value for CSRF protection |
nonce | string | No | Value included in the ID token for replay protection |
code_challenge | string | Yes | PKCE challenge (Base64URL-encoded SHA-256 of code verifier) |
code_challenge_method | string | Yes | Must be S256 |
GET https://auth.solidus.network/authorize?
response_type=code&
client_id=solidus-identity&
redirect_uri=https://identity.solidus.network/auth/callback&
scope=openid profile email did&
state=abc123xyz&
nonce=n-0S6_WzA2Mj&
code_challenge=E9Melhoa2OwvFrEMTJguCHaoeK1t8URWbuGJSstw-cM&
code_challenge_method=S256Success redirect:
https://identity.solidus.network/auth/callback?code=auth_code_7Hk3mRtQ&state=abc123xyzError redirect:
https://identity.solidus.network/auth/callback?error=access_denied&error_description=User+denied+consent&state=abc123xyzFirst-Party Auto-Approve
Registered first-party clients skip the consent screen. The user authenticates and is immediately redirected with an authorization code. Current first-party clients:
| Client ID | Application |
|---|---|
solidus-identity | Identity wallet |
solidus-verify | Verify dashboard |
Third-party clients show a consent screen where the user approves the requested scopes.
Token Exchange
Exchange Authorization Code
Exchange an authorization code for tokens.
POST /token
Auth: None (client authenticates via body or Basic auth)
Content-Type: application/x-www-form-urlencoded
curl -X POST https://auth.solidus.network/token \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=authorization_code" \
-d "code=auth_code_7Hk3mRtQ" \
-d "client_id=solidus-identity" \
-d "client_secret=cs_live_abc123def456..." \
-d "redirect_uri=https://identity.solidus.network/auth/callback" \
-d "code_verifier=dBjftJeZ4CVP-mB92K27uhbUJU1p1r_wW1gFWFOEjXk"| Field | Type | Required | Description |
|---|---|---|---|
grant_type | string | Yes | Must be authorization_code |
code | string | Yes | The authorization code from the redirect |
client_id | string | Yes | Your registered client ID |
client_secret | string | Yes | Your client secret |
redirect_uri | string | Yes | Must match the redirect URI from the authorize request |
code_verifier | string | Yes | PKCE code verifier (the original random string) |
// Response 200
{
"access_token": "eyJhbGciOiJFZERTQSIsInR5cCI6ImF0K2p3dCJ9...",
"id_token": "eyJhbGciOiJFZERTQSIsInR5cCI6IkpXVCJ9...",
"token_type": "Bearer",
"expires_in": 3600,
"refresh_token": "rt_7Hk3mRtQZvXp2nBw9Lj4K..."
}Refresh Token
Exchange a refresh token for a new access token.
POST /token
Content-Type: application/x-www-form-urlencoded
curl -X POST https://auth.solidus.network/token \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "grant_type=refresh_token" \
-d "refresh_token=rt_7Hk3mRtQZvXp2nBw9Lj4K..." \
-d "client_id=solidus-identity" \
-d "client_secret=cs_live_abc123def456..."| Field | Type | Required | Description |
|---|---|---|---|
grant_type | string | Yes | Must be refresh_token |
refresh_token | string | Yes | The refresh token from a previous token exchange |
client_id | string | Yes | Your registered client ID |
client_secret | string | Yes | Your client secret |
// Response 200
{
"access_token": "eyJhbGciOiJFZERTQSIsInR5cCI6ImF0K2p3dCJ9...",
"id_token": "eyJhbGciOiJFZERTQSIsInR5cCI6IkpXVCJ9...",
"token_type": "Bearer",
"expires_in": 3600,
"refresh_token": "rt_9Xm4pLkWnR2nBw9Lj4K..."
}User Info
Get User Info
Retrieve claims about the authenticated user.
GET /userinfo
Auth: Bearer token (access token)
curl https://auth.solidus.network/userinfo \
-H "Authorization: Bearer eyJhbGciOiJFZERTQSIs..."// Response 200
{
"sub": "did:solidus:testnet:7Hk3mRtQZvXp2nBw9Lj4K",
"name": "John Doe",
"email": "[email protected]",
"email_verified": true,
"did": "did:solidus:testnet:7Hk3mRtQZvXp2nBw9Lj4K",
"updated_at": 1746619200
}The sub claim is always the user’s DID. Additional claims depend on the scopes requested during authorization:
| Scope | Claims |
|---|---|
openid | sub |
profile | name, updated_at |
email | email, email_verified |
did | did |
Token Introspection
Introspect Token
Check whether an access token or refresh token is active and retrieve its metadata.
POST /introspect
Auth: Client credentials (via body or Basic auth)
Content-Type: application/x-www-form-urlencoded
curl -X POST https://auth.solidus.network/introspect \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "token=eyJhbGciOiJFZERTQSIs..." \
-d "client_id=solidus-identity" \
-d "client_secret=cs_live_abc123def456..."// Response 200 — active token
{
"active": true,
"sub": "did:solidus:testnet:7Hk3mRtQZvXp2nBw9Lj4K",
"client_id": "solidus-identity",
"scope": "openid profile email did",
"token_type": "Bearer",
"exp": 1746622800,
"iat": 1746619200,
"iss": "https://auth.solidus.network"
}// Response 200 — inactive token
{
"active": false
}Token Revocation
Revoke Token
Revoke an access token or refresh token. Revoking a refresh token also invalidates all access tokens issued from it.
POST /revoke
Auth: Client credentials (via body or Basic auth)
Content-Type: application/x-www-form-urlencoded
curl -X POST https://auth.solidus.network/revoke \
-H "Content-Type: application/x-www-form-urlencoded" \
-d "token=rt_7Hk3mRtQZvXp2nBw9Lj4K..." \
-d "client_id=solidus-identity" \
-d "client_secret=cs_live_abc123def456..."// Response 200
{
"message": "Token revoked"
}The endpoint always returns 200, even if the token was already revoked or invalid, per RFC 7009.
ID Token Structure
ID tokens are signed with EdDSA (Ed25519) and contain standard OIDC claims plus Solidus-specific claims.
// Decoded ID token payload
{
"iss": "https://auth.solidus.network",
"sub": "did:solidus:testnet:7Hk3mRtQZvXp2nBw9Lj4K",
"aud": "solidus-identity",
"exp": 1746622800,
"iat": 1746619200,
"nonce": "n-0S6_WzA2Mj",
"name": "John Doe",
"email": "[email protected]",
"email_verified": true,
"did": "did:solidus:testnet:7Hk3mRtQZvXp2nBw9Lj4K"
}Verify ID tokens using the public keys from the JWKS endpoint. The alg header is always EdDSA and the kid header identifies which key was used.