@nestjs-kit/better-auth 0.0.0-stage → 2.1.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 (142) hide show
  1. package/LICENSE +7 -0
  2. package/README.md +1078 -2
  3. package/dist/admin.cjs +88 -0
  4. package/dist/admin.cjs.map +1 -0
  5. package/dist/admin.d.cts +14 -0
  6. package/dist/admin.d.cts.map +1 -0
  7. package/dist/admin.d.mts +14 -0
  8. package/dist/admin.d.mts.map +1 -0
  9. package/dist/admin.mjs +85 -0
  10. package/dist/admin.mjs.map +1 -0
  11. package/dist/api-key.cjs +164 -0
  12. package/dist/api-key.cjs.map +1 -0
  13. package/dist/api-key.d.cts +42 -0
  14. package/dist/api-key.d.cts.map +1 -0
  15. package/dist/api-key.d.mts +42 -0
  16. package/dist/api-key.d.mts.map +1 -0
  17. package/dist/api-key.mjs +160 -0
  18. package/dist/api-key.mjs.map +1 -0
  19. package/dist/auth-contracts-Brh_Qko9.d.cts +1654 -0
  20. package/dist/auth-contracts-Brh_Qko9.d.cts.map +1 -0
  21. package/dist/auth-contracts-Cz7C4_Ch.d.mts +1654 -0
  22. package/dist/auth-contracts-Cz7C4_Ch.d.mts.map +1 -0
  23. package/dist/auth-decorators-B1mFnGJ6.mjs +284 -0
  24. package/dist/auth-decorators-B1mFnGJ6.mjs.map +1 -0
  25. package/dist/auth-decorators-Cu_nxWnF.cjs +421 -0
  26. package/dist/auth-decorators-Cu_nxWnF.cjs.map +1 -0
  27. package/dist/auth-errors-C3rbTV9p.mjs +301 -0
  28. package/dist/auth-errors-C3rbTV9p.mjs.map +1 -0
  29. package/dist/auth-errors-DmiKl0L_.cjs +378 -0
  30. package/dist/auth-errors-DmiKl0L_.cjs.map +1 -0
  31. package/dist/auth-guard-CLyhAEEj.cjs +136 -0
  32. package/dist/auth-guard-CLyhAEEj.cjs.map +1 -0
  33. package/dist/auth-guard-h9QB_l11.mjs +125 -0
  34. package/dist/auth-guard-h9QB_l11.mjs.map +1 -0
  35. package/dist/auth-module-BgcY2HpA.cjs +2809 -0
  36. package/dist/auth-module-BgcY2HpA.cjs.map +1 -0
  37. package/dist/auth-module-CtHx3gRU.mjs +2708 -0
  38. package/dist/auth-module-CtHx3gRU.mjs.map +1 -0
  39. package/dist/auth-scope-interceptor-BjxAL1-S.cjs +290 -0
  40. package/dist/auth-scope-interceptor-BjxAL1-S.cjs.map +1 -0
  41. package/dist/auth-scope-interceptor-DYPn3b8M.mjs +231 -0
  42. package/dist/auth-scope-interceptor-DYPn3b8M.mjs.map +1 -0
  43. package/dist/bridge-protocol-BDw8opAG.cjs +25 -0
  44. package/dist/bridge-protocol-BDw8opAG.cjs.map +1 -0
  45. package/dist/bridge-protocol-c66aEkr5.mjs +8 -0
  46. package/dist/bridge-protocol-c66aEkr5.mjs.map +1 -0
  47. package/dist/decorate-Cr4Q7bNE.cjs +319 -0
  48. package/dist/decorate-Cr4Q7bNE.cjs.map +1 -0
  49. package/dist/decorate-Dt0e9K6R.mjs +80 -0
  50. package/dist/decorate-Dt0e9K6R.mjs.map +1 -0
  51. package/dist/express.cjs +256 -0
  52. package/dist/express.cjs.map +1 -0
  53. package/dist/express.d.cts +37 -0
  54. package/dist/express.d.cts.map +1 -0
  55. package/dist/express.d.mts +37 -0
  56. package/dist/express.d.mts.map +1 -0
  57. package/dist/express.mjs +254 -0
  58. package/dist/express.mjs.map +1 -0
  59. package/dist/fastify.cjs +218 -0
  60. package/dist/fastify.cjs.map +1 -0
  61. package/dist/fastify.d.cts +28 -0
  62. package/dist/fastify.d.cts.map +1 -0
  63. package/dist/fastify.d.mts +28 -0
  64. package/dist/fastify.d.mts.map +1 -0
  65. package/dist/fastify.mjs +216 -0
  66. package/dist/fastify.mjs.map +1 -0
  67. package/dist/graphql.cjs +509 -0
  68. package/dist/graphql.cjs.map +1 -0
  69. package/dist/graphql.d.cts +38 -0
  70. package/dist/graphql.d.cts.map +1 -0
  71. package/dist/graphql.d.mts +38 -0
  72. package/dist/graphql.d.mts.map +1 -0
  73. package/dist/graphql.mjs +503 -0
  74. package/dist/graphql.mjs.map +1 -0
  75. package/dist/index.cjs +86 -0
  76. package/dist/index.d.cts +2 -0
  77. package/dist/index.d.mts +2 -0
  78. package/dist/index.mjs +8 -0
  79. package/dist/microservices.cjs +231 -0
  80. package/dist/microservices.cjs.map +1 -0
  81. package/dist/microservices.d.cts +39 -0
  82. package/dist/microservices.d.cts.map +1 -0
  83. package/dist/microservices.d.mts +39 -0
  84. package/dist/microservices.d.mts.map +1 -0
  85. package/dist/microservices.mjs +222 -0
  86. package/dist/microservices.mjs.map +1 -0
  87. package/dist/organization.cjs +191 -0
  88. package/dist/organization.cjs.map +1 -0
  89. package/dist/organization.d.cts +40 -0
  90. package/dist/organization.d.cts.map +1 -0
  91. package/dist/organization.d.mts +40 -0
  92. package/dist/organization.d.mts.map +1 -0
  93. package/dist/organization.mjs +177 -0
  94. package/dist/organization.mjs.map +1 -0
  95. package/dist/platform-CZl7TY8j.mjs +414 -0
  96. package/dist/platform-CZl7TY8j.mjs.map +1 -0
  97. package/dist/platform-YICqqYv6.cjs +473 -0
  98. package/dist/platform-YICqqYv6.cjs.map +1 -0
  99. package/dist/platform.cjs +10 -0
  100. package/dist/platform.d.cts +43 -0
  101. package/dist/platform.d.cts.map +1 -0
  102. package/dist/platform.d.mts +43 -0
  103. package/dist/platform.d.mts.map +1 -0
  104. package/dist/platform.mjs +1 -0
  105. package/dist/plugin.cjs +323 -0
  106. package/dist/plugin.cjs.map +1 -0
  107. package/dist/plugin.d.cts +24 -0
  108. package/dist/plugin.d.cts.map +1 -0
  109. package/dist/plugin.d.mts +24 -0
  110. package/dist/plugin.d.mts.map +1 -0
  111. package/dist/plugin.mjs +321 -0
  112. package/dist/plugin.mjs.map +1 -0
  113. package/dist/principal-readings-Chmt6rQV.cjs +208 -0
  114. package/dist/principal-readings-Chmt6rQV.cjs.map +1 -0
  115. package/dist/principal-readings-Ied2staw.mjs +191 -0
  116. package/dist/principal-readings-Ied2staw.mjs.map +1 -0
  117. package/dist/rolldown-runtime-VH7oDXx4.cjs +28 -0
  118. package/dist/testing/conformance.cjs +6214 -0
  119. package/dist/testing/conformance.cjs.map +1 -0
  120. package/dist/testing/conformance.d.cts +528 -0
  121. package/dist/testing/conformance.d.cts.map +1 -0
  122. package/dist/testing/conformance.d.mts +528 -0
  123. package/dist/testing/conformance.d.mts.map +1 -0
  124. package/dist/testing/conformance.mjs +6204 -0
  125. package/dist/testing/conformance.mjs.map +1 -0
  126. package/dist/testing.cjs +221 -0
  127. package/dist/testing.cjs.map +1 -0
  128. package/dist/testing.d.cts +64 -0
  129. package/dist/testing.d.cts.map +1 -0
  130. package/dist/testing.d.mts +64 -0
  131. package/dist/testing.d.mts.map +1 -0
  132. package/dist/testing.mjs +214 -0
  133. package/dist/testing.mjs.map +1 -0
  134. package/dist/websockets.cjs +396 -0
  135. package/dist/websockets.cjs.map +1 -0
  136. package/dist/websockets.d.cts +67 -0
  137. package/dist/websockets.d.cts.map +1 -0
  138. package/dist/websockets.d.mts +67 -0
  139. package/dist/websockets.d.mts.map +1 -0
  140. package/dist/websockets.mjs +383 -0
  141. package/dist/websockets.mjs.map +1 -0
  142. package/package.json +327 -3
@@ -0,0 +1,378 @@
1
+ let better_auth_api = require("better-auth/api");
2
+ //#region src/error-redactor.ts
3
+ /** Reading an arbitrary thrown value must not invoke another escaping fault. */
4
+ function readErrorProperty(value, key) {
5
+ if ((typeof value !== "object" || value === null) && typeof value !== "function") return;
6
+ try {
7
+ return Reflect.get(value, key);
8
+ } catch {
9
+ return;
10
+ }
11
+ }
12
+ var ErrorRedactor = class {
13
+ #secrets;
14
+ constructor(options = {}) {
15
+ const values = /* @__PURE__ */ new Set();
16
+ const add = (value) => {
17
+ if (!value) return;
18
+ values.add(value);
19
+ let decoded = value;
20
+ try {
21
+ decoded = decodeURIComponent(value);
22
+ values.add(decoded);
23
+ } catch {}
24
+ for (const form of [value, decoded]) {
25
+ const separator = form.lastIndexOf(".");
26
+ if (separator >= 16) values.add(form.slice(0, separator));
27
+ }
28
+ };
29
+ for (const value of options.secrets ?? []) add(value);
30
+ const headers = options.headers;
31
+ for (const cookie of (headers?.get("cookie") ?? "").split(";")) {
32
+ const separator = cookie.indexOf("=");
33
+ if (separator >= 0) {
34
+ const value = cookie.slice(separator + 1).trim();
35
+ add(value);
36
+ if (value.startsWith("\"") && value.endsWith("\"")) add(value.slice(1, -1));
37
+ }
38
+ }
39
+ const authorization = headers?.get("authorization");
40
+ if (authorization) {
41
+ add(authorization);
42
+ const credential = /^\S+\s+(.+)$/.exec(authorization)?.[1];
43
+ if (credential) add(credential);
44
+ }
45
+ for (const name of options.credentialHeaders ?? []) {
46
+ const value = headers?.get(name);
47
+ if (value) add(value);
48
+ }
49
+ this.#secrets = [...values].sort((left, right) => right.length - left.length);
50
+ }
51
+ redact(cause) {
52
+ return this.redactCause(cause, 0, /* @__PURE__ */ new Set());
53
+ }
54
+ replaceSecrets(value) {
55
+ for (const secret of this.#secrets) value = value.split(secret).join("[REDACTED]");
56
+ return value;
57
+ }
58
+ diagnostic(value) {
59
+ return this.replaceSecrets(value).split(/[\r\n]/, 1)[0].slice(0, 300);
60
+ }
61
+ redactCause(cause, depth, seen) {
62
+ const message = readErrorProperty(cause, "message");
63
+ const error = new Error(this.diagnostic(typeof message === "string" ? message : typeof cause === "string" ? cause : "Unknown authentication infrastructure failure"));
64
+ const name = readErrorProperty(cause, "name");
65
+ error.name = typeof name === "string" ? this.diagnostic(name) : "Error";
66
+ for (const key of [
67
+ "code",
68
+ "errno",
69
+ "syscall"
70
+ ]) {
71
+ const value = readErrorProperty(cause, key);
72
+ if (typeof value === "string" || typeof value === "number" && Number.isFinite(value)) Object.defineProperty(error, key, {
73
+ value: typeof value === "string" ? this.diagnostic(value) : value,
74
+ enumerable: true
75
+ });
76
+ }
77
+ const stack = readErrorProperty(cause, "stack");
78
+ const frames = typeof stack === "string" ? stack.split(/\r?\n/).filter((line) => /^\s+at .+:\d+:\d+\)?$/.test(line)).map((line) => this.replaceSecrets(line)) : [];
79
+ error.stack = [`${error.name}: ${error.message}`, ...frames].join("\n");
80
+ seen.add(cause);
81
+ const nested = readErrorProperty(cause, "cause");
82
+ if (nested !== void 0 && depth < 3 && !seen.has(nested)) Object.defineProperty(error, "cause", {
83
+ value: this.redactCause(nested, depth + 1, seen),
84
+ enumerable: false
85
+ });
86
+ return error;
87
+ }
88
+ };
89
+ //#endregion
90
+ //#region src/auth-errors.ts
91
+ const FAILURE_BRAND = Symbol.for("@nestjs-kit/better-auth:auth-failure");
92
+ const INFRASTRUCTURE_BRAND = Symbol.for("@nestjs-kit/better-auth:infrastructure-error");
93
+ const CONFIGURATION_BRAND = Symbol.for("@nestjs-kit/better-auth:configuration-error");
94
+ const RAW_CAUSE = Symbol.for("@nestjs-kit/better-auth:raw-cause");
95
+ /** Unredacted causes stay module-private; only an instance's exposeRawCause opt-in attaches one (RAW_CAUSE). */
96
+ const ORIGINAL_CAUSES = /* @__PURE__ */ new WeakMap();
97
+ const SDK_HEADERS = Symbol.for("better-call:api-error-headers");
98
+ function branded(value, brand) {
99
+ Object.defineProperty(value, brand, { value: true });
100
+ return value;
101
+ }
102
+ function isAuthFailure(value) {
103
+ return readErrorProperty(value, FAILURE_BRAND) === true;
104
+ }
105
+ function isInfrastructureError(value) {
106
+ return readErrorProperty(value, INFRASTRUCTURE_BRAND) === true;
107
+ }
108
+ function isConfigurationError(value) {
109
+ return readErrorProperty(value, CONFIGURATION_BRAND) === true;
110
+ }
111
+ function sdkStatus(error) {
112
+ try {
113
+ if (!(0, better_auth_api.isAPIError)(error)) return;
114
+ const status = readErrorProperty(error, "statusCode");
115
+ return typeof status === "number" && Number.isInteger(status) && status >= 100 && status <= 599 ? status : void 0;
116
+ } catch {
117
+ return;
118
+ }
119
+ }
120
+ function sdkReason(error) {
121
+ const reason = readErrorProperty(readErrorProperty(error, "body"), "code");
122
+ return typeof reason === "string" ? reason : void 0;
123
+ }
124
+ /** Internal: preserve cookie lines for the exchange's separately governed cleanup. */
125
+ function getAPIErrorHeaders(error) {
126
+ const result = new Headers();
127
+ for (const value of [readErrorProperty(error, SDK_HEADERS), readErrorProperty(error, "headers")]) {
128
+ if (value === void 0 || value === null) continue;
129
+ try {
130
+ const headers = new Headers(value);
131
+ for (const [name, value] of headers) if (name !== "set-cookie") result.set(name, value);
132
+ for (const cookie of headers.getSetCookie()) result.append("set-cookie", cookie);
133
+ } catch {}
134
+ }
135
+ return result;
136
+ }
137
+ function rejection(input) {
138
+ const codes = {
139
+ 401: "UNAUTHENTICATED",
140
+ 403: "FORBIDDEN",
141
+ 429: "RATE_LIMITED"
142
+ };
143
+ const messages = {
144
+ 401: "Unauthorized",
145
+ 403: "Forbidden",
146
+ 429: "Too Many Requests"
147
+ };
148
+ const headers = new Headers();
149
+ const retry = input.retryAfterSeconds;
150
+ if (retry !== void 0 && Number.isFinite(retry) && retry >= 0) headers.set("retry-after", String(Math.ceil(retry)));
151
+ return branded({
152
+ status: input.status,
153
+ code: codes[input.status],
154
+ reason: input.reason,
155
+ message: input.message ?? messages[input.status],
156
+ challenge: input.challenge,
157
+ ...headers.has("retry-after") ? { headers } : {}
158
+ }, FAILURE_BRAND);
159
+ }
160
+ const AuthFailures = {
161
+ unauthenticated(message) {
162
+ return rejection({
163
+ status: 401,
164
+ message
165
+ });
166
+ },
167
+ rejected: rejection,
168
+ forbidden(reason, message) {
169
+ return rejection({
170
+ status: 403,
171
+ reason,
172
+ message
173
+ });
174
+ },
175
+ fromAPIError(error) {
176
+ const status = sdkStatus(error);
177
+ if (status !== 401 && status !== 403 && status !== 429) return null;
178
+ const originalHeaders = getAPIErrorHeaders(error);
179
+ const delay = readErrorProperty(readErrorProperty(readErrorProperty(error, "body"), "details"), "tryAgainIn");
180
+ const failure = rejection({
181
+ status,
182
+ reason: sdkReason(error),
183
+ challenge: originalHeaders.get("www-authenticate") ?? void 0,
184
+ retryAfterSeconds: status === 429 && typeof delay === "number" ? delay / 1e3 : void 0
185
+ });
186
+ const retryAfter = originalHeaders.get("retry-after");
187
+ if (retryAfter !== null) {
188
+ const headers = new Headers(failure.headers);
189
+ headers.set("retry-after", retryAfter);
190
+ return branded({
191
+ ...failure,
192
+ headers
193
+ }, FAILURE_BRAND);
194
+ }
195
+ return failure;
196
+ }
197
+ };
198
+ var BetterAuthConfigurationError = class BetterAuthConfigurationError extends Error {
199
+ code;
200
+ detail;
201
+ site;
202
+ hint;
203
+ phase;
204
+ extensions = {
205
+ code: "INTERNAL_SERVER_ERROR",
206
+ reason: "AUTH_MISCONFIGURED",
207
+ statusCode: 500
208
+ };
209
+ issues;
210
+ constructor(code, detail, hint) {
211
+ super(detail);
212
+ this.name = "BetterAuthConfigurationError";
213
+ this.code = code;
214
+ this.detail = detail;
215
+ this.hint = hint;
216
+ this.phase = "boot";
217
+ branded(this, CONFIGURATION_BRAND);
218
+ }
219
+ static atRequest(code, detail, options) {
220
+ const error = new BetterAuthConfigurationError(code, "Authentication is misconfigured", options?.hint);
221
+ Object.defineProperties(error, {
222
+ detail: {
223
+ value: detail,
224
+ enumerable: true
225
+ },
226
+ site: {
227
+ value: options?.site,
228
+ enumerable: true
229
+ },
230
+ phase: {
231
+ value: "request",
232
+ enumerable: true
233
+ }
234
+ });
235
+ return error;
236
+ }
237
+ };
238
+ var BetterAuthInfrastructureError = class extends Error {
239
+ cause;
240
+ extensions = {
241
+ code: "INTERNAL_SERVER_ERROR",
242
+ reason: "AUTH_UNAVAILABLE",
243
+ statusCode: 500
244
+ };
245
+ constructor(cause, options) {
246
+ super("Authentication service unavailable");
247
+ this.name = "BetterAuthInfrastructureError";
248
+ this.cause = new ErrorRedactor(options).redact(cause);
249
+ ORIGINAL_CAUSES.set(this, cause);
250
+ branded(this, INFRASTRUCTURE_BRAND);
251
+ }
252
+ };
253
+ /** Internal factory for an instance's explicit diagnostic opt-in, never global state. */
254
+ function createInfrastructureError(cause, options) {
255
+ const error = new BetterAuthInfrastructureError(cause, options);
256
+ if (options?.exposeRawCause === true) Object.defineProperty(error, RAW_CAUSE, {
257
+ value: cause,
258
+ enumerable: false
259
+ });
260
+ return error;
261
+ }
262
+ /**
263
+ * Internal: the form of an already-classified infrastructure error that one request delivers. The request's cookie,
264
+ * authorization and declared credential values are redacted on top of the thrower's own redaction, and the original
265
+ * cause is attached only when the instance opts in, as for errors the kernel classifies itself.
266
+ */
267
+ function redactForRequest(error, options) {
268
+ const original = ORIGINAL_CAUSES.has(error) ? ORIGINAL_CAUSES.get(error) : readErrorProperty(error, RAW_CAUSE);
269
+ const delivered = new BetterAuthInfrastructureError(readErrorProperty(error, "cause"), options);
270
+ ORIGINAL_CAUSES.set(delivered, original);
271
+ if (options.exposeRawCause === true && original !== void 0) Object.defineProperty(delivered, RAW_CAUSE, {
272
+ value: original,
273
+ enumerable: false
274
+ });
275
+ return delivered;
276
+ }
277
+ function getRawCause(error) {
278
+ return readErrorProperty(error, RAW_CAUSE);
279
+ }
280
+ /** Internal safety net. Evaluation performs the authoritative session-loss recheck. */
281
+ function normalizeThrown(error, where, site, secrets, options) {
282
+ if (isAuthFailure(error)) return error;
283
+ if (isInfrastructureError(error) || isConfigurationError(error)) throw error;
284
+ const status = sdkStatus(error);
285
+ const reason = sdkReason(error);
286
+ if (status === 429) return AuthFailures.fromAPIError(error);
287
+ if (status === 401 && where === "policy" && (reason === void 0 || reason === "UNAUTHORIZED")) return {
288
+ sessionLoss: error,
289
+ reason
290
+ };
291
+ if (status === 401 || status === 403) return where === "source" ? AuthFailures.fromAPIError(error) : AuthFailures.forbidden(reason ?? "FORBIDDEN");
292
+ if (status !== void 0 && status < 500) throw BetterAuthConfigurationError.atRequest("BETTER_AUTH_REJECTED_CALL", `better-auth rejected the library's call (${status} ${reason})`, { site });
293
+ throw createInfrastructureError(error, {
294
+ secrets,
295
+ exposeRawCause: options?.exposeRawCause
296
+ });
297
+ }
298
+ //#endregion
299
+ Object.defineProperty(exports, "AuthFailures", {
300
+ enumerable: true,
301
+ get: function() {
302
+ return AuthFailures;
303
+ }
304
+ });
305
+ Object.defineProperty(exports, "BetterAuthConfigurationError", {
306
+ enumerable: true,
307
+ get: function() {
308
+ return BetterAuthConfigurationError;
309
+ }
310
+ });
311
+ Object.defineProperty(exports, "BetterAuthInfrastructureError", {
312
+ enumerable: true,
313
+ get: function() {
314
+ return BetterAuthInfrastructureError;
315
+ }
316
+ });
317
+ Object.defineProperty(exports, "ErrorRedactor", {
318
+ enumerable: true,
319
+ get: function() {
320
+ return ErrorRedactor;
321
+ }
322
+ });
323
+ Object.defineProperty(exports, "createInfrastructureError", {
324
+ enumerable: true,
325
+ get: function() {
326
+ return createInfrastructureError;
327
+ }
328
+ });
329
+ Object.defineProperty(exports, "getAPIErrorHeaders", {
330
+ enumerable: true,
331
+ get: function() {
332
+ return getAPIErrorHeaders;
333
+ }
334
+ });
335
+ Object.defineProperty(exports, "getRawCause", {
336
+ enumerable: true,
337
+ get: function() {
338
+ return getRawCause;
339
+ }
340
+ });
341
+ Object.defineProperty(exports, "isAuthFailure", {
342
+ enumerable: true,
343
+ get: function() {
344
+ return isAuthFailure;
345
+ }
346
+ });
347
+ Object.defineProperty(exports, "isConfigurationError", {
348
+ enumerable: true,
349
+ get: function() {
350
+ return isConfigurationError;
351
+ }
352
+ });
353
+ Object.defineProperty(exports, "isInfrastructureError", {
354
+ enumerable: true,
355
+ get: function() {
356
+ return isInfrastructureError;
357
+ }
358
+ });
359
+ Object.defineProperty(exports, "normalizeThrown", {
360
+ enumerable: true,
361
+ get: function() {
362
+ return normalizeThrown;
363
+ }
364
+ });
365
+ Object.defineProperty(exports, "readErrorProperty", {
366
+ enumerable: true,
367
+ get: function() {
368
+ return readErrorProperty;
369
+ }
370
+ });
371
+ Object.defineProperty(exports, "redactForRequest", {
372
+ enumerable: true,
373
+ get: function() {
374
+ return redactForRequest;
375
+ }
376
+ });
377
+
378
+ //# sourceMappingURL=auth-errors-DmiKl0L_.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-errors-DmiKl0L_.cjs","names":["isAPIError"],"sources":["../src/error-redactor.ts","../src/auth-errors.ts"],"sourcesContent":["/** Inputs come from the active request's owner; the redactor retains no scope. */\nexport interface ErrorRedactorOptions {\n secrets?: readonly string[];\n headers?: Headers;\n credentialHeaders?: readonly string[];\n}\n\n/** Reading an arbitrary thrown value must not invoke another escaping fault. */\nexport function readErrorProperty(value: unknown, key: PropertyKey): unknown {\n if (\n (typeof value !== \"object\" || value === null) &&\n typeof value !== \"function\"\n ) {\n return undefined;\n }\n try {\n return Reflect.get(value, key);\n } catch {\n return undefined;\n }\n}\n\nexport class ErrorRedactor {\n readonly #secrets: readonly string[];\n\n constructor(options: ErrorRedactorOptions = {}) {\n const values = new Set<string>();\n const add = (value: string) => {\n if (!value) {\n return;\n }\n values.add(value);\n let decoded = value;\n try {\n decoded = decodeURIComponent(value);\n values.add(decoded);\n } catch {\n // Invalid escaping must not prevent redaction of the raw credential.\n }\n for (const form of [value, decoded]) {\n const separator = form.lastIndexOf(\".\");\n if (separator >= 16) {\n values.add(form.slice(0, separator));\n }\n }\n };\n for (const value of options.secrets ?? []) {\n add(value);\n }\n const headers = options.headers;\n for (const cookie of (headers?.get(\"cookie\") ?? \"\").split(\";\")) {\n const separator = cookie.indexOf(\"=\");\n if (separator >= 0) {\n const value = cookie.slice(separator + 1).trim();\n add(value);\n if (value.startsWith('\"') && value.endsWith('\"')) {\n add(value.slice(1, -1));\n }\n }\n }\n const authorization = headers?.get(\"authorization\");\n if (authorization) {\n add(authorization);\n const credential = /^\\S+\\s+(.+)$/.exec(authorization)?.[1];\n if (credential) {\n add(credential);\n }\n }\n for (const name of options.credentialHeaders ?? []) {\n const value = headers?.get(name);\n if (value) {\n add(value);\n }\n }\n this.#secrets = [...values].sort(\n (left, right) => right.length - left.length,\n );\n }\n\n redact(cause: unknown): Error {\n return this.redactCause(cause, 0, new Set());\n }\n\n private replaceSecrets(value: string): string {\n for (const secret of this.#secrets) {\n value = value.split(secret).join(\"[REDACTED]\");\n }\n return value;\n }\n\n private diagnostic(value: string): string {\n return this.replaceSecrets(value)\n .split(/[\\r\\n]/, 1)[0]\n .slice(0, 300);\n }\n\n private redactCause(\n cause: unknown,\n depth: number,\n seen: Set<unknown>,\n ): Error {\n const message = readErrorProperty(cause, \"message\");\n const error = new Error(\n this.diagnostic(\n typeof message === \"string\"\n ? message\n : typeof cause === \"string\"\n ? cause\n : \"Unknown authentication infrastructure failure\",\n ),\n );\n const name = readErrorProperty(cause, \"name\");\n error.name = typeof name === \"string\" ? this.diagnostic(name) : \"Error\";\n for (const key of [\"code\", \"errno\", \"syscall\"] as const) {\n const value = readErrorProperty(cause, key);\n if (\n typeof value === \"string\" ||\n (typeof value === \"number\" && Number.isFinite(value))\n ) {\n Object.defineProperty(error, key, {\n value: typeof value === \"string\" ? this.diagnostic(value) : value,\n enumerable: true,\n });\n }\n }\n const stack = readErrorProperty(cause, \"stack\");\n const frames =\n typeof stack === \"string\"\n ? stack\n .split(/\\r?\\n/)\n .filter((line) => /^\\s+at .+:\\d+:\\d+\\)?$/.test(line))\n .map((line) => this.replaceSecrets(line))\n : [];\n error.stack = [`${error.name}: ${error.message}`, ...frames].join(\"\\n\");\n seen.add(cause);\n const nested = readErrorProperty(cause, \"cause\");\n if (nested !== undefined && depth < 3 && !seen.has(nested)) {\n Object.defineProperty(error, \"cause\", {\n value: this.redactCause(nested, depth + 1, seen),\n enumerable: false,\n });\n }\n return error;\n }\n}\n","import type { ExecutionContext } from \"@nestjs/common\";\nimport { isAPIError } from \"better-auth/api\";\nimport {\n ErrorRedactor,\n type ErrorRedactorOptions,\n readErrorProperty,\n} from \"./error-redactor.js\";\n\nconst FAILURE_BRAND = Symbol.for(\"@nestjs-kit/better-auth:auth-failure\");\nconst INFRASTRUCTURE_BRAND = Symbol.for(\n \"@nestjs-kit/better-auth:infrastructure-error\",\n);\nconst CONFIGURATION_BRAND = Symbol.for(\n \"@nestjs-kit/better-auth:configuration-error\",\n);\nconst RAW_CAUSE = Symbol.for(\"@nestjs-kit/better-auth:raw-cause\");\n/** Unredacted causes stay module-private; only an instance's exposeRawCause opt-in attaches one (RAW_CAUSE). */\nconst ORIGINAL_CAUSES = new WeakMap<object, unknown>();\nconst SDK_HEADERS = Symbol.for(\"better-call:api-error-headers\");\n\nexport type AuthErrorCode = \"UNAUTHENTICATED\" | \"FORBIDDEN\" | \"RATE_LIMITED\";\n\n/** A transport-neutral denial. Only transports make it throwable. */\nexport interface AuthFailure {\n readonly status: 401 | 403 | 429;\n readonly code: AuthErrorCode;\n readonly reason?: string;\n readonly message: string;\n readonly challenge?: string;\n readonly headers?: Headers;\n}\n\nexport interface AuthErrorBody {\n statusCode: 401 | 403 | 429;\n error: string;\n code: AuthErrorCode;\n reason?: string;\n message: string;\n}\n\nexport interface AuthGraphqlExtensions {\n code: AuthErrorCode | \"INTERNAL_SERVER_ERROR\";\n reason?: string;\n statusCode: number;\n}\n\nexport interface AuthTransportErrorPayload {\n status: \"error\";\n statusCode: number;\n code: AuthErrorCode;\n reason?: string;\n message: string;\n}\n\nexport interface ErrorMappingOptions {\n map?: (\n failure: AuthFailure,\n context: ExecutionContext,\n transport: string,\n ) => unknown;\n exposeRawCause?: boolean;\n}\n\nfunction branded<T extends object>(value: T, brand: symbol): T {\n Object.defineProperty(value, brand, { value: true });\n return value;\n}\n\nexport function isAuthFailure(value: unknown): value is AuthFailure {\n return readErrorProperty(value, FAILURE_BRAND) === true;\n}\n\nexport function isInfrastructureError(\n value: unknown,\n): value is BetterAuthInfrastructureError {\n return readErrorProperty(value, INFRASTRUCTURE_BRAND) === true;\n}\n\nexport function isConfigurationError(\n value: unknown,\n): value is BetterAuthConfigurationError {\n return readErrorProperty(value, CONFIGURATION_BRAND) === true;\n}\n\nfunction sdkStatus(error: unknown): number | undefined {\n try {\n if (!isAPIError(error)) {\n return undefined;\n }\n const status = readErrorProperty(error, \"statusCode\");\n return typeof status === \"number\" &&\n Number.isInteger(status) &&\n status >= 100 &&\n status <= 599\n ? status\n : undefined;\n } catch {\n return undefined;\n }\n}\n\nfunction sdkReason(error: unknown): string | undefined {\n const reason = readErrorProperty(readErrorProperty(error, \"body\"), \"code\");\n return typeof reason === \"string\" ? reason : undefined;\n}\n\n/** Internal: preserve cookie lines for the exchange's separately governed cleanup. */\nexport function getAPIErrorHeaders(error: unknown): Headers {\n const result = new Headers();\n for (const value of [\n readErrorProperty(error, SDK_HEADERS),\n readErrorProperty(error, \"headers\"),\n ]) {\n if (value === undefined || value === null) {\n continue;\n }\n try {\n const headers = new Headers(value as HeadersInit);\n for (const [name, value] of headers) {\n if (name !== \"set-cookie\") {\n result.set(name, value);\n }\n }\n for (const cookie of headers.getSetCookie()) {\n result.append(\"set-cookie\", cookie);\n }\n } catch {\n // A malformed optional header collection must not mask the original fault.\n }\n }\n return result;\n}\n\nfunction rejection(input: {\n status: 401 | 403 | 429;\n reason?: string;\n message?: string;\n challenge?: string;\n retryAfterSeconds?: number;\n}): AuthFailure {\n const codes = {\n 401: \"UNAUTHENTICATED\",\n 403: \"FORBIDDEN\",\n 429: \"RATE_LIMITED\",\n } as const;\n const messages = {\n 401: \"Unauthorized\",\n 403: \"Forbidden\",\n 429: \"Too Many Requests\",\n } as const;\n const headers = new Headers();\n const retry = input.retryAfterSeconds;\n if (retry !== undefined && Number.isFinite(retry) && retry >= 0) {\n headers.set(\"retry-after\", String(Math.ceil(retry)));\n }\n return branded(\n {\n status: input.status,\n code: codes[input.status],\n reason: input.reason,\n message: input.message ?? messages[input.status],\n challenge: input.challenge,\n ...(headers.has(\"retry-after\") ? { headers } : {}),\n },\n FAILURE_BRAND,\n );\n}\n\nexport const AuthFailures = {\n unauthenticated(message?: string): AuthFailure {\n return rejection({ status: 401, message });\n },\n rejected: rejection,\n forbidden(reason: string, message?: string): AuthFailure {\n return rejection({ status: 403, reason, message });\n },\n fromAPIError(error: unknown): AuthFailure | null {\n const status = sdkStatus(error);\n if (status !== 401 && status !== 403 && status !== 429) {\n return null;\n }\n const originalHeaders = getAPIErrorHeaders(error);\n const details = readErrorProperty(\n readErrorProperty(error, \"body\"),\n \"details\",\n );\n const delay = readErrorProperty(details, \"tryAgainIn\");\n const failure = rejection({\n status,\n reason: sdkReason(error),\n challenge: originalHeaders.get(\"www-authenticate\") ?? undefined,\n retryAfterSeconds:\n status === 429 && typeof delay === \"number\" ? delay / 1000 : undefined,\n });\n const retryAfter = originalHeaders.get(\"retry-after\");\n if (retryAfter !== null) {\n const headers = new Headers(failure.headers);\n headers.set(\"retry-after\", retryAfter);\n return branded({ ...failure, headers }, FAILURE_BRAND);\n }\n return failure;\n },\n};\n\nexport class BetterAuthConfigurationError extends Error {\n readonly code: string;\n readonly detail: string;\n readonly site?: string;\n readonly hint?: string;\n readonly phase: \"boot\" | \"request\";\n readonly extensions = {\n code: \"INTERNAL_SERVER_ERROR\",\n reason: \"AUTH_MISCONFIGURED\",\n statusCode: 500,\n } as const;\n readonly issues?: readonly BetterAuthConfigurationError[];\n\n constructor(code: string, detail: string, hint?: string) {\n super(detail);\n this.name = \"BetterAuthConfigurationError\";\n this.code = code;\n this.detail = detail;\n this.hint = hint;\n this.phase = \"boot\";\n branded(this, CONFIGURATION_BRAND);\n }\n\n static atRequest(\n code: string,\n detail: string,\n options?: { site?: string; hint?: string },\n ): BetterAuthConfigurationError {\n const error = new BetterAuthConfigurationError(\n code,\n \"Authentication is misconfigured\",\n options?.hint,\n );\n Object.defineProperties(error, {\n detail: { value: detail, enumerable: true },\n site: { value: options?.site, enumerable: true },\n phase: { value: \"request\", enumerable: true },\n });\n return error;\n }\n}\n\nexport class BetterAuthInfrastructureError extends Error {\n readonly cause: Error;\n readonly extensions = {\n code: \"INTERNAL_SERVER_ERROR\",\n reason: \"AUTH_UNAVAILABLE\",\n statusCode: 500,\n } as const;\n\n constructor(cause: unknown, options?: { secrets?: readonly string[] }) {\n super(\"Authentication service unavailable\");\n this.name = \"BetterAuthInfrastructureError\";\n this.cause = new ErrorRedactor(options).redact(cause);\n ORIGINAL_CAUSES.set(this, cause);\n branded(this, INFRASTRUCTURE_BRAND);\n }\n}\n\n/** Internal factory for an instance's explicit diagnostic opt-in, never global state. */\nexport function createInfrastructureError(\n cause: unknown,\n options?: ErrorRedactorOptions & { exposeRawCause?: boolean },\n): BetterAuthInfrastructureError {\n // Preserve request-owned redaction inputs without widening the public constructor.\n const error = new BetterAuthInfrastructureError(cause, options);\n if (options?.exposeRawCause === true) {\n Object.defineProperty(error, RAW_CAUSE, {\n value: cause,\n enumerable: false,\n });\n }\n return error;\n}\n\n/**\n * Internal: the form of an already-classified infrastructure error that one request delivers. The request's cookie,\n * authorization and declared credential values are redacted on top of the thrower's own redaction, and the original\n * cause is attached only when the instance opts in, as for errors the kernel classifies itself.\n */\nexport function redactForRequest(\n error: BetterAuthInfrastructureError,\n options: ErrorRedactorOptions & { exposeRawCause?: boolean },\n): BetterAuthInfrastructureError {\n const original = ORIGINAL_CAUSES.has(error)\n ? ORIGINAL_CAUSES.get(error)\n : readErrorProperty(error, RAW_CAUSE);\n const delivered = new BetterAuthInfrastructureError(\n readErrorProperty(error, \"cause\"),\n options,\n );\n ORIGINAL_CAUSES.set(delivered, original);\n if (options.exposeRawCause === true && original !== undefined) {\n Object.defineProperty(delivered, RAW_CAUSE, {\n value: original,\n enumerable: false,\n });\n }\n return delivered;\n}\n\nexport function getRawCause(error: BetterAuthInfrastructureError): unknown {\n return readErrorProperty(error, RAW_CAUSE);\n}\n\n/** Internal: evaluation must distinguish session loss from a failed session read. */\nexport interface SessionLossCandidate {\n readonly sessionLoss: unknown;\n readonly reason?: string;\n}\n\n/** Internal safety net. Evaluation performs the authoritative session-loss recheck. */\nexport function normalizeThrown(\n error: unknown,\n where: \"source\" | \"policy\",\n site: string,\n secrets: readonly string[],\n options?: { exposeRawCause?: boolean },\n): AuthFailure | SessionLossCandidate {\n if (isAuthFailure(error)) {\n return error;\n }\n if (isInfrastructureError(error) || isConfigurationError(error)) {\n throw error;\n }\n const status = sdkStatus(error);\n const reason = sdkReason(error);\n if (status === 429) {\n return AuthFailures.fromAPIError(error)!;\n }\n if (\n status === 401 &&\n where === \"policy\" &&\n (reason === undefined || reason === \"UNAUTHORIZED\")\n ) {\n return { sessionLoss: error, reason };\n }\n if (status === 401 || status === 403) {\n return where === \"source\"\n ? AuthFailures.fromAPIError(error)!\n : AuthFailures.forbidden(reason ?? \"FORBIDDEN\");\n }\n if (status !== undefined && status < 500) {\n throw BetterAuthConfigurationError.atRequest(\n \"BETTER_AUTH_REJECTED_CALL\",\n `better-auth rejected the library's call (${status} ${reason})`,\n { site },\n );\n }\n throw createInfrastructureError(error, {\n secrets,\n exposeRawCause: options?.exposeRawCause,\n });\n}\n"],"mappings":"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"}
@@ -0,0 +1,136 @@
1
+ const require_auth_errors = require("./auth-errors-DmiKl0L_.cjs");
2
+ const require_decorate = require("./decorate-Cr4Q7bNE.cjs");
3
+ let _nestjs_common = require("@nestjs/common");
4
+ //#region src/auth-guard.ts
5
+ let BetterAuthGuard = class BetterAuthGuard {
6
+ core;
7
+ static [require_decorate.AUTH_ENHANCER] = "guard";
8
+ [require_decorate.AUTH_ENHANCER] = "guard";
9
+ constructor(core) {
10
+ this.core = core;
11
+ }
12
+ canActivate(context) {
13
+ return this.core.canActivate(context);
14
+ }
15
+ };
16
+ BetterAuthGuard = require_decorate.__decorate([
17
+ (0, _nestjs_common.Injectable)(),
18
+ require_decorate.__decorateParam(0, (0, _nestjs_common.Inject)(require_decorate.GUARD_CORE)),
19
+ require_decorate.__decorateMetadata("design:paramtypes", [typeof Pick === "undefined" ? Object : Pick])
20
+ ], BetterAuthGuard);
21
+ var GuardCore = class {
22
+ instances;
23
+ planner;
24
+ transports;
25
+ resolver;
26
+ evaluator;
27
+ scope;
28
+ readings;
29
+ constructor(instances, planner, transports, resolver, evaluator, scope, readings) {
30
+ this.instances = instances;
31
+ this.planner = planner;
32
+ this.transports = transports;
33
+ this.resolver = resolver;
34
+ this.evaluator = evaluator;
35
+ this.scope = scope;
36
+ this.readings = readings;
37
+ }
38
+ async canActivate(context) {
39
+ let transport;
40
+ let call;
41
+ let plan;
42
+ try {
43
+ plan = this.planner.forContext(context);
44
+ if (plan.access === "inherit") {
45
+ transport = this.transports.find(context);
46
+ const lineage = transport?.lineage?.(context);
47
+ if (lineage && !this.readings.enclosing(lineage, context.getArgs())) {
48
+ call = this.transports.describe(context, transport);
49
+ throw require_auth_errors.BetterAuthConfigurationError.atRequest("NO_ENCLOSING_DECISION", "An inherited invocation has no enclosing guard decision", { site: plan.site });
50
+ }
51
+ if (plan.originCheck !== "form") return true;
52
+ }
53
+ if (plan.access === "public" && plan.originCheck !== "form") {
54
+ const lineage = this.transports.find(context)?.lineage?.(context);
55
+ if (lineage && !plan.nested) this.readings.recordLineage(lineage, {
56
+ outcome: "no-identity",
57
+ instance: plan.instance
58
+ });
59
+ return true;
60
+ }
61
+ transport = this.transports.select(context);
62
+ call = this.transports.describe(context, transport);
63
+ const entry = this.instances.get(plan.instance);
64
+ if (plan.originCheck !== "off") {
65
+ const browser = call.browser;
66
+ if (browser) {
67
+ if (plan.originCheck === "form" || browser.enforce) {
68
+ const failure = await entry.origin.check(browser, plan.originCheck);
69
+ if (failure) throw failure;
70
+ } else await entry.origin.advisory(browser);
71
+ }
72
+ }
73
+ if (plan.access === "inherit") return true;
74
+ if (plan.access === "public") {
75
+ if (!plan.nested) this.readings.record(call, {
76
+ outcome: "no-identity",
77
+ instance: plan.instance
78
+ });
79
+ return true;
80
+ }
81
+ const result = await this.resolver.resolve(call, {
82
+ auth: entry.handle,
83
+ freshness: plan.freshness,
84
+ accepts: plan.accepts,
85
+ sourceSet: plan.sourceSet
86
+ });
87
+ this.readings.record(call, {
88
+ ...result,
89
+ instance: plan.instance
90
+ });
91
+ if (result.outcome === "rejected") throw result.failure;
92
+ if (result.outcome === "absent") {
93
+ if (plan.access === "optional") return true;
94
+ throw require_auth_errors.AuthFailures.unauthenticated();
95
+ }
96
+ if (!plan.accepts.has(result.principal.kind)) throw require_auth_errors.AuthFailures.forbidden("PRINCIPAL_NOT_SUPPORTED");
97
+ const decision = await this.evaluator.evaluate(plan, result.principal, call, entry, context, transport.id);
98
+ if (decision.effect === "deny") throw require_auth_errors.AuthFailures.rejected({
99
+ status: decision.status ?? 403,
100
+ reason: decision.reason,
101
+ message: decision.message,
102
+ challenge: decision.challenge
103
+ });
104
+ return true;
105
+ } catch (error) {
106
+ if (require_auth_errors.isAuthFailure(error) && transport) {
107
+ const mapping = plan && this.instances.get(plan.instance).options.errors?.map;
108
+ throw mapping ? mapping(error, context, transport.id) : transport.toException(error, context);
109
+ }
110
+ if ((require_auth_errors.isConfigurationError(error) || require_auth_errors.isInfrastructureError(error)) && transport) {
111
+ const repeated = call ? this.scope.surfaced(call.key, error, {
112
+ instance: plan?.instance ?? "default",
113
+ site: plan?.site ?? "guard",
114
+ lineage: call.lineage
115
+ }) : false;
116
+ throw transport.toInternalException?.(error, context, { repeated }) ?? error;
117
+ }
118
+ throw error;
119
+ }
120
+ }
121
+ };
122
+ //#endregion
123
+ Object.defineProperty(exports, "BetterAuthGuard", {
124
+ enumerable: true,
125
+ get: function() {
126
+ return BetterAuthGuard;
127
+ }
128
+ });
129
+ Object.defineProperty(exports, "GuardCore", {
130
+ enumerable: true,
131
+ get: function() {
132
+ return GuardCore;
133
+ }
134
+ });
135
+
136
+ //# sourceMappingURL=auth-guard-CLyhAEEj.cjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"auth-guard-CLyhAEEj.cjs","names":["AUTH_ENHANCER","Injectable","Inject","GUARD_CORE","BetterAuthConfigurationError","AuthFailures","isAuthFailure","isConfigurationError","isInfrastructureError"],"sources":["../src/auth-guard.ts"],"sourcesContent":["import {\n Inject,\n Injectable,\n type CanActivate,\n type ExecutionContext,\n} from \"@nestjs/common\";\nimport type {\n AuthTransport,\n PrincipalResolver,\n RoutePlan,\n TransportCall,\n} from \"./auth-contracts.js\";\nimport {\n AuthFailures,\n BetterAuthConfigurationError,\n isAuthFailure,\n isConfigurationError,\n isInfrastructureError,\n} from \"./auth-errors.js\";\nimport { AUTH_ENHANCER, GUARD_CORE } from \"./auth-tokens.js\";\nimport type { AuthorizationEvaluator } from \"./authorization-evaluator.js\";\nimport type { InstanceLookup } from \"./instance-registry.js\";\nimport type { PrincipalReadings } from \"./principal-readings.js\";\nimport type { RequestScope } from \"./request-scope.js\";\nimport type { RoutePlanner } from \"./route-planner.js\";\nimport type { TransportRegistry } from \"./transport-registry.js\";\n\n@Injectable()\nexport class BetterAuthGuard implements CanActivate {\n static readonly [AUTH_ENHANCER] = \"guard\";\n readonly [AUTH_ENHANCER] = \"guard\";\n\n constructor(\n @Inject(GUARD_CORE) private readonly core: Pick<GuardCore, \"canActivate\">,\n ) {}\n\n canActivate(context: ExecutionContext): Promise<boolean> {\n return this.core.canActivate(context);\n }\n}\nexport class GuardCore implements CanActivate {\n constructor(\n private readonly instances: InstanceLookup,\n private readonly planner: RoutePlanner,\n private readonly transports: TransportRegistry,\n private readonly resolver: PrincipalResolver,\n private readonly evaluator: AuthorizationEvaluator,\n private readonly scope: RequestScope,\n private readonly readings: PrincipalReadings,\n ) {}\n\n async canActivate(context: ExecutionContext): Promise<boolean> {\n let transport: AuthTransport | undefined;\n let call: TransportCall | undefined;\n let plan: RoutePlan | undefined;\n try {\n plan = this.planner.forContext(context);\n if (plan.access === \"inherit\") {\n transport = this.transports.find(context);\n const lineage = transport?.lineage?.(context);\n if (lineage && !this.readings.enclosing(lineage, context.getArgs())) {\n call = this.transports.describe(context, transport);\n throw BetterAuthConfigurationError.atRequest(\n \"NO_ENCLOSING_DECISION\",\n \"An inherited invocation has no enclosing guard decision\",\n { site: plan.site },\n );\n }\n if (plan.originCheck !== \"form\") {\n return true;\n }\n }\n if (plan.access === \"public\" && plan.originCheck !== \"form\") {\n const lineage = this.transports.find(context)?.lineage?.(context);\n if (lineage && !plan.nested) {\n this.readings.recordLineage(lineage, {\n outcome: \"no-identity\",\n instance: plan.instance,\n });\n }\n return true;\n }\n transport = this.transports.select(context);\n call = this.transports.describe(context, transport);\n const entry = this.instances.get(plan.instance);\n if (plan.originCheck !== \"off\") {\n const browser = call.browser;\n if (browser) {\n if (plan.originCheck === \"form\" || browser.enforce) {\n const failure = await entry.origin.check(browser, plan.originCheck);\n if (failure) {\n throw failure;\n }\n } else {\n await entry.origin.advisory(browser);\n }\n }\n }\n if (plan.access === \"inherit\") {\n return true;\n }\n if (plan.access === \"public\") {\n if (!plan.nested) {\n this.readings.record(call, {\n outcome: \"no-identity\",\n instance: plan.instance,\n });\n }\n return true;\n }\n const result = await this.resolver.resolve(call, {\n auth: entry.handle,\n freshness: plan.freshness,\n accepts: plan.accepts,\n sourceSet: plan.sourceSet,\n });\n this.readings.record(call, { ...result, instance: plan.instance });\n if (result.outcome === \"rejected\") {\n throw result.failure;\n }\n if (result.outcome === \"absent\") {\n if (plan.access === \"optional\") {\n return true;\n }\n throw AuthFailures.unauthenticated();\n }\n if (!plan.accepts.has(result.principal.kind)) {\n throw AuthFailures.forbidden(\"PRINCIPAL_NOT_SUPPORTED\");\n }\n const decision = await this.evaluator.evaluate(\n plan,\n result.principal,\n call,\n entry,\n context,\n transport.id,\n );\n if (decision.effect === \"deny\") {\n throw AuthFailures.rejected({\n status: decision.status ?? 403,\n reason: decision.reason,\n message: decision.message,\n challenge: decision.challenge,\n });\n }\n return true;\n } catch (error) {\n if (isAuthFailure(error) && transport) {\n const mapping =\n plan && this.instances.get(plan.instance).options.errors?.map;\n throw mapping\n ? mapping(error, context, transport.id)\n : transport.toException(error, context);\n }\n if (\n (isConfigurationError(error) || isInfrastructureError(error)) &&\n transport\n ) {\n const repeated = call\n ? this.scope.surfaced(call.key, error, {\n instance: plan?.instance ?? \"default\",\n site: plan?.site ?? \"guard\",\n lineage: call.lineage,\n })\n : false;\n throw (\n transport.toInternalException?.(error, context, { repeated }) ?? error\n );\n }\n throw error;\n }\n }\n}\n"],"mappings":"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"}