@dereekb/firebase-server 13.11.3 → 13.11.4

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.
package/oidc/package.json CHANGED
@@ -1,16 +1,16 @@
1
1
  {
2
2
  "name": "@dereekb/firebase-server/oidc",
3
- "version": "13.11.3",
3
+ "version": "13.11.4",
4
4
  "peerDependencies": {
5
- "@dereekb/analytics": "13.11.3",
6
- "@dereekb/date": "13.11.3",
7
- "@dereekb/firebase": "13.11.3",
8
- "@dereekb/firebase-server": "13.11.3",
9
- "@dereekb/model": "13.11.3",
10
- "@dereekb/nestjs": "13.11.3",
11
- "@dereekb/rxjs": "13.11.3",
12
- "@dereekb/util": "13.11.3",
13
- "@dereekb/zoho": "13.11.3",
5
+ "@dereekb/analytics": "13.11.4",
6
+ "@dereekb/date": "13.11.4",
7
+ "@dereekb/firebase": "13.11.4",
8
+ "@dereekb/firebase-server": "13.11.4",
9
+ "@dereekb/model": "13.11.4",
10
+ "@dereekb/nestjs": "13.11.4",
11
+ "@dereekb/rxjs": "13.11.4",
12
+ "@dereekb/util": "13.11.4",
13
+ "@dereekb/zoho": "13.11.4",
14
14
  "@nestjs/common": "^11.1.19",
15
15
  "@nestjs/config": "^4.0.4",
16
16
  "express": "^5.2.1",
@@ -3,6 +3,7 @@ import { OidcProviderConfigService } from '../service';
3
3
  import { type OAuthInteractionConsentRequest, type OAuthInteractionLoginRequest, type OidcInteractionUid } from '@dereekb/firebase';
4
4
  import { OidcAccountService } from '../service/oidc.account.service';
5
5
  import { OidcInteractionService } from '../service/oidc.interaction.service';
6
+ import { OidcService } from '../service/oidc.service';
6
7
  /**
7
8
  * Controller for OIDC interaction endpoints (login/consent).
8
9
  *
@@ -17,7 +18,8 @@ export declare class OidcInteractionController {
17
18
  private readonly oidcInteractionService;
18
19
  private readonly oidcProviderConfigService;
19
20
  private readonly accountService;
20
- constructor(oidcInteractionService: OidcInteractionService, oidcProviderConfigService: OidcProviderConfigService, accountService: OidcAccountService);
21
+ private readonly oidcService;
22
+ constructor(oidcInteractionService: OidcInteractionService, oidcProviderConfigService: OidcProviderConfigService, accountService: OidcAccountService, oidcService: OidcService);
21
23
  /**
22
24
  * GET /interaction/:uid
23
25
  *
@@ -1,6 +1,7 @@
1
- import { type AsyncFirebaseFunctionCreateAction, type AsyncOidcEntryUpdateAction, type AsyncOidcEntryDeleteAction, type CreateOidcClientParams, type CreateOidcClientResult, type UpdateOidcClientParams, type DeleteOidcClientParams, type RotateOidcClientSecretParams, type RotateOidcClientSecretResult, type OidcEntryDocument } from '@dereekb/firebase';
1
+ import { type AsyncFirebaseFunctionCreateAction, type AsyncOidcEntryUpdateAction, type AsyncOidcEntryDeleteAction, type CreateOidcClientParams, type CreateOidcClientResult, type UpdateOidcClientParams, type DeleteOidcClientParams, type DeleteOidcTokenParams, type RotateOidcClientSecretParams, type RotateOidcClientSecretResult, type OidcEntryDocument } from '@dereekb/firebase';
2
2
  import { type FirebaseServerActionsContext } from '@dereekb/firebase-server';
3
3
  import { type OidcClientService } from '../../service/oidc.client.service';
4
+ import { type OidcService } from '../../service/oidc.service';
4
5
  /**
5
6
  * Context providing the OIDC client service and server action utilities needed by OIDC model server actions.
6
7
  */
@@ -9,6 +10,10 @@ export interface OidcModelServerActionsContext extends FirebaseServerActionsCont
9
10
  * Service for managing OIDC client adapter entries.
10
11
  */
11
12
  readonly oidcClientService: OidcClientService;
13
+ /**
14
+ * Core OIDC service used for grant revocation.
15
+ */
16
+ readonly oidcService: OidcService;
12
17
  }
13
18
  /**
14
19
  * Abstract service class defining all server-side OIDC client CRUD actions.
@@ -20,6 +25,7 @@ export declare abstract class OidcModelServerActions {
20
25
  abstract updateOidcClient(params: UpdateOidcClientParams): AsyncOidcEntryUpdateAction<UpdateOidcClientParams>;
21
26
  abstract rotateOidcClientSecret(params: RotateOidcClientSecretParams): AsyncFirebaseFunctionCreateAction<RotateOidcClientSecretParams, RotateOidcClientSecretResult, OidcEntryDocument>;
22
27
  abstract deleteOidcClient(params: DeleteOidcClientParams): AsyncOidcEntryDeleteAction<DeleteOidcClientParams>;
28
+ abstract deleteOidcToken(params: DeleteOidcTokenParams): AsyncOidcEntryDeleteAction<DeleteOidcTokenParams>;
23
29
  }
24
30
  /**
25
31
  * Creates a concrete {@link OidcModelServerActions} implementation wired to the provided context.
@@ -73,3 +79,18 @@ export declare function rotateOidcClientSecretFactory(context: OidcModelServerAc
73
79
  * @returns a transform function factory for deleting OIDC clients
74
80
  */
75
81
  export declare function deleteOidcClientFactory(context: OidcModelServerActionsContext): import("@dereekb/model").TransformAndValidateFunctionResultFunction<import("@dereekb/firebase").TargetModelParams, (document: OidcEntryDocument) => Promise<void>, object, unknown>;
82
+ /**
83
+ * Factory for the `deleteOidcToken` action.
84
+ *
85
+ * Asserts the target {@link OidcEntryDocument} is of type `Grant`, then delegates to
86
+ * {@link OidcService.revokeGrant} so all grantable token entries (`AccessToken`,
87
+ * `RefreshToken`, `AuthorizationCode`, `DeviceCode`, `BackchannelAuthenticationRequest`)
88
+ * sharing the grant id are deleted along with the Grant entry itself.
89
+ *
90
+ * Per-user authorization (this user owns this Grant) is enforced upstream via the
91
+ * model permission service before this action runs.
92
+ *
93
+ * @param context - the OIDC model server actions context
94
+ * @returns a transform function factory for revoking OIDC grants
95
+ */
96
+ export declare function deleteOidcTokenFactory(context: OidcModelServerActionsContext): import("@dereekb/model").TransformAndValidateFunctionResultFunction<import("@dereekb/firebase").TargetModelParams, (document: OidcEntryDocument) => Promise<void>, object, unknown>;
@@ -1,17 +1,20 @@
1
1
  import { type ModuleMetadata } from '@nestjs/common';
2
2
  import { OidcModelServerActions } from './oidcmodel.action.server';
3
3
  import { OidcClientService } from '../../service/oidc.client.service';
4
+ import { OidcService } from '../../service/oidc.service';
4
5
  /**
5
- * Factory that creates an {@link OidcModelServerActions} instance from the injected {@link OidcClientService}.
6
+ * Factory that creates an {@link OidcModelServerActions} instance from the injected services.
6
7
  *
7
- * @param oidcClientService - the OIDC client service to wire into the server actions
8
+ * @param oidcClientService - the OIDC client service for client CRUD actions
9
+ * @param oidcService - the core OIDC service for grant revocation
8
10
  * @returns the configured OidcModelServerActions instance
9
11
  */
10
- export declare function oidcModelServerActionsFactory(oidcClientService: OidcClientService): OidcModelServerActions;
12
+ export declare function oidcModelServerActionsFactory(oidcClientService: OidcClientService, oidcService: OidcService): OidcModelServerActions;
11
13
  export interface ProvideAppOidcModelMetadataConfig {
12
14
  /**
13
15
  * The OidcModule that exports the required OIDC dependencies:
14
16
  * - {@link OidcClientService}
17
+ * - {@link OidcService}
15
18
  */
16
19
  readonly oidcModule: Required<ModuleMetadata>['imports']['0'];
17
20
  }
@@ -1,5 +1,5 @@
1
1
  import type { Configuration } from 'oidc-provider';
2
- import { type WebsitePath, type SlashPath } from '@dereekb/util';
2
+ import { type WebsitePath, type SlashPath, type Seconds } from '@dereekb/util';
3
3
  import { type OidcScope, type OidcTokenEndpointAuthMethod } from '@dereekb/firebase';
4
4
  import { type JwksServiceConfig } from './service/oidc.jwks.service';
5
5
  import { type JwksKeyConverterConfig } from './model';
@@ -49,27 +49,51 @@ export interface OidcProviderConfig<S extends OidcScope = OidcScope> {
49
49
  }
50
50
  /**
51
51
  * Configures the lifetime (in seconds) for each token type issued by the OIDC provider.
52
+ *
53
+ * `session` and `grant` set the *default* TTLs; the effective values may be reduced when a
54
+ * client passes the `dbx_session_ttl` request param (see {@link OidcModuleConfig.maxRequestedLoginDuration}).
52
55
  */
53
56
  export interface OidcTokenLifetimes {
54
57
  /**
55
58
  * Access token lifetime in seconds. Defaults to 900 (15 min).
56
59
  */
57
- readonly accessToken: number;
60
+ readonly accessToken: Seconds;
58
61
  /**
59
62
  * ID token lifetime in seconds. Defaults to 3600 (1 hour).
60
63
  */
61
- readonly idToken: number;
64
+ readonly idToken: Seconds;
62
65
  /**
63
66
  * Refresh token lifetime in seconds (absolute). Defaults to 2592000 (30 days).
64
67
  */
65
- readonly refreshToken: number;
68
+ readonly refreshToken: Seconds;
66
69
  /**
67
70
  * Authorization code lifetime in seconds. Defaults to 60.
68
71
  */
69
- readonly authorizationCode: number;
72
+ readonly authorizationCode: Seconds;
73
+ /**
74
+ * Session lifetime in seconds. Defaults to 2592000 (30 days).
75
+ *
76
+ * Caps how long a user's authenticated session at the IdP lasts before re-authentication is required.
77
+ */
78
+ readonly session: Seconds;
79
+ /**
80
+ * Grant lifetime in seconds. Defaults to 2592000 (30 days).
81
+ *
82
+ * Caps how long a granted authorization (consent) lasts. Once the grant expires, refresh tokens
83
+ * issued under it stop working and the user must re-consent.
84
+ */
85
+ readonly grant: Seconds;
70
86
  }
71
87
  /**
72
- * Default token lifetimes: 15 min access tokens, 30-day refresh tokens, 60 s auth codes.
88
+ * Default global ceiling for a client-requested login duration, in seconds. 90 days.
89
+ */
90
+ export declare const DEFAULT_MAX_REQUESTED_LOGIN_DURATION_SECONDS: number;
91
+ /**
92
+ * Default global floor for a client-requested login duration, in seconds. 1 hour.
93
+ */
94
+ export declare const DEFAULT_MIN_REQUESTED_LOGIN_DURATION_SECONDS: number;
95
+ /**
96
+ * Default token lifetimes: 15 min access tokens, 30-day refresh tokens, 30-day sessions/grants, 60 s auth codes.
73
97
  */
74
98
  export declare const DEFAULT_OIDC_TOKEN_LIFETIMES: OidcTokenLifetimes;
75
99
  /**
@@ -108,6 +132,29 @@ export declare abstract class OidcModuleConfig {
108
132
  * Token lifetime configuration.
109
133
  */
110
134
  readonly tokenLifetimes: OidcTokenLifetimes;
135
+ /**
136
+ * Maximum login duration (seconds) a client may request via the `dbx_session_ttl` auth-URL param.
137
+ *
138
+ * Acts as the global server cap for any per-request duration. A registered client can declare its own
139
+ * lower ceiling via the `dbx_max_session_ttl` client metadata field; the effective ceiling is
140
+ * `min(client.dbx_max_session_ttl, this)`.
141
+ *
142
+ * Defaults to {@link DEFAULT_MAX_REQUESTED_LOGIN_DURATION_SECONDS} (90 days).
143
+ */
144
+ readonly maxRequestedLoginDuration?: number;
145
+ /**
146
+ * Minimum login duration (seconds) a client may request via the `dbx_session_ttl` auth-URL param.
147
+ *
148
+ * Requested values below this floor are clamped up. Prevents pathological 30-second sessions.
149
+ *
150
+ * Defaults to {@link DEFAULT_MIN_REQUESTED_LOGIN_DURATION_SECONDS} (1 hour).
151
+ */
152
+ readonly minRequestedLoginDuration?: number;
153
+ /**
154
+ * Default login duration (seconds) used when a client does NOT pass the `dbx_session_ttl`
155
+ * auth-URL param. When undefined, falls back to {@link OidcTokenLifetimes.refreshToken}.
156
+ */
157
+ readonly defaultRequestedLoginDuration?: number;
111
158
  /**
112
159
  * JWKS service configuration (encryption secret, rotated key max age).
113
160
  */
@@ -164,6 +211,35 @@ export declare abstract class OidcModuleConfig {
164
211
  * Defaults to `false`.
165
212
  */
166
213
  readonly registrationEnabled?: boolean;
214
+ /**
215
+ * Whether the oidc-provider should trust upstream proxy headers
216
+ * (`X-Forwarded-Host`, `X-Forwarded-Proto`) when computing the request URL
217
+ * used to build resume/return URLs and discovery metadata absolute paths.
218
+ *
219
+ * Required when running behind a reverse proxy such as Firebase Hosting →
220
+ * Cloud Run / Cloud Functions, where the request `Host` header is the
221
+ * underlying Cloud Run host (e.g. `api-xxxxx-uc.a.run.app`) and not the
222
+ * canonical issuer host. Without this, the interaction `returnTo` URL is
223
+ * built off the Cloud Run host and the browser is redirected away from the
224
+ * issuer's domain after login — causing the interaction cookies (scoped to
225
+ * the canonical host) to be missing on the resume request and producing
226
+ * "authorization request has expired".
227
+ *
228
+ * Maps to `provider.proxy = <value>` on the underlying oidc-provider
229
+ * (which is the Koa `app.proxy` setting).
230
+ *
231
+ * Defaults to `'prod_only'` if the environment is `production`, otherwise `false`.
232
+ */
233
+ readonly trustProxy?: boolean;
234
+ /**
235
+ * Whether to trust proxy headers in a non-production environment, such as the local environment.
236
+ *
237
+ * The dev environment typically does not require proxy headers, and setting
238
+ * `true` will result in errors.
239
+ *
240
+ * Defaults to `false`.
241
+ */
242
+ readonly trustProxyInNonProduction?: boolean;
167
243
  /**
168
244
  * Validates that all required fields are present on the config.
169
245
  *
@@ -89,7 +89,7 @@ export interface ProvideAppOidcModuleMetadataConfig extends Pick<ModuleMetadata,
89
89
  /**
90
90
  * Optional overrides to merge into the {@link OidcModuleConfig} produced by the factory.
91
91
  */
92
- readonly config?: Partial<Pick<OidcModuleConfig, 'suppressBodyParserWarning' | 'renderError' | 'protectedPaths' | 'appOAuthInteractionPath' | 'appOAuthLoginUrlPart' | 'appOAuthConsentUrlPart' | 'tokenEndpointAuthMethods' | 'registrationEnabled'>>;
92
+ readonly config?: Partial<Pick<OidcModuleConfig, 'suppressBodyParserWarning' | 'renderError' | 'protectedPaths' | 'appOAuthInteractionPath' | 'appOAuthLoginUrlPart' | 'appOAuthConsentUrlPart' | 'tokenEndpointAuthMethods' | 'registrationEnabled' | 'trustProxy' | 'trustProxyInNonProduction' | 'tokenLifetimes' | 'maxRequestedLoginDuration' | 'minRequestedLoginDuration' | 'defaultRequestedLoginDuration'>>;
93
93
  }
94
94
  /**
95
95
  * Convenience function used to generate ModuleMetadata for an app's OidcModule.
@@ -1,6 +1,11 @@
1
1
  import type { AdapterConstructor } from 'oidc-provider';
2
2
  import { type OidcServerFirestoreCollections } from '../model';
3
3
  import { type OidcEncryptionService } from './oidc.encryption.service';
4
+ /**
5
+ * Model types that support grantId-based revocation.
6
+ */
7
+ export declare const GRANTABLE_MODEL_NAMES: readonly ["AccessToken", "AuthorizationCode", "RefreshToken", "DeviceCode", "BackchannelAuthenticationRequest"];
8
+ export type GrantableModelName = (typeof GRANTABLE_MODEL_NAMES)[number];
4
9
  /**
5
10
  * Creates an oidc-provider adapter constructor backed by Firestore via {@link OidcServerFirestoreCollections}.
6
11
  *
@@ -50,10 +50,16 @@ export declare class OidcInteractionService {
50
50
  /**
51
51
  * Finds an existing grant by ID, or creates a new one.
52
52
  *
53
+ * For new grants, optionally pre-set `expiresIn` so {@link Grant#save} writes the requested TTL
54
+ * instead of falling through to the configured Grant TTL function (which cannot read the original
55
+ * `dbx_session_ttl` request param when save is driven from a NestJS controller — see
56
+ * {@link OidcService#resolveLoginDurationForGrant}).
57
+ *
53
58
  * @param grantId - the existing grant ID to look up, or undefined to create a new grant
54
59
  * @param accountId - the account ID for creating a new grant
55
60
  * @param clientId - the client ID for creating a new grant
61
+ * @param expiresInSeconds - optional TTL (seconds) to assign to a newly-created grant
56
62
  * @returns the found or newly created grant
57
63
  */
58
- findOrCreateGrant(grantId: string | undefined, accountId: string, clientId: string): Promise<Grant>;
64
+ findOrCreateGrant(grantId: string | undefined, accountId: string, clientId: string, expiresInSeconds?: number): Promise<Grant>;
59
65
  }
@@ -1,4 +1,4 @@
1
- import type { default as Provider, Configuration } from 'oidc-provider';
1
+ import { type default as Provider, type Configuration } from 'oidc-provider';
2
2
  import { OidcModuleConfig } from '../oidc.config';
3
3
  import { JwksService } from './oidc.jwks.service';
4
4
  import { OidcAccountService } from './oidc.account.service';
@@ -27,6 +27,22 @@ export declare class OidcService {
27
27
  * @returns the lazily-initialized oidc-provider instance
28
28
  */
29
29
  getProvider(): Promise<Provider>;
30
+ /**
31
+ * Resolves the login-duration TTL (seconds) for a Grant being created from a fresh consent submission.
32
+ *
33
+ * The Grant TTL configured on the oidc-provider only fires when oidc-provider's koa middleware drives
34
+ * `grant.save()` (so `AsyncLocalStorage` carries the request context). Our consent flow saves grants
35
+ * from a NestJS controller, so we resolve the TTL up-front and pre-set `grant.expiresIn` before saving.
36
+ *
37
+ * Mirrors the resolution used by the `Grant`/`Session` TTL functions in {@link buildProviderConfiguration}.
38
+ *
39
+ * @param requestedRawTtl - The raw `dbx_session_ttl` value from `interaction.params`, if any.
40
+ * @param clientPayload - The persisted client metadata, used to read the per-client `dbx_max_session_ttl` cap.
41
+ * @returns The resolved Grant TTL in seconds.
42
+ */
43
+ resolveLoginDurationForGrant(requestedRawTtl: unknown, clientPayload: {
44
+ dbx_max_session_ttl?: number;
45
+ } | undefined): number;
30
46
  /**
31
47
  * Verifies an opaque access token and returns the {@link OidcAuthData}.
32
48
  *
@@ -37,6 +53,20 @@ export declare class OidcService {
37
53
  * @returns The auth context, or `undefined` if the token is invalid or expired.
38
54
  */
39
55
  verifyAccessToken(rawToken: string): Promise<OidcAuthData | undefined>;
56
+ /**
57
+ * Revokes a Grant entry and every grantable token entry that references it.
58
+ *
59
+ * Iterates through every grantable model (`AccessToken`, `AuthorizationCode`,
60
+ * `RefreshToken`, `DeviceCode`, `BackchannelAuthenticationRequest`) and calls
61
+ * the adapter's `revokeByGrantId` to delete all matching entries, then
62
+ * deletes the Grant adapter entry itself. After this resolves, any token
63
+ * referencing the grant is gone — `verifyAccessToken` returns `undefined`
64
+ * and a `grant_type=refresh_token` exchange fails with `invalid_grant`.
65
+ *
66
+ * @param grantId - the grant id (and Grant adapter entry id) to revoke
67
+ * @throws when the Grant entry does not exist
68
+ */
69
+ revokeGrant(grantId: string): Promise<void>;
40
70
  /**
41
71
  * Finds a client payload by ID directly from the adapter store.
42
72
  *
@@ -0,0 +1,85 @@
1
+ import type { KoaContextWithOIDC } from 'oidc-provider';
2
+ /**
3
+ * Custom OIDC auth-URL parameter clients use to request a non-default login duration.
4
+ *
5
+ * Value is integer seconds. Subject to per-client and global server caps via {@link resolveLoginDurationSeconds}.
6
+ */
7
+ export declare const DBX_FIREBASE_SERVER_OIDC_SESSION_TTL_PARAM = "dbx_session_ttl";
8
+ /**
9
+ * Custom oidc-provider client metadata field for a client's maximum requestable login duration (seconds).
10
+ */
11
+ export declare const DBX_FIREBASE_SERVER_OIDC_MAX_SESSION_TTL_CLIENT_METADATA = "dbx_max_session_ttl";
12
+ /**
13
+ * Inputs to {@link resolveLoginDurationSeconds}.
14
+ */
15
+ export interface ResolveLoginDurationInput {
16
+ /**
17
+ * Seconds requested by the client via {@link DBX_FIREBASE_SERVER_OIDC_SESSION_TTL_PARAM}, or undefined when not provided.
18
+ */
19
+ readonly requestedSeconds: number | undefined;
20
+ /**
21
+ * Per-client ceiling from the client's {@link DBX_FIREBASE_SERVER_OIDC_MAX_SESSION_TTL_CLIENT_METADATA} metadata, or undefined.
22
+ */
23
+ readonly clientMaxSeconds: number | undefined;
24
+ /**
25
+ * Global server ceiling (seconds).
26
+ */
27
+ readonly serverMaxSeconds: number;
28
+ /**
29
+ * Global server floor (seconds).
30
+ */
31
+ readonly serverMinSeconds: number;
32
+ /**
33
+ * Default duration (seconds) used when `requestedSeconds` is undefined.
34
+ */
35
+ readonly defaultSeconds: number;
36
+ }
37
+ /**
38
+ * Clamps a requested login duration into the allowed range.
39
+ *
40
+ * Resolution order:
41
+ * 1. Pick the requested value, falling back to the configured default when omitted.
42
+ * 2. Compute the effective ceiling as `min(serverMax, clientMax-or-Infinity)`.
43
+ * 3. Clamp the value to `[serverMin, ceiling]`.
44
+ *
45
+ * @param input - The clamp inputs (requested value, client cap, server bounds, default).
46
+ * @returns The clamped duration in seconds.
47
+ *
48
+ * @example
49
+ * ```typescript
50
+ * resolveLoginDurationSeconds({
51
+ * requestedSeconds: 60 * 24 * 60 * 60, // 60 days
52
+ * clientMaxSeconds: 30 * 24 * 60 * 60, // 30 days client cap
53
+ * serverMaxSeconds: 90 * 24 * 60 * 60, // 90 days global cap
54
+ * serverMinSeconds: 60 * 60, // 1 hour floor
55
+ * defaultSeconds: 30 * 24 * 60 * 60
56
+ * }); // → 30 * 24 * 60 * 60 (clamped to client max)
57
+ * ```
58
+ */
59
+ export declare function resolveLoginDurationSeconds(input: ResolveLoginDurationInput): number;
60
+ /**
61
+ * Parses a raw `dbx_session_ttl` value (string or number, from URL query / form / persisted interaction params)
62
+ * into a positive integer number of seconds. Returns `undefined` when missing or invalid so the caller falls
63
+ * back to a default.
64
+ *
65
+ * @param raw - The raw value to parse.
66
+ * @returns The parsed positive integer seconds, or `undefined` when absent/invalid.
67
+ */
68
+ export declare function parseRequestedSessionTtlSeconds(raw: unknown): number | undefined;
69
+ /**
70
+ * Reads {@link DBX_FIREBASE_SERVER_OIDC_SESSION_TTL_PARAM} from a KoaContextWithOIDC and parses it to a positive integer
71
+ * number of seconds. Returns `undefined` when missing or invalid (so the caller falls back to a default).
72
+ *
73
+ * @param ctx - The OIDC Koa context, or undefined.
74
+ * @returns The parsed positive integer seconds, or `undefined` when absent/invalid.
75
+ */
76
+ export declare function readRequestedSessionTtlSeconds(ctx: KoaContextWithOIDC | undefined): number | undefined;
77
+ /**
78
+ * Inspects oidc-provider entities on the context to find the resolved Grant expiry.
79
+ *
80
+ * Returns the remaining seconds until the Grant expires, or `undefined` when no Grant is bound to the context.
81
+ *
82
+ * @param ctx - The OIDC Koa context, or undefined.
83
+ * @returns The remaining seconds until grant expiry, or `undefined` when no grant is bound or it has expired.
84
+ */
85
+ export declare function readRemainingGrantSeconds(ctx: KoaContextWithOIDC | undefined): number | undefined;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@dereekb/firebase-server",
3
- "version": "13.11.3",
3
+ "version": "13.11.4",
4
4
  "sideEffects": false,
5
5
  "exports": {
6
6
  "./test": {
@@ -44,15 +44,15 @@
44
44
  "main": "./index.cjs.js",
45
45
  "types": "./src/index.d.ts",
46
46
  "peerDependencies": {
47
- "@dereekb/analytics": "13.11.3",
48
- "@dereekb/date": "13.11.3",
49
- "@dereekb/dbx-core": "13.11.3",
50
- "@dereekb/firebase": "13.11.3",
51
- "@dereekb/model": "13.11.3",
52
- "@dereekb/nestjs": "13.11.3",
53
- "@dereekb/rxjs": "13.11.3",
54
- "@dereekb/util": "13.11.3",
55
- "@dereekb/zoho": "13.11.3",
47
+ "@dereekb/analytics": "13.11.4",
48
+ "@dereekb/date": "13.11.4",
49
+ "@dereekb/dbx-core": "13.11.4",
50
+ "@dereekb/firebase": "13.11.4",
51
+ "@dereekb/model": "13.11.4",
52
+ "@dereekb/nestjs": "13.11.4",
53
+ "@dereekb/rxjs": "13.11.4",
54
+ "@dereekb/util": "13.11.4",
55
+ "@dereekb/zoho": "13.11.4",
56
56
  "@google-cloud/firestore": "^7.11.6",
57
57
  "@google-cloud/storage": "^7.19.0",
58
58
  "@nestjs/common": "^11.1.19",
package/test/package.json CHANGED
@@ -1,16 +1,16 @@
1
1
  {
2
2
  "name": "@dereekb/firebase-server/test",
3
- "version": "13.11.3",
3
+ "version": "13.11.4",
4
4
  "peerDependencies": {
5
- "@dereekb/analytics": "13.11.3",
6
- "@dereekb/date": "13.11.3",
7
- "@dereekb/firebase": "13.11.3",
8
- "@dereekb/firebase-server": "13.11.3",
9
- "@dereekb/firebase-server/oidc": "13.11.3",
10
- "@dereekb/model": "13.11.3",
11
- "@dereekb/nestjs": "13.11.3",
12
- "@dereekb/rxjs": "13.11.3",
13
- "@dereekb/util": "13.11.3",
5
+ "@dereekb/analytics": "13.11.4",
6
+ "@dereekb/date": "13.11.4",
7
+ "@dereekb/firebase": "13.11.4",
8
+ "@dereekb/firebase-server": "13.11.4",
9
+ "@dereekb/firebase-server/oidc": "13.11.4",
10
+ "@dereekb/model": "13.11.4",
11
+ "@dereekb/nestjs": "13.11.4",
12
+ "@dereekb/rxjs": "13.11.4",
13
+ "@dereekb/util": "13.11.4",
14
14
  "@google-cloud/firestore": "^7.11.6",
15
15
  "@google-cloud/storage": "^7.19.0",
16
16
  "@nestjs/common": "^11.1.19",
@@ -23,7 +23,7 @@
23
23
  "supertest": "^7.2.2"
24
24
  },
25
25
  "devDependencies": {
26
- "@dereekb/nestjs": "13.11.3"
26
+ "@dereekb/nestjs": "13.11.4"
27
27
  },
28
28
  "exports": {
29
29
  "./package.json": "./package.json",
package/zoho/package.json CHANGED
@@ -1,15 +1,15 @@
1
1
  {
2
2
  "name": "@dereekb/firebase-server/zoho",
3
- "version": "13.11.3",
3
+ "version": "13.11.4",
4
4
  "peerDependencies": {
5
- "@dereekb/analytics": "13.11.3",
6
- "@dereekb/date": "13.11.3",
7
- "@dereekb/model": "13.11.3",
8
- "@dereekb/nestjs": "13.11.3",
9
- "@dereekb/rxjs": "13.11.3",
10
- "@dereekb/firebase": "13.11.3",
11
- "@dereekb/util": "13.11.3",
12
- "@dereekb/zoho": "13.11.3"
5
+ "@dereekb/analytics": "13.11.4",
6
+ "@dereekb/date": "13.11.4",
7
+ "@dereekb/model": "13.11.4",
8
+ "@dereekb/nestjs": "13.11.4",
9
+ "@dereekb/rxjs": "13.11.4",
10
+ "@dereekb/firebase": "13.11.4",
11
+ "@dereekb/util": "13.11.4",
12
+ "@dereekb/zoho": "13.11.4"
13
13
  },
14
14
  "exports": {
15
15
  "./package.json": "./package.json",