@baukit/auth-node 0.3.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.
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Patrick Koss
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
package/README.md ADDED
@@ -0,0 +1,76 @@
1
+ # @baukit/auth-node
2
+
3
+ `@baukit/auth-node` is the Node 24 OIDC device-flow package for CLI and MCP clients. It handles discovery, RFC 8628 polling, S256 PKCE, refresh rotation, and a local profile cache. It has no runtime dependencies.
4
+
5
+ The package does not print instructions or open a browser. Supply callbacks for those actions.
6
+
7
+ ## Device-flow client
8
+
9
+ ```ts
10
+ import { DeviceFlowClient } from '@baukit/auth-node/device-flow';
11
+
12
+ const auth = new DeviceFlowClient(
13
+ {
14
+ issuer: process.env['OIDC_ISSUER'] ?? '',
15
+ clientId: process.env['OIDC_CLIENT_ID'] ?? '',
16
+ scopes: ['openid', 'profile', 'offline_access'],
17
+ audience: 'notes-api',
18
+ cache: {
19
+ namespace: 'notes-mcp',
20
+ },
21
+ },
22
+ {
23
+ environmentToken: () => process.env['NOTES_API_TOKEN'],
24
+ },
25
+ );
26
+
27
+ await auth.login({
28
+ presentation: {
29
+ showVerification: ({ verificationUri, userCode }) => {
30
+ process.stderr.write(`Open ${verificationUri}\nEnter ${userCode}\n`);
31
+ },
32
+ showStatus: (status) => {
33
+ process.stderr.write(`Login status: ${status}\n`);
34
+ },
35
+ openBrowser: (url) => openProductBrowser(url),
36
+ },
37
+ });
38
+
39
+ const token = await auth.accessToken();
40
+ ```
41
+
42
+ `accessToken()` checks the injected environment-token source first. It then reads the selected cache profile and refreshes near-expiry tokens. Refreshes share one promise in a process and hold an adjacent `.lock` file while reading and replacing the cache.
43
+
44
+ Pass an `AbortSignal` to `login`, `accessToken`, or `logout`. Discovery and token requests have a 15-second default timeout. A login has a 10-minute total timeout. Both limits are configurable.
45
+
46
+ ## Endpoint policy
47
+
48
+ The configured issuer must match discovery metadata. Put known issuer aliases in `endpointPolicy.issuerAllowlist`. Token and device endpoints must share the issuer origin and path. Put a provider's documented endpoint origin in `endpointOriginAllowlist` when it uses a separate origin.
49
+
50
+ All issuer, device, token, and verification URLs require HTTPS. Local development can set `allowLoopbackHttp: true`; this permits only `localhost`, `127.0.0.0/8`, and `::1`.
51
+
52
+ Discovery and token bodies are limited to 64 KiB by default. Errors contain a stable code, an allowlisted message, an optional HTTP status, and no provider body. The client does not log.
53
+
54
+ ## Cache contract
55
+
56
+ The JSON cache holds named profiles under one namespace. `defaultTokenCachePath(namespace)` resolves to `$XDG_CONFIG_HOME/<namespace>/tokens.json`, or `~/.config/<namespace>/tokens.json` when `XDG_CONFIG_HOME` is unset.
57
+
58
+ On POSIX systems the cache file must have mode `0600` and its immediate directory must have mode `0700`. Existing unsafe permissions fail with `cache_permission`. The cache rejects symlink path components. Writes use a new temporary file, sync it, and atomically rename it, so a write failure before rename leaves the old file intact. Windows skips POSIX mode checks and relies on host ACLs.
59
+
60
+ Use a separate namespace or profile for accounts that must not share credentials. `logout()` removes the selected profile and leaves other profiles in place.
61
+
62
+ ## Display-only claims
63
+
64
+ `displayClaims()` and `decodeDisplayOnlyClaims()` decode a small allowlist of JWT fields without checking the signature. Use the result only for labels such as a `whoami` display. Never use it for authorization, storage partitions, audit identity, or analytics identity.
65
+
66
+ ## Migration from product-local auth
67
+
68
+ Replace local discovery, device polling, refresh, and cache functions with one `DeviceFlowClient`. Keep these product inputs in the application:
69
+
70
+ - environment variable names and defaults;
71
+ - issuer, client ID, scopes, and audience;
72
+ - CLI text and browser-launch behavior;
73
+ - API base URL and bearer-token wiring; and
74
+ - cache namespace, path, and profile selection.
75
+
76
+ Older product caches do not have the versioned profile document used here. Sign out or remove the old file, then run the product's login command once. The package intentionally does not guess which product-owned legacy shape it received.
@@ -0,0 +1,38 @@
1
+ export interface CachedTokenProfile {
2
+ readonly accessToken: string;
3
+ readonly refreshToken?: string;
4
+ readonly idToken?: string;
5
+ readonly tokenType: string;
6
+ readonly expiresAt: number;
7
+ readonly issuer: string;
8
+ readonly clientId: string;
9
+ readonly scopes: readonly string[];
10
+ readonly audience?: string;
11
+ }
12
+ export interface TokenCacheTransaction {
13
+ read(profile: string): Promise<CachedTokenProfile | undefined>;
14
+ write(profile: string, value: CachedTokenProfile): Promise<void>;
15
+ remove(profile: string): Promise<boolean>;
16
+ }
17
+ export interface NodeTokenCacheOptions {
18
+ readonly namespace: string;
19
+ readonly path?: string;
20
+ readonly platform?: NodeJS.Platform;
21
+ readonly now?: () => number;
22
+ readonly sleep?: (milliseconds: number, signal?: AbortSignal) => Promise<void>;
23
+ readonly lockTimeoutMs?: number;
24
+ readonly lockRetryMs?: number;
25
+ }
26
+ export declare function defaultTokenCachePath(namespace: string, environment?: Readonly<Record<string, string | undefined>>): string;
27
+ /** A versioned profile cache that serializes mutations with an adjacent lock file. */
28
+ export declare class NodeTokenCache {
29
+ #private;
30
+ readonly path: string;
31
+ readonly namespace: string;
32
+ constructor(options: NodeTokenCacheOptions);
33
+ read(profile?: string): Promise<CachedTokenProfile | undefined>;
34
+ write(profile: string, value: CachedTokenProfile, signal?: AbortSignal): Promise<void>;
35
+ remove(profile?: string, signal?: AbortSignal): Promise<boolean>;
36
+ withLock<T>(action: (transaction: TokenCacheTransaction) => Promise<T>, signal?: AbortSignal): Promise<T>;
37
+ }
38
+ //# sourceMappingURL=cache.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cache.d.ts","sourceRoot":"","sources":["../src/cache.ts"],"names":[],"mappings":"AAmBA,MAAM,WAAW,kBAAkB;IACjC,QAAQ,CAAC,WAAW,EAAE,MAAM,CAAC;IAC7B,QAAQ,CAAC,YAAY,CAAC,EAAE,MAAM,CAAC;IAC/B,QAAQ,CAAC,OAAO,CAAC,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,MAAM,EAAE,MAAM,CAAC;IACxB,QAAQ,CAAC,QAAQ,EAAE,MAAM,CAAC;IAC1B,QAAQ,CAAC,MAAM,EAAE,SAAS,MAAM,EAAE,CAAC;IACnC,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC;CAC5B;AAQD,MAAM,WAAW,qBAAqB;IACpC,IAAI,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,kBAAkB,GAAG,SAAS,CAAC,CAAC;IAC/D,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,kBAAkB,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IACjE,MAAM,CAAC,OAAO,EAAE,MAAM,GAAG,OAAO,CAAC,OAAO,CAAC,CAAC;CAC3C;AAED,MAAM,WAAW,qBAAqB;IACpC,QAAQ,CAAC,SAAS,EAAE,MAAM,CAAC;IAC3B,QAAQ,CAAC,IAAI,CAAC,EAAE,MAAM,CAAC;IACvB,QAAQ,CAAC,QAAQ,CAAC,EAAE,MAAM,CAAC,QAAQ,CAAC;IACpC,QAAQ,CAAC,GAAG,CAAC,EAAE,MAAM,MAAM,CAAC;IAC5B,QAAQ,CAAC,KAAK,CAAC,EAAE,CAAC,YAAY,EAAE,MAAM,EAAE,MAAM,CAAC,EAAE,WAAW,KAAK,OAAO,CAAC,IAAI,CAAC,CAAC;IAC/E,QAAQ,CAAC,aAAa,CAAC,EAAE,MAAM,CAAC;IAChC,QAAQ,CAAC,WAAW,CAAC,EAAE,MAAM,CAAC;CAC/B;AAED,wBAAgB,qBAAqB,CACnC,SAAS,EAAE,MAAM,EACjB,WAAW,GAAE,QAAQ,CAAC,MAAM,CAAC,MAAM,EAAE,MAAM,GAAG,SAAS,CAAC,CAAe,GACtE,MAAM,CAQR;AAED,sFAAsF;AACtF,qBAAa,cAAc;;IACzB,SAAgB,IAAI,EAAE,MAAM,CAAC;IAC7B,SAAgB,SAAS,EAAE,MAAM,CAAC;gBAOf,OAAO,EAAE,qBAAqB;IAiBpC,IAAI,CAAC,OAAO,SAAY,GAAG,OAAO,CAAC,kBAAkB,GAAG,SAAS,CAAC;IAMxE,KAAK,CAAC,OAAO,EAAE,MAAM,EAAE,KAAK,EAAE,kBAAkB,EAAE,MAAM,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,IAAI,CAAC;IAMtF,MAAM,CAAC,OAAO,SAAY,EAAE,MAAM,CAAC,EAAE,WAAW,GAAG,OAAO,CAAC,OAAO,CAAC;IAI7D,QAAQ,CAAC,CAAC,EACrB,MAAM,EAAE,CAAC,WAAW,EAAE,qBAAqB,KAAK,OAAO,CAAC,CAAC,CAAC,EAC1D,MAAM,CAAC,EAAE,WAAW,GACnB,OAAO,CAAC,CAAC,CAAC;CAyHd"}
package/dist/cache.js ADDED
@@ -0,0 +1,316 @@
1
+ /// <reference types="node" />
2
+ import { constants } from 'node:fs';
3
+ import { chmod, lstat, mkdir, open, rename, unlink } from 'node:fs/promises';
4
+ import { homedir } from 'node:os';
5
+ import { dirname, join, parse, resolve, sep } from 'node:path';
6
+ import { randomUUID } from 'node:crypto';
7
+ import { AuthNodeError } from './errors.js';
8
+ const CACHE_VERSION = 1;
9
+ const CACHE_MAX_BYTES = 256 * 1024;
10
+ const DEFAULT_LOCK_TIMEOUT_MS = 10_000;
11
+ const DEFAULT_LOCK_RETRY_MS = 50;
12
+ const PRIVATE_FILE_MODE = 0o600;
13
+ const PRIVATE_DIRECTORY_MODE = 0o700;
14
+ const UNSAFE_MODE_BITS = 0o077;
15
+ const SAFE_NAME = /^[A-Za-z0-9][A-Za-z0-9._-]{0,63}$/u;
16
+ export function defaultTokenCachePath(namespace, environment = process.env) {
17
+ validateName(namespace, 'cache namespace');
18
+ const configuredHome = environment['XDG_CONFIG_HOME']?.trim();
19
+ const configHome = configuredHome === undefined || configuredHome.length === 0
20
+ ? join(homedir(), '.config')
21
+ : configuredHome;
22
+ return join(configHome, namespace, 'tokens.json');
23
+ }
24
+ /** A versioned profile cache that serializes mutations with an adjacent lock file. */
25
+ export class NodeTokenCache {
26
+ path;
27
+ namespace;
28
+ #platform;
29
+ #now;
30
+ #sleep;
31
+ #lockTimeoutMs;
32
+ #lockRetryMs;
33
+ constructor(options) {
34
+ validateName(options.namespace, 'cache namespace');
35
+ this.namespace = options.namespace;
36
+ this.path = resolve(options.path ?? defaultTokenCachePath(options.namespace));
37
+ this.#platform = options.platform ?? process.platform;
38
+ this.#now = options.now ?? Date.now;
39
+ this.#sleep = options.sleep ?? abortableDelay;
40
+ this.#lockTimeoutMs = positiveInteger(options.lockTimeoutMs ?? DEFAULT_LOCK_TIMEOUT_MS, 'cache lock timeout');
41
+ this.#lockRetryMs = positiveInteger(options.lockRetryMs ?? DEFAULT_LOCK_RETRY_MS, 'cache lock retry interval');
42
+ }
43
+ async read(profile = 'default') {
44
+ validateName(profile, 'cache profile');
45
+ const document = await this.#readDocument();
46
+ return document === undefined ? undefined : ownProfile(document.profiles, profile);
47
+ }
48
+ write(profile, value, signal) {
49
+ return this.withLock(async (transaction) => {
50
+ await transaction.write(profile, value);
51
+ }, signal);
52
+ }
53
+ remove(profile = 'default', signal) {
54
+ return this.withLock((transaction) => transaction.remove(profile), signal);
55
+ }
56
+ async withLock(action, signal) {
57
+ throwIfAborted(signal);
58
+ const lock = await this.#acquireLock(signal);
59
+ try {
60
+ const transaction = {
61
+ read: (profile) => this.#readProfile(profile),
62
+ write: (profile, value) => this.#writeProfile(profile, value),
63
+ remove: (profile) => this.#removeProfile(profile),
64
+ };
65
+ return await action(transaction);
66
+ }
67
+ finally {
68
+ await this.#releaseLock(lock);
69
+ }
70
+ }
71
+ async #readProfile(profile) {
72
+ validateName(profile, 'cache profile');
73
+ const document = await this.#readDocument();
74
+ return document === undefined ? undefined : ownProfile(document.profiles, profile);
75
+ }
76
+ async #writeProfile(profile, value) {
77
+ validateName(profile, 'cache profile');
78
+ validateProfile(value);
79
+ const current = await this.#readDocument();
80
+ const profiles = { ...(current?.profiles ?? {}), [profile]: value };
81
+ await this.#replaceDocument({ version: CACHE_VERSION, namespace: this.namespace, profiles });
82
+ }
83
+ async #removeProfile(profile) {
84
+ validateName(profile, 'cache profile');
85
+ const current = await this.#readDocument();
86
+ if (current === undefined || ownProfile(current.profiles, profile) === undefined)
87
+ return false;
88
+ const profiles = Object.fromEntries(Object.entries(current.profiles).filter(([name]) => name !== profile));
89
+ await this.#replaceDocument({ version: CACHE_VERSION, namespace: this.namespace, profiles });
90
+ return true;
91
+ }
92
+ async #readDocument() {
93
+ await assertNoSymlink(this.path, true);
94
+ let handle;
95
+ try {
96
+ handle = await open(this.path, constants.O_RDONLY | constants.O_NOFOLLOW);
97
+ }
98
+ catch (error) {
99
+ if (nodeError(error, 'ENOENT'))
100
+ return undefined;
101
+ throw cacheIoError(error, 'cache_read_failed');
102
+ }
103
+ try {
104
+ const metadata = await handle.stat();
105
+ validateCacheFile(metadata, this.#platform);
106
+ if (metadata.size > CACHE_MAX_BYTES)
107
+ throw new AuthNodeError('cache_corrupt');
108
+ const contents = await handle.readFile({ encoding: 'utf8' });
109
+ if (Buffer.byteLength(contents) > CACHE_MAX_BYTES) {
110
+ throw new AuthNodeError('cache_corrupt');
111
+ }
112
+ return parseDocument(contents, this.namespace);
113
+ }
114
+ catch (error) {
115
+ if (error instanceof AuthNodeError)
116
+ throw error;
117
+ throw cacheIoError(error, 'cache_read_failed');
118
+ }
119
+ finally {
120
+ await handle.close().catch(() => undefined);
121
+ }
122
+ }
123
+ async #replaceDocument(document) {
124
+ const directory = dirname(this.path);
125
+ await preparePrivateDirectory(directory, this.#platform);
126
+ await assertNoSymlink(this.path, true);
127
+ const temporaryPath = `${this.path}.${String(process.pid)}.${randomUUID()}.tmp`;
128
+ let handle;
129
+ try {
130
+ handle = await open(temporaryPath, 'wx', PRIVATE_FILE_MODE);
131
+ await handle.writeFile(`${JSON.stringify(document, null, 2)}\n`, 'utf8');
132
+ await handle.sync();
133
+ await handle.close();
134
+ handle = undefined;
135
+ if (this.#platform !== 'win32')
136
+ await chmod(temporaryPath, PRIVATE_FILE_MODE);
137
+ await assertNoSymlink(this.path, true);
138
+ await rename(temporaryPath, this.path);
139
+ }
140
+ catch (error) {
141
+ await handle?.close().catch(() => undefined);
142
+ await unlink(temporaryPath).catch(() => undefined);
143
+ if (error instanceof AuthNodeError)
144
+ throw error;
145
+ throw cacheIoError(error, 'cache_write_failed');
146
+ }
147
+ }
148
+ async #acquireLock(signal) {
149
+ const directory = dirname(this.path);
150
+ await preparePrivateDirectory(directory, this.#platform);
151
+ const lockPath = `${this.path}.lock`;
152
+ const deadline = this.#now() + this.#lockTimeoutMs;
153
+ for (;;) {
154
+ throwIfAborted(signal);
155
+ await assertNoSymlink(lockPath, true);
156
+ try {
157
+ return await open(lockPath, 'wx', PRIVATE_FILE_MODE);
158
+ }
159
+ catch (error) {
160
+ if (!nodeError(error, 'EEXIST'))
161
+ throw cacheIoError(error, 'cache_write_failed');
162
+ }
163
+ if (this.#now() >= deadline)
164
+ throw new AuthNodeError('cache_lock_timeout', { retryable: true });
165
+ await this.#sleep(this.#lockRetryMs, signal);
166
+ }
167
+ }
168
+ async #releaseLock(handle) {
169
+ const lockPath = `${this.path}.lock`;
170
+ let stillOwned = false;
171
+ try {
172
+ const held = await handle.stat();
173
+ const current = await lstat(lockPath);
174
+ stillOwned = held.dev === current.dev && held.ino === current.ino;
175
+ }
176
+ catch {
177
+ stillOwned = false;
178
+ }
179
+ await handle.close().catch(() => undefined);
180
+ if (stillOwned)
181
+ await unlink(lockPath).catch(() => undefined);
182
+ }
183
+ }
184
+ function parseDocument(contents, namespace) {
185
+ let value;
186
+ try {
187
+ value = JSON.parse(contents);
188
+ }
189
+ catch {
190
+ throw new AuthNodeError('cache_corrupt');
191
+ }
192
+ if (!isRecord(value) || value['version'] !== CACHE_VERSION || value['namespace'] !== namespace) {
193
+ throw new AuthNodeError('cache_corrupt');
194
+ }
195
+ const rawProfiles = value['profiles'];
196
+ if (!isRecord(rawProfiles))
197
+ throw new AuthNodeError('cache_corrupt');
198
+ const profiles = {};
199
+ for (const [name, profile] of Object.entries(rawProfiles)) {
200
+ validateNameOrCorrupt(name);
201
+ validateProfile(profile);
202
+ profiles[name] = profile;
203
+ }
204
+ return { version: CACHE_VERSION, namespace, profiles };
205
+ }
206
+ function validateProfile(value) {
207
+ if (!isRecord(value) ||
208
+ !nonEmptyString(value['accessToken']) ||
209
+ (value['refreshToken'] !== undefined && !nonEmptyString(value['refreshToken'])) ||
210
+ (value['idToken'] !== undefined && !nonEmptyString(value['idToken'])) ||
211
+ !nonEmptyString(value['tokenType']) ||
212
+ typeof value['expiresAt'] !== 'number' ||
213
+ !Number.isFinite(value['expiresAt']) ||
214
+ value['expiresAt'] <= 0 ||
215
+ !nonEmptyString(value['issuer']) ||
216
+ !nonEmptyString(value['clientId']) ||
217
+ !Array.isArray(value['scopes']) ||
218
+ !value['scopes'].every(nonEmptyString) ||
219
+ (value['audience'] !== undefined && !nonEmptyString(value['audience']))) {
220
+ throw new AuthNodeError('cache_corrupt');
221
+ }
222
+ }
223
+ async function preparePrivateDirectory(path, platform) {
224
+ try {
225
+ await assertNoSymlink(path, false);
226
+ await mkdir(path, { recursive: true, mode: PRIVATE_DIRECTORY_MODE });
227
+ await assertNoSymlink(path, false);
228
+ const metadata = await lstat(path);
229
+ if (!metadata.isDirectory())
230
+ throw new AuthNodeError('cache_permission');
231
+ if (platform !== 'win32' && (metadata.mode & UNSAFE_MODE_BITS) !== 0) {
232
+ throw new AuthNodeError('cache_permission');
233
+ }
234
+ }
235
+ catch (error) {
236
+ if (error instanceof AuthNodeError)
237
+ throw error;
238
+ throw cacheIoError(error, 'cache_permission');
239
+ }
240
+ }
241
+ async function assertNoSymlink(path, allowMissingLeaf) {
242
+ const absolute = resolve(path);
243
+ const root = parse(absolute).root;
244
+ const parts = absolute.slice(root.length).split(sep).filter(Boolean);
245
+ let current = root;
246
+ for (let index = 0; index < parts.length; index += 1) {
247
+ current = join(current, parts[index] ?? '');
248
+ try {
249
+ const metadata = await lstat(current);
250
+ if (metadata.isSymbolicLink())
251
+ throw new AuthNodeError('cache_symlink');
252
+ }
253
+ catch (error) {
254
+ if (nodeError(error, 'ENOENT') && (allowMissingLeaf || index < parts.length))
255
+ return;
256
+ throw error;
257
+ }
258
+ }
259
+ }
260
+ function validateCacheFile(metadata, platform) {
261
+ if (!metadata.isFile())
262
+ throw new AuthNodeError('cache_permission');
263
+ if (platform !== 'win32' && (metadata.mode & UNSAFE_MODE_BITS) !== 0) {
264
+ throw new AuthNodeError('cache_permission');
265
+ }
266
+ }
267
+ function validateName(value, label) {
268
+ if (!SAFE_NAME.test(value))
269
+ throw new TypeError(`${label} has an invalid format.`);
270
+ }
271
+ function validateNameOrCorrupt(value) {
272
+ if (!SAFE_NAME.test(value))
273
+ throw new AuthNodeError('cache_corrupt');
274
+ }
275
+ function positiveInteger(value, label) {
276
+ if (!Number.isSafeInteger(value) || value <= 0)
277
+ throw new RangeError(`${label} must be positive.`);
278
+ return value;
279
+ }
280
+ function cacheIoError(error, fallback) {
281
+ return new AuthNodeError(nodeError(error, 'EACCES') || nodeError(error, 'EPERM') ? 'cache_permission' : fallback);
282
+ }
283
+ function nodeError(error, code) {
284
+ return (error instanceof Error && 'code' in error && error.code === code);
285
+ }
286
+ function isRecord(value) {
287
+ return typeof value === 'object' && value !== null && !Array.isArray(value);
288
+ }
289
+ function nonEmptyString(value) {
290
+ return typeof value === 'string' && value.length > 0;
291
+ }
292
+ function ownProfile(profiles, name) {
293
+ return Object.hasOwn(profiles, name) ? profiles[name] : undefined;
294
+ }
295
+ function throwIfAborted(signal) {
296
+ if (signal?.aborted === true)
297
+ throw new AuthNodeError('aborted');
298
+ }
299
+ function abortableDelay(milliseconds, signal) {
300
+ return new Promise((resolveDelay, reject) => {
301
+ if (signal?.aborted === true) {
302
+ reject(new AuthNodeError('aborted'));
303
+ return;
304
+ }
305
+ const onAbort = () => {
306
+ clearTimeout(timeout);
307
+ reject(new AuthNodeError('aborted'));
308
+ };
309
+ const timeout = setTimeout(() => {
310
+ signal?.removeEventListener('abort', onAbort);
311
+ resolveDelay();
312
+ }, milliseconds);
313
+ signal?.addEventListener('abort', onAbort, { once: true });
314
+ });
315
+ }
316
+ //# sourceMappingURL=cache.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cache.js","sourceRoot":"","sources":["../src/cache.ts"],"names":[],"mappings":"AAAA,8BAA8B;AAE9B,OAAO,EAAE,SAAS,EAAc,MAAM,SAAS,CAAC;AAChD,OAAO,EAAE,KAAK,EAAE,KAAK,EAAE,KAAK,EAAE,IAAI,EAAE,MAAM,EAAE,MAAM,EAAmB,MAAM,kBAAkB,CAAC;AAC9F,OAAO,EAAE,OAAO,EAAE,MAAM,SAAS,CAAC;AAClC,OAAO,EAAE,OAAO,EAAE,IAAI,EAAE,KAAK,EAAE,OAAO,EAAE,GAAG,EAAE,MAAM,WAAW,CAAC;AAC/D,OAAO,EAAE,UAAU,EAAE,MAAM,aAAa,CAAC;AAEzC,OAAO,EAAE,aAAa,EAAE,MAAM,aAAa,CAAC;AAE5C,MAAM,aAAa,GAAG,CAAC,CAAC;AACxB,MAAM,eAAe,GAAG,GAAG,GAAG,IAAI,CAAC;AACnC,MAAM,uBAAuB,GAAG,MAAM,CAAC;AACvC,MAAM,qBAAqB,GAAG,EAAE,CAAC;AACjC,MAAM,iBAAiB,GAAG,KAAK,CAAC;AAChC,MAAM,sBAAsB,GAAG,KAAK,CAAC;AACrC,MAAM,gBAAgB,GAAG,KAAK,CAAC;AAC/B,MAAM,SAAS,GAAG,oCAAoC,CAAC;AAoCvD,MAAM,UAAU,qBAAqB,CACnC,SAAiB,EACjB,cAA4D,OAAO,CAAC,GAAG;IAEvE,YAAY,CAAC,SAAS,EAAE,iBAAiB,CAAC,CAAC;IAC3C,MAAM,cAAc,GAAG,WAAW,CAAC,iBAAiB,CAAC,EAAE,IAAI,EAAE,CAAC;IAC9D,MAAM,UAAU,GACd,cAAc,KAAK,SAAS,IAAI,cAAc,CAAC,MAAM,KAAK,CAAC;QACzD,CAAC,CAAC,IAAI,CAAC,OAAO,EAAE,EAAE,SAAS,CAAC;QAC5B,CAAC,CAAC,cAAc,CAAC;IACrB,OAAO,IAAI,CAAC,UAAU,EAAE,SAAS,EAAE,aAAa,CAAC,CAAC;AACpD,CAAC;AAED,sFAAsF;AACtF,MAAM,OAAO,cAAc;IACT,IAAI,CAAS;IACb,SAAS,CAAS;IACzB,SAAS,CAAkB;IAC3B,IAAI,CAAe;IACnB,MAAM,CAAgE;IACtE,cAAc,CAAS;IACvB,YAAY,CAAS;IAE9B,YAAmB,OAA8B;QAC/C,YAAY,CAAC,OAAO,CAAC,SAAS,EAAE,iBAAiB,CAAC,CAAC;QACnD,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,SAAS,CAAC;QACnC,IAAI,CAAC,IAAI,GAAG,OAAO,CAAC,OAAO,CAAC,IAAI,IAAI,qBAAqB,CAAC,OAAO,CAAC,SAAS,CAAC,CAAC,CAAC;QAC9E,IAAI,CAAC,SAAS,GAAG,OAAO,CAAC,QAAQ,IAAI,OAAO,CAAC,QAAQ,CAAC;QACtD,IAAI,CAAC,IAAI,GAAG,OAAO,CAAC,GAAG,IAAI,IAAI,CAAC,GAAG,CAAC;QACpC,IAAI,CAAC,MAAM,GAAG,OAAO,CAAC,KAAK,IAAI,cAAc,CAAC;QAC9C,IAAI,CAAC,cAAc,GAAG,eAAe,CACnC,OAAO,CAAC,aAAa,IAAI,uBAAuB,EAChD,oBAAoB,CACrB,CAAC;QACF,IAAI,CAAC,YAAY,GAAG,eAAe,CACjC,OAAO,CAAC,WAAW,IAAI,qBAAqB,EAC5C,2BAA2B,CAC5B,CAAC;IACJ,CAAC;IAEM,KAAK,CAAC,IAAI,CAAC,OAAO,GAAG,SAAS;QACnC,YAAY,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC;QACvC,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;QAC5C,OAAO,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,UAAU,CAAC,QAAQ,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;IACrF,CAAC;IAEM,KAAK,CAAC,OAAe,EAAE,KAAyB,EAAE,MAAoB;QAC3E,OAAO,IAAI,CAAC,QAAQ,CAAC,KAAK,EAAE,WAAW,EAAE,EAAE;YACzC,MAAM,WAAW,CAAC,KAAK,CAAC,OAAO,EAAE,KAAK,CAAC,CAAC;QAC1C,CAAC,EAAE,MAAM,CAAC,CAAC;IACb,CAAC;IAEM,MAAM,CAAC,OAAO,GAAG,SAAS,EAAE,MAAoB;QACrD,OAAO,IAAI,CAAC,QAAQ,CAAC,CAAC,WAAW,EAAE,EAAE,CAAC,WAAW,CAAC,MAAM,CAAC,OAAO,CAAC,EAAE,MAAM,CAAC,CAAC;IAC7E,CAAC;IAEM,KAAK,CAAC,QAAQ,CACnB,MAA0D,EAC1D,MAAoB;QAEpB,cAAc,CAAC,MAAM,CAAC,CAAC;QACvB,MAAM,IAAI,GAAG,MAAM,IAAI,CAAC,YAAY,CAAC,MAAM,CAAC,CAAC;QAC7C,IAAI,CAAC;YACH,MAAM,WAAW,GAA0B;gBACzC,IAAI,EAAE,CAAC,OAAO,EAAE,EAAE,CAAC,IAAI,CAAC,YAAY,CAAC,OAAO,CAAC;gBAC7C,KAAK,EAAE,CAAC,OAAO,EAAE,KAAK,EAAE,EAAE,CAAC,IAAI,CAAC,aAAa,CAAC,OAAO,EAAE,KAAK,CAAC;gBAC7D,MAAM,EAAE,CAAC,OAAO,EAAE,EAAE,CAAC,IAAI,CAAC,cAAc,CAAC,OAAO,CAAC;aAClD,CAAC;YACF,OAAO,MAAM,MAAM,CAAC,WAAW,CAAC,CAAC;QACnC,CAAC;gBAAS,CAAC;YACT,MAAM,IAAI,CAAC,YAAY,CAAC,IAAI,CAAC,CAAC;QAChC,CAAC;IACH,CAAC;IAED,KAAK,CAAC,YAAY,CAAC,OAAe;QAChC,YAAY,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC;QACvC,MAAM,QAAQ,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;QAC5C,OAAO,QAAQ,KAAK,SAAS,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC,UAAU,CAAC,QAAQ,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC;IACrF,CAAC;IAED,KAAK,CAAC,aAAa,CAAC,OAAe,EAAE,KAAyB;QAC5D,YAAY,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC;QACvC,eAAe,CAAC,KAAK,CAAC,CAAC;QACvB,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;QAC3C,MAAM,QAAQ,GAAG,EAAE,GAAG,CAAC,OAAO,EAAE,QAAQ,IAAI,EAAE,CAAC,EAAE,CAAC,OAAO,CAAC,EAAE,KAAK,EAAE,CAAC;QACpE,MAAM,IAAI,CAAC,gBAAgB,CAAC,EAAE,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,QAAQ,EAAE,CAAC,CAAC;IAC/F,CAAC;IAED,KAAK,CAAC,cAAc,CAAC,OAAe;QAClC,YAAY,CAAC,OAAO,EAAE,eAAe,CAAC,CAAC;QACvC,MAAM,OAAO,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE,CAAC;QAC3C,IAAI,OAAO,KAAK,SAAS,IAAI,UAAU,CAAC,OAAO,CAAC,QAAQ,EAAE,OAAO,CAAC,KAAK,SAAS;YAAE,OAAO,KAAK,CAAC;QAC/F,MAAM,QAAQ,GAAG,MAAM,CAAC,WAAW,CACjC,MAAM,CAAC,OAAO,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,MAAM,CAAC,CAAC,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,IAAI,KAAK,OAAO,CAAC,CACtE,CAAC;QACF,MAAM,IAAI,CAAC,gBAAgB,CAAC,EAAE,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,IAAI,CAAC,SAAS,EAAE,QAAQ,EAAE,CAAC,CAAC;QAC7F,OAAO,IAAI,CAAC;IACd,CAAC;IAED,KAAK,CAAC,aAAa;QACjB,MAAM,eAAe,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;QACvC,IAAI,MAAkB,CAAC;QACvB,IAAI,CAAC;YACH,MAAM,GAAG,MAAM,IAAI,CAAC,IAAI,CAAC,IAAI,EAAE,SAAS,CAAC,QAAQ,GAAG,SAAS,CAAC,UAAU,CAAC,CAAC;QAC5E,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,SAAS,CAAC,KAAK,EAAE,QAAQ,CAAC;gBAAE,OAAO,SAAS,CAAC;YACjD,MAAM,YAAY,CAAC,KAAK,EAAE,mBAAmB,CAAC,CAAC;QACjD,CAAC;QACD,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;YACrC,iBAAiB,CAAC,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,CAAC;YAC5C,IAAI,QAAQ,CAAC,IAAI,GAAG,eAAe;gBAAE,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;YAC9E,MAAM,QAAQ,GAAG,MAAM,MAAM,CAAC,QAAQ,CAAC,EAAE,QAAQ,EAAE,MAAM,EAAE,CAAC,CAAC;YAC7D,IAAI,MAAM,CAAC,UAAU,CAAC,QAAQ,CAAC,GAAG,eAAe,EAAE,CAAC;gBAClD,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;YAC3C,CAAC;YACD,OAAO,aAAa,CAAC,QAAQ,EAAE,IAAI,CAAC,SAAS,CAAC,CAAC;QACjD,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,KAAK,YAAY,aAAa;gBAAE,MAAM,KAAK,CAAC;YAChD,MAAM,YAAY,CAAC,KAAK,EAAE,mBAAmB,CAAC,CAAC;QACjD,CAAC;gBAAS,CAAC;YACT,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;QAC9C,CAAC;IACH,CAAC;IAED,KAAK,CAAC,gBAAgB,CAAC,QAAuB;QAC5C,MAAM,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACrC,MAAM,uBAAuB,CAAC,SAAS,EAAE,IAAI,CAAC,SAAS,CAAC,CAAC;QACzD,MAAM,eAAe,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;QACvC,MAAM,aAAa,GAAG,GAAG,IAAI,CAAC,IAAI,IAAI,MAAM,CAAC,OAAO,CAAC,GAAG,CAAC,IAAI,UAAU,EAAE,MAAM,CAAC;QAChF,IAAI,MAA8B,CAAC;QACnC,IAAI,CAAC;YACH,MAAM,GAAG,MAAM,IAAI,CAAC,aAAa,EAAE,IAAI,EAAE,iBAAiB,CAAC,CAAC;YAC5D,MAAM,MAAM,CAAC,SAAS,CAAC,GAAG,IAAI,CAAC,SAAS,CAAC,QAAQ,EAAE,IAAI,EAAE,CAAC,CAAC,IAAI,EAAE,MAAM,CAAC,CAAC;YACzE,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;YACpB,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC;YACrB,MAAM,GAAG,SAAS,CAAC;YACnB,IAAI,IAAI,CAAC,SAAS,KAAK,OAAO;gBAAE,MAAM,KAAK,CAAC,aAAa,EAAE,iBAAiB,CAAC,CAAC;YAC9E,MAAM,eAAe,CAAC,IAAI,CAAC,IAAI,EAAE,IAAI,CAAC,CAAC;YACvC,MAAM,MAAM,CAAC,aAAa,EAAE,IAAI,CAAC,IAAI,CAAC,CAAC;QACzC,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,MAAM,MAAM,EAAE,KAAK,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;YAC7C,MAAM,MAAM,CAAC,aAAa,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;YACnD,IAAI,KAAK,YAAY,aAAa;gBAAE,MAAM,KAAK,CAAC;YAChD,MAAM,YAAY,CAAC,KAAK,EAAE,oBAAoB,CAAC,CAAC;QAClD,CAAC;IACH,CAAC;IAED,KAAK,CAAC,YAAY,CAAC,MAAoB;QACrC,MAAM,SAAS,GAAG,OAAO,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACrC,MAAM,uBAAuB,CAAC,SAAS,EAAE,IAAI,CAAC,SAAS,CAAC,CAAC;QACzD,MAAM,QAAQ,GAAG,GAAG,IAAI,CAAC,IAAI,OAAO,CAAC;QACrC,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,EAAE,GAAG,IAAI,CAAC,cAAc,CAAC;QACnD,SAAS,CAAC;YACR,cAAc,CAAC,MAAM,CAAC,CAAC;YACvB,MAAM,eAAe,CAAC,QAAQ,EAAE,IAAI,CAAC,CAAC;YACtC,IAAI,CAAC;gBACH,OAAO,MAAM,IAAI,CAAC,QAAQ,EAAE,IAAI,EAAE,iBAAiB,CAAC,CAAC;YACvD,CAAC;YAAC,OAAO,KAAK,EAAE,CAAC;gBACf,IAAI,CAAC,SAAS,CAAC,KAAK,EAAE,QAAQ,CAAC;oBAAE,MAAM,YAAY,CAAC,KAAK,EAAE,oBAAoB,CAAC,CAAC;YACnF,CAAC;YACD,IAAI,IAAI,CAAC,IAAI,EAAE,IAAI,QAAQ;gBACzB,MAAM,IAAI,aAAa,CAAC,oBAAoB,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,CAAC,CAAC;YACrE,MAAM,IAAI,CAAC,MAAM,CAAC,IAAI,CAAC,YAAY,EAAE,MAAM,CAAC,CAAC;QAC/C,CAAC;IACH,CAAC;IAED,KAAK,CAAC,YAAY,CAAC,MAAkB;QACnC,MAAM,QAAQ,GAAG,GAAG,IAAI,CAAC,IAAI,OAAO,CAAC;QACrC,IAAI,UAAU,GAAG,KAAK,CAAC;QACvB,IAAI,CAAC;YACH,MAAM,IAAI,GAAG,MAAM,MAAM,CAAC,IAAI,EAAE,CAAC;YACjC,MAAM,OAAO,GAAG,MAAM,KAAK,CAAC,QAAQ,CAAC,CAAC;YACtC,UAAU,GAAG,IAAI,CAAC,GAAG,KAAK,OAAO,CAAC,GAAG,IAAI,IAAI,CAAC,GAAG,KAAK,OAAO,CAAC,GAAG,CAAC;QACpE,CAAC;QAAC,MAAM,CAAC;YACP,UAAU,GAAG,KAAK,CAAC;QACrB,CAAC;QACD,MAAM,MAAM,CAAC,KAAK,EAAE,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;QAC5C,IAAI,UAAU;YAAE,MAAM,MAAM,CAAC,QAAQ,CAAC,CAAC,KAAK,CAAC,GAAG,EAAE,CAAC,SAAS,CAAC,CAAC;IAChE,CAAC;CACF;AAED,SAAS,aAAa,CAAC,QAAgB,EAAE,SAAiB;IACxD,IAAI,KAAc,CAAC;IACnB,IAAI,CAAC;QACH,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,QAAQ,CAAY,CAAC;IAC1C,CAAC;IAAC,MAAM,CAAC;QACP,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;IAC3C,CAAC;IACD,IAAI,CAAC,QAAQ,CAAC,KAAK,CAAC,IAAI,KAAK,CAAC,SAAS,CAAC,KAAK,aAAa,IAAI,KAAK,CAAC,WAAW,CAAC,KAAK,SAAS,EAAE,CAAC;QAC/F,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;IAC3C,CAAC;IACD,MAAM,WAAW,GAAG,KAAK,CAAC,UAAU,CAAC,CAAC;IACtC,IAAI,CAAC,QAAQ,CAAC,WAAW,CAAC;QAAE,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;IACrE,MAAM,QAAQ,GAAuC,EAAE,CAAC;IACxD,KAAK,MAAM,CAAC,IAAI,EAAE,OAAO,CAAC,IAAI,MAAM,CAAC,OAAO,CAAC,WAAW,CAAC,EAAE,CAAC;QAC1D,qBAAqB,CAAC,IAAI,CAAC,CAAC;QAC5B,eAAe,CAAC,OAAO,CAAC,CAAC;QACzB,QAAQ,CAAC,IAAI,CAAC,GAAG,OAAO,CAAC;IAC3B,CAAC;IACD,OAAO,EAAE,OAAO,EAAE,aAAa,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC;AACzD,CAAC;AAED,SAAS,eAAe,CAAC,KAAc;IACrC,IACE,CAAC,QAAQ,CAAC,KAAK,CAAC;QAChB,CAAC,cAAc,CAAC,KAAK,CAAC,aAAa,CAAC,CAAC;QACrC,CAAC,KAAK,CAAC,cAAc,CAAC,KAAK,SAAS,IAAI,CAAC,cAAc,CAAC,KAAK,CAAC,cAAc,CAAC,CAAC,CAAC;QAC/E,CAAC,KAAK,CAAC,SAAS,CAAC,KAAK,SAAS,IAAI,CAAC,cAAc,CAAC,KAAK,CAAC,SAAS,CAAC,CAAC,CAAC;QACrE,CAAC,cAAc,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACnC,OAAO,KAAK,CAAC,WAAW,CAAC,KAAK,QAAQ;QACtC,CAAC,MAAM,CAAC,QAAQ,CAAC,KAAK,CAAC,WAAW,CAAC,CAAC;QACpC,KAAK,CAAC,WAAW,CAAC,IAAI,CAAC;QACvB,CAAC,cAAc,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QAChC,CAAC,cAAc,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC;QAClC,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC;QAC/B,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,KAAK,CAAC,cAAc,CAAC;QACtC,CAAC,KAAK,CAAC,UAAU,CAAC,KAAK,SAAS,IAAI,CAAC,cAAc,CAAC,KAAK,CAAC,UAAU,CAAC,CAAC,CAAC,EACvE,CAAC;QACD,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;IAC3C,CAAC;AACH,CAAC;AAED,KAAK,UAAU,uBAAuB,CAAC,IAAY,EAAE,QAAyB;IAC5E,IAAI,CAAC;QACH,MAAM,eAAe,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACnC,MAAM,KAAK,CAAC,IAAI,EAAE,EAAE,SAAS,EAAE,IAAI,EAAE,IAAI,EAAE,sBAAsB,EAAE,CAAC,CAAC;QACrE,MAAM,eAAe,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;QACnC,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,IAAI,CAAC,CAAC;QACnC,IAAI,CAAC,QAAQ,CAAC,WAAW,EAAE;YAAE,MAAM,IAAI,aAAa,CAAC,kBAAkB,CAAC,CAAC;QACzE,IAAI,QAAQ,KAAK,OAAO,IAAI,CAAC,QAAQ,CAAC,IAAI,GAAG,gBAAgB,CAAC,KAAK,CAAC,EAAE,CAAC;YACrE,MAAM,IAAI,aAAa,CAAC,kBAAkB,CAAC,CAAC;QAC9C,CAAC;IACH,CAAC;IAAC,OAAO,KAAK,EAAE,CAAC;QACf,IAAI,KAAK,YAAY,aAAa;YAAE,MAAM,KAAK,CAAC;QAChD,MAAM,YAAY,CAAC,KAAK,EAAE,kBAAkB,CAAC,CAAC;IAChD,CAAC;AACH,CAAC;AAED,KAAK,UAAU,eAAe,CAAC,IAAY,EAAE,gBAAyB;IACpE,MAAM,QAAQ,GAAG,OAAO,CAAC,IAAI,CAAC,CAAC;IAC/B,MAAM,IAAI,GAAG,KAAK,CAAC,QAAQ,CAAC,CAAC,IAAI,CAAC;IAClC,MAAM,KAAK,GAAG,QAAQ,CAAC,KAAK,CAAC,IAAI,CAAC,MAAM,CAAC,CAAC,KAAK,CAAC,GAAG,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC;IACrE,IAAI,OAAO,GAAG,IAAI,CAAC;IACnB,KAAK,IAAI,KAAK,GAAG,CAAC,EAAE,KAAK,GAAG,KAAK,CAAC,MAAM,EAAE,KAAK,IAAI,CAAC,EAAE,CAAC;QACrD,OAAO,GAAG,IAAI,CAAC,OAAO,EAAE,KAAK,CAAC,KAAK,CAAC,IAAI,EAAE,CAAC,CAAC;QAC5C,IAAI,CAAC;YACH,MAAM,QAAQ,GAAG,MAAM,KAAK,CAAC,OAAO,CAAC,CAAC;YACtC,IAAI,QAAQ,CAAC,cAAc,EAAE;gBAAE,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;QAC1E,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,IAAI,SAAS,CAAC,KAAK,EAAE,QAAQ,CAAC,IAAI,CAAC,gBAAgB,IAAI,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC;gBAAE,OAAO;YACrF,MAAM,KAAK,CAAC;QACd,CAAC;IACH,CAAC;AACH,CAAC;AAED,SAAS,iBAAiB,CAAC,QAAe,EAAE,QAAyB;IACnE,IAAI,CAAC,QAAQ,CAAC,MAAM,EAAE;QAAE,MAAM,IAAI,aAAa,CAAC,kBAAkB,CAAC,CAAC;IACpE,IAAI,QAAQ,KAAK,OAAO,IAAI,CAAC,QAAQ,CAAC,IAAI,GAAG,gBAAgB,CAAC,KAAK,CAAC,EAAE,CAAC;QACrE,MAAM,IAAI,aAAa,CAAC,kBAAkB,CAAC,CAAC;IAC9C,CAAC;AACH,CAAC;AAED,SAAS,YAAY,CAAC,KAAa,EAAE,KAAa;IAChD,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC;QAAE,MAAM,IAAI,SAAS,CAAC,GAAG,KAAK,yBAAyB,CAAC,CAAC;AACrF,CAAC;AAED,SAAS,qBAAqB,CAAC,KAAa;IAC1C,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC,KAAK,CAAC;QAAE,MAAM,IAAI,aAAa,CAAC,eAAe,CAAC,CAAC;AACvE,CAAC;AAED,SAAS,eAAe,CAAC,KAAa,EAAE,KAAa;IACnD,IAAI,CAAC,MAAM,CAAC,aAAa,CAAC,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC;QAC5C,MAAM,IAAI,UAAU,CAAC,GAAG,KAAK,oBAAoB,CAAC,CAAC;IACrD,OAAO,KAAK,CAAC;AACf,CAAC;AAED,SAAS,YAAY,CACnB,KAAc,EACd,QAAyE;IAEzE,OAAO,IAAI,aAAa,CACtB,SAAS,CAAC,KAAK,EAAE,QAAQ,CAAC,IAAI,SAAS,CAAC,KAAK,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,kBAAkB,CAAC,CAAC,CAAC,QAAQ,CACxF,CAAC;AACJ,CAAC;AAED,SAAS,SAAS,CAAC,KAAc,EAAE,IAAY;IAC7C,OAAO,CACL,KAAK,YAAY,KAAK,IAAI,MAAM,IAAI,KAAK,IAAK,KAA+B,CAAC,IAAI,KAAK,IAAI,CAC5F,CAAC;AACJ,CAAC;AAED,SAAS,QAAQ,CAAC,KAAc;IAC9B,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,KAAK,IAAI,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,KAAK,CAAC,CAAC;AAC9E,CAAC;AAED,SAAS,cAAc,CAAC,KAAc;IACpC,OAAO,OAAO,KAAK,KAAK,QAAQ,IAAI,KAAK,CAAC,MAAM,GAAG,CAAC,CAAC;AACvD,CAAC;AAED,SAAS,UAAU,CACjB,QAAsD,EACtD,IAAY;IAEZ,OAAO,MAAM,CAAC,MAAM,CAAC,QAAQ,EAAE,IAAI,CAAC,CAAC,CAAC,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,SAAS,CAAC;AACpE,CAAC;AAED,SAAS,cAAc,CAAC,MAAoB;IAC1C,IAAI,MAAM,EAAE,OAAO,KAAK,IAAI;QAAE,MAAM,IAAI,aAAa,CAAC,SAAS,CAAC,CAAC;AACnE,CAAC;AAED,SAAS,cAAc,CAAC,YAAoB,EAAE,MAAoB;IAChE,OAAO,IAAI,OAAO,CAAC,CAAC,YAAY,EAAE,MAAM,EAAE,EAAE;QAC1C,IAAI,MAAM,EAAE,OAAO,KAAK,IAAI,EAAE,CAAC;YAC7B,MAAM,CAAC,IAAI,aAAa,CAAC,SAAS,CAAC,CAAC,CAAC;YACrC,OAAO;QACT,CAAC;QACD,MAAM,OAAO,GAAG,GAAS,EAAE;YACzB,YAAY,CAAC,OAAO,CAAC,CAAC;YACtB,MAAM,CAAC,IAAI,aAAa,CAAC,SAAS,CAAC,CAAC,CAAC;QACvC,CAAC,CAAC;QACF,MAAM,OAAO,GAAG,UAAU,CAAC,GAAG,EAAE;YAC9B,MAAM,EAAE,mBAAmB,CAAC,OAAO,EAAE,OAAO,CAAC,CAAC;YAC9C,YAAY,EAAE,CAAC;QACjB,CAAC,EAAE,YAAY,CAAC,CAAC;QACjB,MAAM,EAAE,gBAAgB,CAAC,OAAO,EAAE,OAAO,EAAE,EAAE,IAAI,EAAE,IAAI,EAAE,CAAC,CAAC;IAC7D,CAAC,CAAC,CAAC;AACL,CAAC"}
@@ -0,0 +1,80 @@
1
+ import { type CachedTokenProfile, type NodeTokenCacheOptions } from './cache.js';
2
+ export interface EndpointPolicy {
3
+ /** Additional issuer values accepted when discovery returns an alias. */
4
+ readonly issuerAllowlist?: readonly string[];
5
+ /** Additional origins allowed for discovered token and device endpoints. */
6
+ readonly endpointOriginAllowlist?: readonly string[];
7
+ /** Permits plain HTTP only for localhost and literal loopback addresses. */
8
+ readonly allowLoopbackHttp?: boolean;
9
+ }
10
+ export interface DeviceFlowClientConfig {
11
+ readonly issuer: string;
12
+ readonly clientId: string;
13
+ readonly scopes?: readonly string[];
14
+ readonly audience?: string;
15
+ readonly cache: Pick<NodeTokenCacheOptions, 'namespace'> & Partial<Omit<NodeTokenCacheOptions, 'namespace'>>;
16
+ readonly profile?: string;
17
+ readonly endpointPolicy?: EndpointPolicy;
18
+ readonly maxResponseBytes?: number;
19
+ readonly requestTimeoutMs?: number;
20
+ readonly loginTimeoutMs?: number;
21
+ readonly refreshLeewaySeconds?: number;
22
+ }
23
+ export type DeviceFlowStatus = 'waiting' | 'slow-down' | 'authorized';
24
+ export interface DeviceVerification {
25
+ readonly verificationUri: string;
26
+ readonly verificationUriComplete?: string;
27
+ readonly userCode: string;
28
+ }
29
+ export interface DeviceFlowPresentation {
30
+ readonly showVerification?: (verification: DeviceVerification) => void | Promise<void>;
31
+ readonly showStatus?: (status: DeviceFlowStatus) => void | Promise<void>;
32
+ readonly openBrowser?: (url: string) => void | Promise<void>;
33
+ }
34
+ export interface DeviceFlowEnvironment {
35
+ readonly fetch?: typeof globalThis.fetch;
36
+ readonly now?: () => number;
37
+ readonly sleep?: (milliseconds: number, signal?: AbortSignal) => Promise<void>;
38
+ readonly signal?: AbortSignal;
39
+ readonly environmentToken?: () => string | undefined | Promise<string | undefined>;
40
+ }
41
+ export interface AccessTokenOptions {
42
+ readonly forceRefresh?: boolean;
43
+ readonly signal?: AbortSignal;
44
+ }
45
+ export interface LoginOptions {
46
+ readonly signal?: AbortSignal;
47
+ readonly presentation?: DeviceFlowPresentation;
48
+ }
49
+ export interface OidcDeviceMetadata {
50
+ readonly issuer: string;
51
+ readonly deviceAuthorizationEndpoint: string;
52
+ readonly tokenEndpoint: string;
53
+ }
54
+ export interface DisplayOnlyClaims {
55
+ readonly subject?: string;
56
+ readonly name?: string;
57
+ readonly preferredUsername?: string;
58
+ readonly email?: string;
59
+ readonly expiresAt?: number;
60
+ }
61
+ /** Node OIDC device-flow client. It never writes to stdout, stderr, or a logger. */
62
+ export declare class DeviceFlowClient {
63
+ #private;
64
+ constructor(config: DeviceFlowClientConfig, environment?: DeviceFlowEnvironment);
65
+ discover(signal?: AbortSignal): Promise<OidcDeviceMetadata>;
66
+ login(options?: LoginOptions): Promise<CachedTokenProfile>;
67
+ accessToken(options?: AccessTokenOptions): Promise<string>;
68
+ logout(signal?: AbortSignal): Promise<boolean>;
69
+ /** Returns unverified claims for display text only. Never use them for authorization or identity keys. */
70
+ displayClaims(): Promise<DisplayOnlyClaims | undefined>;
71
+ }
72
+ export interface DeviceProviderRequestOptions {
73
+ readonly maxResponseBytes: number;
74
+ readonly requestTimeoutMs: number;
75
+ readonly signal?: AbortSignal;
76
+ }
77
+ export declare function discoverDeviceProvider(configuredIssuer: string, policy: EndpointPolicy, fetchImplementation: typeof globalThis.fetch, options: DeviceProviderRequestOptions): Promise<OidcDeviceMetadata>;
78
+ /** Decodes a small allowlist of unverified JWT claims for display text only. */
79
+ export declare function decodeDisplayOnlyClaims(token: string): DisplayOnlyClaims | undefined;
80
+ //# sourceMappingURL=device-flow.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"device-flow.d.ts","sourceRoot":"","sources":["../src/device-flow.ts"],"names":[],"mappings":"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"}