@udibo/oauth2 0.4.1 → 0.5.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (159) hide show
  1. package/README.md +3 -3
  2. package/SECURITY.md +0 -4
  3. package/esm/adapters/hono/_common.d.ts +10 -13
  4. package/esm/adapters/hono/_common.js +11 -20
  5. package/esm/adapters/hono/authorization-server.d.ts +16 -10
  6. package/esm/adapters/hono/authorization-server.js +13 -8
  7. package/esm/adapters/hono/bff/auth-request-store.d.ts +4 -0
  8. package/esm/adapters/hono/bff/auth-request-store.js +4 -0
  9. package/esm/adapters/hono/bff/bff.d.ts +29 -18
  10. package/esm/adapters/hono/bff/bff.js +15 -11
  11. package/esm/adapters/hono/bff/proxy.js +7 -55
  12. package/esm/adapters/hono/bff/session-store.d.ts +9 -9
  13. package/esm/adapters/hono/bff/session-store.js +3 -2
  14. package/esm/adapters/hono/bff/testing.d.ts +14 -3
  15. package/esm/adapters/hono/bff/testing.js +14 -3
  16. package/esm/adapters/hono/identity.d.ts +5 -3
  17. package/esm/adapters/hono/identity.js +1 -17
  18. package/esm/adapters/hono/resource-server.d.ts +3 -2
  19. package/esm/adapters/hono/resource-server.js +3 -2
  20. package/esm/client/_http.d.ts +4 -7
  21. package/esm/client/_http.js +4 -37
  22. package/esm/client/base.d.ts +3 -6
  23. package/esm/client/bff-client.d.ts +7 -6
  24. package/esm/client/bff-client.js +7 -6
  25. package/esm/client/browser-storage.d.ts +33 -34
  26. package/esm/client/browser-storage.js +47 -32
  27. package/esm/client/check.d.ts +10 -3
  28. package/esm/client/check.js +28 -8
  29. package/esm/client/direct-client.d.ts +49 -29
  30. package/esm/client/direct-client.js +59 -59
  31. package/esm/client/discovery-cache.d.ts +12 -5
  32. package/esm/client/discovery-cache.js +11 -4
  33. package/esm/client/events.d.ts +11 -3
  34. package/esm/client/events.js +1 -1
  35. package/esm/client/mod.d.ts +6 -4
  36. package/esm/client/mod.js +5 -3
  37. package/esm/client/storage.d.ts +53 -23
  38. package/esm/client/storage.js +43 -15
  39. package/esm/errors.d.ts +15 -12
  40. package/esm/errors.js +12 -8
  41. package/esm/identity/delivery.d.ts +7 -7
  42. package/esm/identity/delivery.js +1 -2
  43. package/esm/identity/errors.d.ts +10 -4
  44. package/esm/identity/errors.js +4 -1
  45. package/esm/identity/events.d.ts +21 -5
  46. package/esm/identity/events.js +4 -2
  47. package/esm/identity/external/_shared.d.ts +5 -7
  48. package/esm/identity/external/_shared.js +5 -7
  49. package/esm/identity/external/_token-exchange.d.ts +3 -6
  50. package/esm/identity/external/_token-exchange.js +2 -5
  51. package/esm/identity/external/apple-client-secret.d.ts +13 -8
  52. package/esm/identity/external/apple-client-secret.js +9 -6
  53. package/esm/identity/external/apple.d.ts +17 -10
  54. package/esm/identity/external/apple.js +12 -9
  55. package/esm/identity/external/discord.d.ts +5 -1
  56. package/esm/identity/external/errors.d.ts +6 -2
  57. package/esm/identity/external/errors.js +6 -2
  58. package/esm/identity/external/flow.d.ts +9 -6
  59. package/esm/identity/external/flow.js +6 -5
  60. package/esm/identity/external/github.d.ts +7 -3
  61. package/esm/identity/external/github.js +2 -2
  62. package/esm/identity/external/google.d.ts +5 -1
  63. package/esm/identity/external/oauth2.d.ts +13 -2
  64. package/esm/identity/external/oauth2.js +3 -3
  65. package/esm/identity/external/oidc.d.ts +21 -10
  66. package/esm/identity/external/oidc.js +11 -6
  67. package/esm/identity/external/provider.d.ts +4 -2
  68. package/esm/identity/identifier.d.ts +6 -5
  69. package/esm/identity/identifier.js +6 -5
  70. package/esm/identity/lockout.d.ts +4 -3
  71. package/esm/identity/lockout.js +4 -3
  72. package/esm/identity/mfa/mod.d.ts +2 -1
  73. package/esm/identity/mfa/mod.js +2 -1
  74. package/esm/identity/mfa/recovery-codes.d.ts +2 -1
  75. package/esm/identity/mfa/service.d.ts +29 -11
  76. package/esm/identity/mfa/service.js +35 -11
  77. package/esm/identity/mfa/totp.d.ts +4 -2
  78. package/esm/identity/mfa/totp.js +4 -2
  79. package/esm/identity/migration.d.ts +8 -7
  80. package/esm/identity/migration.js +9 -12
  81. package/esm/identity/mod.d.ts +2 -2
  82. package/esm/identity/mod.js +2 -2
  83. package/esm/identity/otp.d.ts +23 -16
  84. package/esm/identity/otp.js +13 -12
  85. package/esm/identity/password-policy.d.ts +3 -3
  86. package/esm/identity/password-policy.js +3 -3
  87. package/esm/identity/password.d.ts +23 -20
  88. package/esm/identity/password.js +15 -16
  89. package/esm/identity/rate-limit.d.ts +1 -7
  90. package/esm/identity/rate-limit.js +1 -2
  91. package/esm/identity/service.d.ts +76 -44
  92. package/esm/identity/service.js +86 -60
  93. package/esm/identity/session.d.ts +5 -4
  94. package/esm/identity/session.js +5 -4
  95. package/esm/identity/token-flow.d.ts +8 -8
  96. package/esm/identity/token-flow.js +5 -6
  97. package/esm/models/client.d.ts +7 -4
  98. package/esm/models/token.d.ts +2 -3
  99. package/esm/react/callback.d.ts +3 -3
  100. package/esm/react/callback.js +3 -3
  101. package/esm/react/components/class-names.d.ts +3 -6
  102. package/esm/react/components/class-names.js +3 -6
  103. package/esm/react/components/internal.d.ts +7 -17
  104. package/esm/react/components/internal.js +7 -17
  105. package/esm/react/components/mod.d.ts +7 -5
  106. package/esm/react/components/mod.js +7 -5
  107. package/esm/react/components/types.d.ts +8 -6
  108. package/esm/react/context.d.ts +3 -3
  109. package/esm/react/provider.d.ts +3 -2
  110. package/esm/react/provider.js +0 -13
  111. package/esm/react/require-auth.d.ts +0 -3
  112. package/esm/react/require-auth.js +0 -3
  113. package/esm/react/testing.d.ts +3 -2
  114. package/esm/react/testing.js +3 -3
  115. package/esm/react/use-oauth2.d.ts +1 -1
  116. package/esm/server/authorization-server.d.ts +81 -54
  117. package/esm/server/authorization-server.js +76 -100
  118. package/esm/server/grants/authorization-code.d.ts +7 -3
  119. package/esm/server/grants/authorization-code.js +6 -2
  120. package/esm/server/grants/device-authorization.d.ts +1 -1
  121. package/esm/server/grants/grant.d.ts +15 -8
  122. package/esm/server/grants/grant.js +26 -18
  123. package/esm/server/grants/password.d.ts +1 -1
  124. package/esm/server/grants/refresh-token.d.ts +6 -3
  125. package/esm/server/grants/refresh-token.js +4 -3
  126. package/esm/server/introspection-token-reader.d.ts +16 -7
  127. package/esm/server/introspection-token-reader.js +9 -3
  128. package/esm/server/jwks-token-reader.d.ts +3 -3
  129. package/esm/server/jwks-token-reader.js +3 -3
  130. package/esm/server/redirect-uri.d.ts +6 -9
  131. package/esm/server/redirect-uri.js +7 -34
  132. package/esm/server/resource-server.d.ts +5 -3
  133. package/esm/server/resource-server.js +5 -3
  134. package/esm/server/services/client.d.ts +5 -1
  135. package/esm/server/services/device-authorization.d.ts +6 -6
  136. package/esm/server/services/token.d.ts +15 -8
  137. package/esm/server/services/token.js +1 -1
  138. package/esm/server/signing-keys.d.ts +24 -9
  139. package/esm/server/signing-keys.js +20 -9
  140. package/esm/testing/contract/mod.d.ts +3 -3
  141. package/esm/testing/contract/mod.js +3 -3
  142. package/esm/testing/mod.d.ts +4 -2
  143. package/esm/testing/mod.js +4 -2
  144. package/esm/testing/services.d.ts +1 -1
  145. package/esm/testing/services.js +1 -1
  146. package/esm/testing/tenant.d.ts +13 -4
  147. package/esm/utils/_buffer.d.ts +3 -2
  148. package/esm/utils/_buffer.js +3 -2
  149. package/esm/utils/_timing-safe.d.ts +8 -6
  150. package/esm/utils/_timing-safe.js +8 -6
  151. package/esm/utils/basic-auth.d.ts +5 -12
  152. package/esm/utils/basic-auth.js +5 -12
  153. package/esm/utils/crypto.d.ts +2 -1
  154. package/esm/utils/crypto.js +2 -1
  155. package/esm/utils/text.d.ts +2 -9
  156. package/esm/utils/text.js +2 -9
  157. package/esm/utils/url.d.ts +2 -2
  158. package/esm/utils/url.js +0 -2
  159. package/package.json +1 -1
@@ -37,14 +37,18 @@ export interface EndSessionContext<Client extends ClientInterface> {
37
37
  /** The logout request itself. */
38
38
  request: Request;
39
39
  /**
40
- * The relying party the logout names — from a signature-valid
41
- * `id_token_hint`'s audience, or from `client_id`. Null when the request
42
- * named none, or named one this server does not know.
40
+ * The relying party the logout names — from `client_id`, else from the first
41
+ * audience of a signature-valid `id_token_hint`. When the request sends
42
+ * both, `client_id` must be one of the hint's audiences (OIDC RP-Initiated
43
+ * Logout 1.0 §2); a mismatch is a 400 `invalid_request` and this callback
44
+ * never runs. Null when the request named none, or named one this server
45
+ * does not know.
43
46
  */
44
47
  client: Client | null;
45
48
  /**
46
- * The `sub` of a signature-valid `id_token_hint`. Null when the request sent
47
- * no hint, or one that did not verify — so a session lookup keyed on it must
49
+ * The `sub` of an `id_token_hint` that verifies against the current signing
50
+ * key. Null when the request sent no hint, or one that did not verify
51
+ * (including one signed by a key since rotated out of signing) — so a session lookup keyed on it must
48
52
  * handle "no subject", which is the ordinary case for a client that never
49
53
  * requested `openid`.
50
54
  */
@@ -77,7 +81,8 @@ export interface EndSessionResult {
77
81
  * request that reaches the endpoint, including ones whose parameters do not
78
82
  * check out — refusing to end a session because a *redirect* was unauthorized
79
83
  * would leave the person signed in, which is the opposite of what they asked
80
- * for.
84
+ * for. The one request that never reaches it is a self-contradictory one: a
85
+ * `client_id` that is not an audience of the `id_token_hint` it came with.
81
86
  */
82
87
  export type EndSessionFn<Client extends ClientInterface> = (context: EndSessionContext<Client>) => EndSessionResult | void | Promise<EndSessionResult | void>;
83
88
  /** Grants configuration for the authorization server. */
@@ -156,7 +161,7 @@ export interface AuthorizationServerOptions<Client extends ClientInterface, User
156
161
  * the token endpoint mints an `id_token` for user-bound grants with the
157
162
  * `openid` scope, and the JWKS/UserInfo endpoints and
158
163
  * `openid-configuration` metadata go live. In multi-instance deploys load
159
- * one persisted key on every instance (see `signing-keys.ts`).
164
+ * one persisted key on every instance (see `importSigningKeyJwk`).
160
165
  */
161
166
  signingKeys?: SigningKeyProvider;
162
167
  /**
@@ -190,8 +195,9 @@ export interface AuthorizationServerOptions<Client extends ClientInterface, User
190
195
  /**
191
196
  * Extra OIDC claims for the id_token and UserInfo response (e.g. `name`,
192
197
  * `email` when the scope allows). Merged under the protocol claims — `sub`
193
- * (from `subjectOf`) and the id_token's `iss`/`aud`/`iat`/`exp`/`nonce`
194
- * always win.
198
+ * (from `subjectOf`) and the id_token's `iss`/`aud`/`iat`/`exp` always win,
199
+ * and `nonce` is the authorization request's own: present exactly when that
200
+ * request carried one, whatever is returned here.
195
201
  * The third argument is this credential's recorded authentication event,
196
202
  * including on refresh and UserInfo. Return its fields to emit them; never
197
203
  * substitute a user's newer session event. It is absent for legacy records.
@@ -202,9 +208,13 @@ export interface AuthorizationServerOptions<Client extends ClientInterface, User
202
208
  * permits them), so a resource server validating by introspection sees the
203
209
  * same authorization claims a JWT access token carries — feed it the same
204
210
  * computation `userClaims` uses and the two validation strategies stay in
205
- * field-level parity. Called with the introspected token; the RFC 7662
206
- * protocol fields (`active`, `scope`, `client_id`, `token_type`, `exp`,
207
- * `iss`, `sub`, `username`) always win over anything it returns.
211
+ * field-level parity. Called with the introspected token. Each RFC 7662
212
+ * protocol field the server sets (`active`, `scope`, `client_id`,
213
+ * `token_type`, `exp`, `iss`, `sub`, `username`) wins over anything it
214
+ * returns. One the server leaves unset is not stripped — a `scope` for an
215
+ * unscoped token reaches the response — except `sub` and `username`, which
216
+ * are dropped for a token with no user so that their presence keeps meaning
217
+ * "there is a resource owner" (RFC 9700 §4.15.1).
208
218
  */
209
219
  introspectionClaims?: (token: Token<Client, User, S>) => Promise<Record<string, unknown>> | Record<string, unknown>;
210
220
  /**
@@ -246,8 +256,9 @@ export interface AuthorizationServerOptions<Client extends ClientInterface, User
246
256
  *
247
257
  * - `{ user, authorizedScope?, authenticationContext? }` — user is authenticated; the authorize flow
248
258
  * continues. `authorizedScope` declares scopes the user has already
249
- * pre-authorized for this client; anything in the requested scope not
250
- * covered by it triggers consent. **Omitting `authorizedScope` means
259
+ * pre-authorized for this client; consent is needed unless it covers the
260
+ * whole accepted scope (the requested scope after the token service's
261
+ * `acceptedScope`). **Omitting `authorizedScope` means
251
262
  * "nothing pre-authorized"** — so any requested scope needs consent: the
252
263
  * framework calls `handleConsent` when one is configured, and otherwise
253
264
  * treats the request as consented and grants the accepted scope. To
@@ -272,8 +283,9 @@ export type AuthenticateUserFn<User> = (request: Request) => Promise<{
272
283
  * Called when the requested scope is not already covered by the user's
273
284
  * pre-authorized scope. Return one of:
274
285
  *
275
- * - `{ approved: true, scope? }` — consent granted. `scope` optionally
276
- * narrows the granted scope (RFC 6749 §3.3 allows partial grants).
286
+ * - `{ approved: true, scope? }` — consent granted. `scope`, when set,
287
+ * replaces the granted scope (RFC 6749 §3.3 allows partial grants). The
288
+ * server does not check it against the requested scope, so return a subset.
277
289
  * - `{ approved: false }` — consent denied. The framework redirects to
278
290
  * `redirect_uri` with `error=access_denied`.
279
291
  * - A `Response` — short-circuits the rest of the authorize flow and is
@@ -304,8 +316,8 @@ export interface ResolvedEndpoints {
304
316
  endSession?: string;
305
317
  }
306
318
  /**
307
- * Every endpoint the authorization server serves, by name — the seven it
308
- * advertises in its metadata (the {@link ResolvedEndpoints} keys) plus
319
+ * Every endpoint the authorization server serves, by name — the eight it can
320
+ * advertise in its metadata (the {@link ResolvedEndpoints} keys) plus
309
321
  * `metadata` and `oidcMetadata`, the two discovery documents that are served
310
322
  * but never advertised. Index {@link ENDPOINT_PATHS} and
311
323
  * {@link ENDPOINT_METHODS} with it to enumerate the whole surface.
@@ -317,7 +329,7 @@ export type EndpointKey = "authorization" | "token" | "revocation" | "introspect
317
329
  * these paths — as the Hono adapter's `routes()` does — to match what the
318
330
  * server advertises in its RFC 8414 metadata.
319
331
  *
320
- * Covers the whole served surface: the seven endpoints the server advertises,
332
+ * Covers the whole served surface: the eight endpoints the server can advertise,
321
333
  * plus the two discovery documents (`metadata` for RFC 8414,
322
334
  * `oidcMetadata` for OIDC Discovery) that are served but never advertised.
323
335
  * Pair it with {@link ENDPOINT_METHODS} to enumerate path *and* verbs.
@@ -333,7 +345,7 @@ export declare const ENDPOINT_PATHS: Readonly<Record<EndpointKey, string>>;
333
345
  /**
334
346
  * The HTTP methods each endpoint in {@link ENDPOINT_PATHS} answers — `POST` for
335
347
  * the token-style endpoints, `GET` for authorize/JWKS/discovery, both for
336
- * UserInfo. Read it instead of re-deriving verbs per endpoint, so a hand-rolled
348
+ * UserInfo and end-session. Read it instead of re-deriving verbs per endpoint, so a hand-rolled
337
349
  * mount answers exactly what the built-in `routes()` does.
338
350
  *
339
351
  * @example
@@ -352,6 +364,7 @@ export declare const ENDPOINT_METHODS: Readonly<Record<EndpointKey, readonly str
352
364
  * - Introspection endpoint (POST /introspect) - RFC 7662
353
365
  * - Device authorization endpoint (POST /device_authorization) - RFC 8628
354
366
  * - Metadata endpoint (GET /.well-known/oauth-authorization-server) - RFC 8414
367
+ * - OIDC discovery, JWKS, UserInfo, and end-session endpoints, when configured
355
368
  *
356
369
  * Framework-agnostic: each `handle*Request` method takes a web `Request` and
357
370
  * returns a `Response`, so an adapter routes its endpoints to them. Extends
@@ -424,19 +437,12 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
424
437
  * (`grant.issuesIdToken !== false`).
425
438
  */
426
439
  createTokenResponse(token: Token<Client, User, S>, context: AuthorizationServerContext<Client, User, S>, grant?: DispatchableGrant<Client, User, S>): Promise<Response>;
427
- /**
428
- * Applies `Cache-Control: no-store` and `Pragma: no-cache` headers to an
429
- * error per RFC 6749 Section 5.2. The headers land on both the rethrown
430
- * error (when {@link throwOnError} is true) and the generated response.
431
- */
440
+ /** Sets the RFC 6749 §5.2 `no-store` cache headers on an error. */
432
441
  private addCacheHeaders;
433
442
  /**
434
- * Error-prepare callback for the endpoints that authenticate the client
435
- * (token, revocation, introspection, device authorization). Attaches the
436
- * RFC 6749 Section 5.2 cache headers, and — when client authentication was
437
- * attempted via the `Authorization` header and failed with a 401 — the
438
- * matching `WWW-Authenticate: Basic` challenge that RFC 6749 Section 5.2
439
- * requires.
443
+ * Error-prepare callback for client-authenticated endpoints: cache headers,
444
+ * plus the RFC 6749 §5.2 `WWW-Authenticate: Basic` challenge on a 401 when
445
+ * the request sent an `Authorization` header.
440
446
  */
441
447
  private prepareClientAuthError;
442
448
  /**
@@ -444,14 +450,18 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
444
450
  * Supports multiple grant types based on the configured grants.
445
451
  *
446
452
  * A malformed request — wrong method, a content-type other than
447
- * `application/x-www-form-urlencoded`, or an unsupported grant — is a 400
448
- * `invalid_request`.
453
+ * `application/x-www-form-urlencoded`, or no `grant_type` — is a 400
454
+ * `invalid_request`. A `grant_type` with no registered grant is
455
+ * `unsupported_grant_type`, checked before client authentication; a client
456
+ * not registered for the grant is `unauthorized_client`.
449
457
  */
450
458
  handleTokenRequest(request: Request): Promise<Response>;
451
459
  /**
452
460
  * Mint an OIDC id_token for a user-bound token whose scope includes
453
461
  * `openid`, or `undefined` when the OIDC surface is off (no signing keys),
454
462
  * the token has no user, the scope lacks `openid`, or no issuer resolved.
463
+ * The id_token's `aud` is the client id and it expires one hour after
464
+ * issue.
455
465
  */
456
466
  mintIdToken(token: Token<Client, User, S>, context: AuthorizationServerContext<Client, User, S>): Promise<string | undefined>;
457
467
  /**
@@ -488,8 +498,12 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
488
498
  * `endSession` does the ending and this method does the protocol around it:
489
499
  * identifying the relying party, authorizing the return trip, and shaping
490
500
  * the response. `endSession` is always called, even when nothing else about
491
- * the request checks out, because a logout that refuses to log anyone out is
492
- * the worst possible failure mode for this endpoint.
501
+ * the client, hint, or redirect checks out, because a logout that refuses to
502
+ * log anyone out is the worst possible failure mode for this endpoint. The
503
+ * sole exception is a `client_id` that is not among the audiences of a
504
+ * verified `id_token_hint` sent with it: OIDC RP-Initiated Logout 1.0 §2
505
+ * requires the two to agree, so that request is a 400 `invalid_request`
506
+ * and ends no session.
493
507
  *
494
508
  * **Authorizing `post_logout_redirect_uri` is the whole security surface.**
495
509
  * It is matched by **exact string** against the resolved client's
@@ -501,11 +515,14 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
501
515
  * registered, the browser is **not** sent there — it goes to `fallback` if
502
516
  * the app supplied one, or gets a bare 204.
503
517
  *
504
- * `id_token_hint` is verified against the signing keys but its expiry is
505
- * ignored: by the time anyone logs out the id_token naming their session has
506
- * usually expired, and it is a hint, not authority. `client_id` is accepted
507
- * as the fallback identifier the spec allows. `state` rides along only to a
508
- * URI that passed authorization.
518
+ * `id_token_hint` is verified against the current signing key only — a hint
519
+ * signed by a key since rotated out of signing yields no subject — and its
520
+ * expiry is ignored: by the time anyone logs out the id_token naming their
521
+ * session has usually expired, and it is a hint, not authority. `client_id`,
522
+ * when sent, names the client ahead of the hint's audience, and when both
523
+ * are sent `client_id` must be one of the hint's audiences — a mismatch is
524
+ * a 400 `invalid_request` (OIDC RP-Initiated Logout 1.0 §2). `state` rides
525
+ * along only to a URI that passed authorization.
509
526
  *
510
527
  * Wire the app's session teardown through the `endSession` **constructor
511
528
  * option**; this method answers 404 without it, and the discovery document
@@ -529,18 +546,20 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
529
546
  /**
530
547
  * Parses authorization request parameters from the query string.
531
548
  *
532
- * The authorization endpoint is GET-only (RFC 6749 Section 3.1 requires GET
533
- * and only permits POST), so parameters are read from `url.searchParams`.
549
+ * Reads only `url.searchParams`: RFC 6749 Section 3.1 requires GET support
550
+ * and leaves POST optional, and this server serves the endpoint on GET.
534
551
  */
535
552
  parseAuthorizeParameters(request: Request): AuthorizeParameters;
536
553
  /**
537
554
  * Handles an authorization request (GET /authorize).
538
555
  * Used for the authorization code flow.
539
556
  *
540
- * Once the request has named a redirect URI the client registered, failures
541
- * are reported to that URI as an RFC 6749 Section 4.1.2.1 error redirect;
542
- * before that they are error responses from this endpoint, since there is no
543
- * verified place to send the user back to.
557
+ * Once a redirect target is verified — the requested `redirect_uri` matched
558
+ * a registration, or the request omitted it and the client has a literal
559
+ * registration, whose first entry is used — failures are reported to it as
560
+ * an RFC 6749 Section 4.1.2.1 error redirect; before that they are error
561
+ * responses from this endpoint, since there is no verified place to send the
562
+ * user back to.
544
563
  *
545
564
  * Requires a grant extending {@linkcode AuthorizationCodeGrant} registered
546
565
  * under `authorization_code`; without one the endpoint answers 500
@@ -608,8 +627,11 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
608
627
  * that field describes how an access token is presented, and its `exp` is
609
628
  * the refresh token's own expiry.
610
629
  *
611
- * A token with no user — the client acting as its own resource owner, as
612
- * the client credentials grant issues — carries no `sub` and no `username`;
630
+ * A token with a user carries `sub` from `subjectOf` — the same value the
631
+ * id_token and UserInfo carry — and `username` when the user has one. A
632
+ * token with no user — the client acting as its own resource owner, as the
633
+ * client credentials grant issues — carries neither, even when
634
+ * {@linkcode AuthorizationServerOptions.introspectionClaims} returns them;
613
635
  * `client_id` identifies the machine. `sub` is optional in RFC 7662, and
614
636
  * leaving it absent keeps `sub` an unambiguous "there is a resource owner"
615
637
  * signal rather than overloading `client_id` into the subject namespace
@@ -694,13 +716,18 @@ export declare class AuthorizationServer<Client extends ClientInterface, User, S
694
716
  * - `POST {revocationEndpoint}` → `handleRevocationRequest`
695
717
  * - `POST {introspectionEndpoint}` → `handleIntrospectionRequest`
696
718
  * - `POST {deviceAuthorizationEndpoint}` → `handleDeviceAuthorizationRequest`
697
- * - `GET /.well-known/oauth-authorization-server` → `handleMetadataRequest`
719
+ * - `GET {jwksEndpoint}` → `handleJwksRequest`
720
+ * - `GET`/`POST {userinfoEndpoint}` → `handleUserInfoRequest`
721
+ * - `GET /.well-known/oauth-authorization-server` → `handleMetadataRequest`
722
+ * - `GET /.well-known/openid-configuration` → `handleOidcMetadataRequest`
723
+ *
724
+ * The two discovery paths are matched literally, not against the issuer.
698
725
  *
699
- * The authorization endpoint is deliberately **not** routed: `/authorize`
700
- * needs an `authenticateUser` (and optional `handleConsent`) callback this
701
- * transport has no access to, and in real flows it's a browser navigation,
702
- * never a call through the client's `fetch`. A request to it throws an
703
- * actionable error pointing at `handleAuthorizeRequest`. Any other path also
726
+ * The authorization and end-session endpoints are deliberately **not**
727
+ * routed: in real flows both are browser navigations, never calls through the
728
+ * client's `fetch`, and `/authorize` needs an `authenticateUser` (and optional
729
+ * `handleConsent`) callback this transport has no access to. A request to
730
+ * either throws an error naming the handler to drive directly. Any other path also
704
731
  * throws — the helper intentionally does not proxy arbitrary paths; if a call
705
732
  * lands here unexpectedly, that's a wiring bug worth surfacing rather than
706
733
  * silently forwarding.