Catalyst-Plugin-OpenIDConnect
view release on metacpan or search on metacpan
API_REFERENCE.md view on Meta::CPAN
# OpenID Connect API Reference
Complete API documentation for the Catalyst::Plugin::OpenIDConnect endpoints.
## Base URL
```
http://localhost:5000
```
Replace with your actual issuer URL.
## Authentication Methods
- **Client Authentication**: Use `client_id` and `client_secret` in request body for token endpoint
- **Bearer Token**: Use `Authorization: Bearer <access_token>` header for protected resources
## Discovery Endpoint
### GET /.well-known/openid-configuration
Returns the OpenID Provider Configuration.
**Response:**
```json
{
"issuer": "http://localhost:5000",
"authorization_endpoint": "http://localhost:5000/openidconnect/authorize",
"token_endpoint": "http://localhost:5000/openidconnect/token",
"userinfo_endpoint": "http://localhost:5000/openidconnect/userinfo",
"jwks_uri": "http://localhost:5000/openidconnect/jwks",
"scopes_supported": ["openid", "profile", "email", "phone", "address"],
"response_types_supported": ["code", "id_token token"],
"response_modes_supported": ["query", "fragment", "form_post"],
"grant_types_supported": ["authorization_code", "refresh_token", "implicit"],
"subject_types_supported": ["public", "pairwise"],
"id_token_signing_alg_values_supported": ["RS256"],
"userinfo_signing_alg_values_supported": ["RS256"],
"claims_supported": [
"sub", "name", "given_name", "family_name", "email", "email_verified",
"picture", "phone_number", "updated_at"
],
"claim_types_supported": ["normal", "aggregated", "distributed"],
"request_parameter_supported": true,
"request_uri_parameter_supported": true
}
```
---
## Authorization Endpoint
### GET /openidconnect/authorize
Initiates an OpenID Connect authorization request.
**Parameters:**
| Parameter | Type | Required | Description |
|-----------|------|----------|-------------|
| response_type | string | Yes | Must be "code" |
| client_id | string | Yes | The client identifier |
| redirect_uri | string | Yes | Where to redirect after authorization |
| scope | string | No | Space-separated scopes (default: "openid") |
| state | string | Recommended | CSRF protection state value |
| nonce | string | No | Session binding nonce (client validates it matches auth request) |
| code_challenge | string | Conditional | PKCE challenge value (RFC 7636). **Required for public clients** (those without a `client_secret`). Strongly recommended for all clients. Value is `BASE64URL(SHA256(ASCII(code_verifier)))`. |
| code_challenge_method | string | Conditional | Must be `S256` when `code_challenge` is provided. `plain` is not supported. |
| prompt | string | No | "login" to force re-authentication |
| max_age | integer | No | Maximum age of authentication (seconds) |
| ui_locales | string | No | Preferred UI locales |
| id_token_hint | string | No | Preferred user identity |
| login_hint | string | No | Hint for login (e.g., email) |
| acr_values | string | No | Authentication context class references |
**Example Request:**
```
GET /openidconnect/authorize?
response_type=code&
client_id=my-app&
redirect_uri=https://app.example.com/callback&
scope=openid%20profile%20email&
state=xyz789&
nonce=n-0S6_WzA2Mj
```
**Successful Response (Redirect):**
```
API_REFERENCE.md view on Meta::CPAN
post-logout redirect URIs in the server configuration:
```
# catalyst.conf (Apache-style)
<clients>
<my-app>
post_logout_redirect_uris = https://app.example.com/logged-out
</my-app>
</clients>
```
```perl
# Perl hash config
clients => {
'my-app' => {
post_logout_redirect_uris => [
'https://app.example.com/logged-out',
],
},
},
```
---
## JWT Token Format
### ID Token Structure
ID tokens are signed JWTs containing user claims. They have three parts separated by dots:
```
header.payload.signature
```
**Header:**
```json
{
"alg": "RS256",
"typ": "JWT",
"kid": "example-key-1"
}
```
**Payload (Claims):**
```json
{
"iss": "http://localhost:5000",
"sub": "24400320",
"aud": "my-app",
"nonce": "n-0S6_WzA2Mj",
"exp": 1311281970,
"iat": 1311280970,
"name": "Jane Doe",
"email": "janedoe@example.com",
"email_verified": true
}
```
**Verification:**
1. Verify the signature using the public key from the JWKS endpoint
2. Verify `iss` matches expected issuer
3. Verify `aud` contains your client ID
4. Verify `exp` is in the future
5. Verify `nonce` matches the one sent in authorization request
---
## Standard Claims Reference
The UserInfo endpoint and ID token may include these standard claims:
### Profile Claims
- `sub` - Unique subject identifier
- `name` - Full name
- `given_name` - Given (first) name
- `family_name` - Family (last) name
- `middle_name` - Middle name
- `nickname` - Nickname
- `preferred_username` - Preferred username
- `profile` - Profile URL
- `picture` - Picture/avatar URL
- `website` - Website URL
- `gender` - Gender (male, female, other)
- `birthdate` - Birth date (YYYY-MM-DD)
- `zoneinfo` - Timezone (IANA tz string)
- `locale` - Locale/language (BCP47 tag)
- `updated_at` - Profile update time (Unix timestamp)
### Email Claims
- `email` - Email address
- `email_verified` - Whether mail is verified (boolean)
### Phone Claims
- `phone_number` - Phone number (E.164 format)
- `phone_number_verified` - Whether phone verified (boolean)
### Address Claims
- `address` - Physical address (JSON object)
---
## Scopes
### Supported Scopes
| Scope | Description |
|-------|-------------|
| openid | Basic OpenID Connect (required) |
| profile | Name, picture, birthdate, etc. |
| email | Email and email_verified claims |
| phone | Phone number claims |
| address | Physical address claims |
---
## HTTP Status Codes
| Code | Meaning |
|------|---------|
| 200 | Success |
| 302 | Redirect (authorization code response) |
| 400 | Bad request (invalid parameters) |
| 401 | Unauthorized (invalid/missing token) |
| 500 | Server error |
---
## Rate Limiting
Currently not implemented. Production deployments should add rate limiting.
( run in 1.145 second using v1.01-cache-2.11-cpan-9581c071862 )