@aura-stack/auth 0.4.0 → 0.5.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/@types/index.d.ts +6 -2
- package/dist/@types/router.d.d.ts +6 -2
- package/dist/actions/callback/access-token.cjs +103 -59
- package/dist/actions/callback/access-token.d.ts +7 -3
- package/dist/actions/callback/access-token.js +3 -3
- package/dist/actions/callback/callback.cjs +200 -134
- package/dist/actions/callback/callback.d.ts +32 -3
- package/dist/actions/callback/callback.js +11 -12
- package/dist/actions/callback/userinfo.cjs +103 -70
- package/dist/actions/callback/userinfo.d.ts +6 -2
- package/dist/actions/callback/userinfo.js +7 -8
- package/dist/actions/csrfToken/csrfToken.cjs +7 -15
- package/dist/actions/csrfToken/csrfToken.d.ts +3 -1
- package/dist/actions/csrfToken/csrfToken.js +7 -8
- package/dist/actions/index.cjs +502 -295
- package/dist/actions/index.d.ts +5 -2
- package/dist/actions/index.js +23 -20
- package/dist/actions/session/session.cjs +76 -24
- package/dist/actions/session/session.d.ts +3 -1
- package/dist/actions/session/session.js +6 -4
- package/dist/actions/signIn/authorization-url.cjs +288 -0
- package/dist/actions/signIn/authorization-url.d.ts +31 -0
- package/dist/actions/signIn/authorization-url.js +16 -0
- package/dist/actions/signIn/authorization.cjs +91 -132
- package/dist/actions/signIn/authorization.d.ts +17 -16
- package/dist/actions/signIn/authorization.js +8 -7
- package/dist/actions/signIn/signIn.cjs +319 -191
- package/dist/actions/signIn/signIn.d.ts +32 -3
- package/dist/actions/signIn/signIn.js +10 -9
- package/dist/actions/signOut/signOut.cjs +211 -212
- package/dist/actions/signOut/signOut.d.ts +9 -1
- package/dist/actions/signOut/signOut.js +9 -10
- package/dist/api/createApi.cjs +750 -0
- package/dist/api/createApi.d.ts +12 -0
- package/dist/api/createApi.js +19 -0
- package/dist/api/getSession.cjs +141 -0
- package/dist/api/getSession.d.ts +16 -0
- package/dist/api/getSession.js +10 -0
- package/dist/api/signIn.cjs +549 -0
- package/dist/api/signIn.d.ts +26 -0
- package/dist/api/signIn.js +15 -0
- package/dist/api/signOut.cjs +279 -0
- package/dist/api/signOut.d.ts +16 -0
- package/dist/api/signOut.js +13 -0
- package/dist/assert.cjs +42 -9
- package/dist/assert.d.ts +8 -4
- package/dist/assert.js +5 -5
- package/dist/{chunk-KJBAQZX2.js → chunk-2A5B7GWR.js} +44 -11
- package/dist/chunk-2GQLSIJ2.js +40 -0
- package/dist/chunk-2IR674WX.js +44 -0
- package/dist/chunk-3J5TUH2I.js +50 -0
- package/dist/chunk-4RWSYUKX.js +98 -0
- package/dist/chunk-5X7JZMEF.js +0 -0
- package/dist/{chunk-TZB6MUXN.js → chunk-7BE46WWS.js} +21 -11
- package/dist/chunk-7YYXFKLR.js +35 -0
- package/dist/chunk-C3A37LQC.js +33 -0
- package/dist/chunk-CITNGXDA.js +31 -0
- package/dist/chunk-CWX724AG.js +78 -0
- package/dist/chunk-D2CSIUKP.js +74 -0
- package/dist/{chunk-ICAZ4OVS.js → chunk-FPCVZUVG.js} +2 -2
- package/dist/{chunk-XGLBNXL4.js → chunk-GNNBM2WJ.js} +17 -9
- package/dist/chunk-JOCGX3RP.js +59 -0
- package/dist/chunk-KBXWTD6E.js +94 -0
- package/dist/{chunk-XUP6KKNG.js → chunk-LATR3NIV.js} +48 -37
- package/dist/chunk-LAYPUDQF.js +39 -0
- package/dist/chunk-LX3TJ2TJ.js +294 -0
- package/dist/{chunk-6MXFPFR3.js → chunk-NHZBQNRR.js} +19 -19
- package/dist/{chunk-TM5IPSNF.js → chunk-PDP3PHB3.js} +33 -19
- package/dist/chunk-PHYNROD4.js +47 -0
- package/dist/chunk-QQEKY4XP.js +29 -0
- package/dist/{chunk-VNCNJKS2.js → chunk-U4RK4LKJ.js} +82 -1
- package/dist/{chunk-RRLIF4PQ.js → chunk-U5663F2U.js} +16 -1
- package/dist/chunk-UN7X6SU5.js +53 -0
- package/dist/chunk-UZQJJD6A.js +100 -0
- package/dist/{chunk-NUDITUKX.js → chunk-V6LLEAR4.js} +22 -15
- package/dist/{chunk-4MYWAOLG.js → chunk-WHNDRO3N.js} +20 -1
- package/dist/{chunk-5W4BRQYG.js → chunk-XY5R3EHH.js} +6 -3
- package/dist/client/client.cjs +135 -0
- package/dist/client/client.d.ts +85 -0
- package/dist/client/client.js +9 -0
- package/dist/client/index.cjs +135 -0
- package/dist/client/index.d.ts +14 -0
- package/dist/client/index.js +10 -0
- package/dist/context.cjs +1237 -0
- package/dist/context.d.ts +16 -0
- package/dist/context.js +28 -0
- package/dist/cookie.cjs +33 -2
- package/dist/cookie.d.ts +9 -5
- package/dist/cookie.js +3 -2
- package/dist/createAuth.cjs +2320 -0
- package/dist/createAuth.d.ts +12 -0
- package/dist/createAuth.js +48 -0
- package/dist/env.cjs +24 -2
- package/dist/env.d.ts +4 -1
- package/dist/env.js +9 -3
- package/dist/errors.cjs +17 -0
- package/dist/errors.d.ts +13 -3
- package/dist/errors.js +5 -1
- package/dist/{index-CSyIJmCM.d.ts → index-_aXtxb_s.d.ts} +383 -13
- package/dist/index.cjs +2135 -1547
- package/dist/index.d.ts +9 -30
- package/dist/index.js +46 -119
- package/dist/jose.cjs +52 -14
- package/dist/jose.d.ts +12 -25
- package/dist/jose.js +11 -3
- package/dist/logger.cjs +132 -0
- package/dist/logger.d.ts +6 -2
- package/dist/logger.js +10 -1
- package/dist/oauth/atlassian.cjs +57 -0
- package/dist/oauth/atlassian.d.ts +12 -0
- package/dist/oauth/atlassian.js +6 -0
- package/dist/oauth/bitbucket.d.ts +6 -2
- package/dist/oauth/discord.d.ts +6 -2
- package/dist/oauth/dropbox.cjs +53 -0
- package/dist/oauth/dropbox.d.ts +12 -0
- package/dist/oauth/dropbox.js +6 -0
- package/dist/oauth/figma.d.ts +6 -2
- package/dist/oauth/github.d.ts +6 -2
- package/dist/oauth/gitlab.d.ts +6 -2
- package/dist/oauth/index.cjs +278 -88
- package/dist/oauth/index.d.ts +6 -2
- package/dist/oauth/index.js +27 -11
- package/dist/oauth/mailchimp.d.ts +6 -2
- package/dist/oauth/notion.cjs +131 -0
- package/dist/oauth/notion.d.ts +12 -0
- package/dist/oauth/notion.js +9 -0
- package/dist/oauth/pinterest.d.ts +6 -2
- package/dist/oauth/spotify.d.ts +6 -2
- package/dist/oauth/strava.d.ts +6 -2
- package/dist/oauth/twitch.cjs +95 -0
- package/dist/oauth/twitch.d.ts +12 -0
- package/dist/oauth/twitch.js +7 -0
- package/dist/oauth/x.d.ts +6 -2
- package/dist/schemas.cjs +84 -51
- package/dist/schemas.d.ts +103 -23
- package/dist/schemas.js +1 -1
- package/dist/secure.cjs +36 -36
- package/dist/secure.d.ts +10 -4
- package/dist/secure.js +7 -6
- package/dist/utils.cjs +109 -3
- package/dist/utils.d.ts +15 -4
- package/dist/utils.js +11 -4
- package/package.json +9 -5
- package/dist/chunk-4EKY7655.js +0 -123
- package/dist/chunk-7QF22LHP.js +0 -67
- package/dist/chunk-ALG3GIV4.js +0 -95
- package/dist/chunk-FRJFWTOY.js +0 -70
- package/dist/chunk-PHFH2MGS.js +0 -36
- package/dist/chunk-QQVSRXGX.js +0 -149
|
@@ -0,0 +1,279 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __defProp = Object.defineProperty;
|
|
3
|
+
var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
|
|
4
|
+
var __getOwnPropNames = Object.getOwnPropertyNames;
|
|
5
|
+
var __hasOwnProp = Object.prototype.hasOwnProperty;
|
|
6
|
+
var __export = (target, all) => {
|
|
7
|
+
for (var name in all)
|
|
8
|
+
__defProp(target, name, { get: all[name], enumerable: true });
|
|
9
|
+
};
|
|
10
|
+
var __copyProps = (to, from, except, desc) => {
|
|
11
|
+
if (from && typeof from === "object" || typeof from === "function") {
|
|
12
|
+
for (let key of __getOwnPropNames(from))
|
|
13
|
+
if (!__hasOwnProp.call(to, key) && key !== except)
|
|
14
|
+
__defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
|
|
15
|
+
}
|
|
16
|
+
return to;
|
|
17
|
+
};
|
|
18
|
+
var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
|
|
19
|
+
|
|
20
|
+
// src/api/signOut.ts
|
|
21
|
+
var signOut_exports = {};
|
|
22
|
+
__export(signOut_exports, {
|
|
23
|
+
signOut: () => signOut
|
|
24
|
+
});
|
|
25
|
+
module.exports = __toCommonJS(signOut_exports);
|
|
26
|
+
|
|
27
|
+
// src/env.ts
|
|
28
|
+
var import_meta = {};
|
|
29
|
+
var env = new Proxy({}, {
|
|
30
|
+
get(_, prop) {
|
|
31
|
+
if (typeof prop !== "string") return void 0;
|
|
32
|
+
const hasProperty = (process2) => {
|
|
33
|
+
return process2 && Object.prototype.hasOwnProperty.call(process2, prop);
|
|
34
|
+
};
|
|
35
|
+
try {
|
|
36
|
+
if (typeof process !== "undefined" && hasProperty(process.env)) {
|
|
37
|
+
return process.env[prop];
|
|
38
|
+
}
|
|
39
|
+
if (typeof import_meta !== "undefined" && hasProperty(import_meta.env)) {
|
|
40
|
+
return import_meta.env[prop];
|
|
41
|
+
}
|
|
42
|
+
if (typeof Deno !== "undefined" && Deno.env?.get) {
|
|
43
|
+
return Deno.env.get(prop);
|
|
44
|
+
}
|
|
45
|
+
if (typeof Bun !== "undefined" && hasProperty(Bun.env)) {
|
|
46
|
+
return Bun.env[prop];
|
|
47
|
+
}
|
|
48
|
+
const globalValue = globalThis[prop];
|
|
49
|
+
return typeof globalValue === "string" ? globalValue : void 0;
|
|
50
|
+
} catch {
|
|
51
|
+
return void 0;
|
|
52
|
+
}
|
|
53
|
+
}
|
|
54
|
+
});
|
|
55
|
+
|
|
56
|
+
// src/cookie.ts
|
|
57
|
+
var import_cookie = require("@aura-stack/router/cookie");
|
|
58
|
+
|
|
59
|
+
// src/errors.ts
|
|
60
|
+
var AuthInternalError = class extends Error {
|
|
61
|
+
type = "AUTH_INTERNAL_ERROR";
|
|
62
|
+
code;
|
|
63
|
+
constructor(code, message, options) {
|
|
64
|
+
super(message, options);
|
|
65
|
+
this.code = code;
|
|
66
|
+
this.name = new.target.name;
|
|
67
|
+
Error.captureStackTrace(this, new.target);
|
|
68
|
+
}
|
|
69
|
+
};
|
|
70
|
+
var AuthSecurityError = class extends Error {
|
|
71
|
+
type = "AUTH_SECURITY_ERROR";
|
|
72
|
+
code;
|
|
73
|
+
constructor(code, message, options) {
|
|
74
|
+
super(message, options);
|
|
75
|
+
this.code = code;
|
|
76
|
+
this.name = new.target.name;
|
|
77
|
+
Error.captureStackTrace(this, new.target);
|
|
78
|
+
}
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
// src/cookie.ts
|
|
82
|
+
var defaultCookieOptions = {
|
|
83
|
+
httpOnly: true,
|
|
84
|
+
sameSite: "lax",
|
|
85
|
+
path: "/",
|
|
86
|
+
maxAge: 60 * 60 * 24 * 15
|
|
87
|
+
};
|
|
88
|
+
var oauthCookieOptions = {
|
|
89
|
+
httpOnly: true,
|
|
90
|
+
maxAge: 5 * 60,
|
|
91
|
+
sameSite: "lax",
|
|
92
|
+
expires: new Date(Date.now() + 5 * 60 * 1e3)
|
|
93
|
+
};
|
|
94
|
+
var expiredCookieAttributes = {
|
|
95
|
+
...defaultCookieOptions,
|
|
96
|
+
expires: /* @__PURE__ */ new Date(0),
|
|
97
|
+
maxAge: 0,
|
|
98
|
+
secure: true
|
|
99
|
+
};
|
|
100
|
+
var getCookie = (request, cookieName) => {
|
|
101
|
+
const cookies = request instanceof Request ? request.headers.get("Cookie") : request.get("Cookie");
|
|
102
|
+
if (!cookies) {
|
|
103
|
+
throw new AuthInternalError("COOKIE_NOT_FOUND", "No cookies found. There is no active session");
|
|
104
|
+
}
|
|
105
|
+
const value = (0, import_cookie.parse)(cookies)[cookieName];
|
|
106
|
+
if (!value) {
|
|
107
|
+
throw new AuthInternalError("COOKIE_NOT_FOUND", `Cookie "${cookieName}" not found. There is no active session`);
|
|
108
|
+
}
|
|
109
|
+
return value;
|
|
110
|
+
};
|
|
111
|
+
|
|
112
|
+
// src/utils.ts
|
|
113
|
+
var import_router = require("@aura-stack/router");
|
|
114
|
+
|
|
115
|
+
// src/assert.ts
|
|
116
|
+
var import_crypto = require("@aura-stack/jose/crypto");
|
|
117
|
+
var isJWTPayloadWithToken = (payload) => {
|
|
118
|
+
return typeof payload === "object" && payload !== null && "token" in payload && typeof payload?.token === "string";
|
|
119
|
+
};
|
|
120
|
+
var timingSafeEqual = (a, b) => {
|
|
121
|
+
const bufferA = import_crypto.encoder.encode(a);
|
|
122
|
+
const bufferB = import_crypto.encoder.encode(b);
|
|
123
|
+
const len = Math.max(bufferA.length, bufferB.length);
|
|
124
|
+
let diff = 0;
|
|
125
|
+
for (let i = 0; i < len; i++) {
|
|
126
|
+
diff |= (bufferA[i] ?? 0) ^ (bufferB[i] ?? 0);
|
|
127
|
+
}
|
|
128
|
+
return diff === 0 && bufferA.length === bufferB.length;
|
|
129
|
+
};
|
|
130
|
+
|
|
131
|
+
// src/utils.ts
|
|
132
|
+
var equals = (a, b) => {
|
|
133
|
+
if (a === null || b === null || a === void 0 || b === void 0) return false;
|
|
134
|
+
return a === b;
|
|
135
|
+
};
|
|
136
|
+
var getErrorName = (error) => {
|
|
137
|
+
if (error instanceof Error) {
|
|
138
|
+
return error.name;
|
|
139
|
+
}
|
|
140
|
+
return typeof error === "string" ? error : "UnknownError";
|
|
141
|
+
};
|
|
142
|
+
|
|
143
|
+
// src/jose.ts
|
|
144
|
+
var import_jose = require("@aura-stack/jose");
|
|
145
|
+
var import_jose2 = require("@aura-stack/jose/jose");
|
|
146
|
+
var import_crypto2 = require("@aura-stack/jose/crypto");
|
|
147
|
+
var jwtVerificationOptions = {
|
|
148
|
+
algorithms: ["HS256"],
|
|
149
|
+
typ: "JWT"
|
|
150
|
+
};
|
|
151
|
+
|
|
152
|
+
// src/secure.ts
|
|
153
|
+
var verifyCSRF = async (jose, cookie, header) => {
|
|
154
|
+
try {
|
|
155
|
+
const cookiePayload = await jose.verifyJWS(cookie, jwtVerificationOptions);
|
|
156
|
+
const headerPayload = await jose.verifyJWS(header, jwtVerificationOptions);
|
|
157
|
+
if (!isJWTPayloadWithToken(cookiePayload)) {
|
|
158
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "Cookie payload missing token field.");
|
|
159
|
+
}
|
|
160
|
+
if (!isJWTPayloadWithToken(headerPayload)) {
|
|
161
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "Header payload missing token field.");
|
|
162
|
+
}
|
|
163
|
+
if (!equals(cookiePayload.token.length, headerPayload.token.length)) {
|
|
164
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "The CSRF tokens do not match.");
|
|
165
|
+
}
|
|
166
|
+
if (!timingSafeEqual(cookiePayload.token, headerPayload.token)) {
|
|
167
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "The CSRF tokens do not match.");
|
|
168
|
+
}
|
|
169
|
+
return true;
|
|
170
|
+
} catch {
|
|
171
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "The CSRF tokens do not match.");
|
|
172
|
+
}
|
|
173
|
+
};
|
|
174
|
+
|
|
175
|
+
// src/headers.ts
|
|
176
|
+
var cacheControl = {
|
|
177
|
+
"Cache-Control": "no-store",
|
|
178
|
+
Pragma: "no-cache",
|
|
179
|
+
Expires: "0",
|
|
180
|
+
Vary: "Cookie"
|
|
181
|
+
};
|
|
182
|
+
var contentSecurityPolicy = {
|
|
183
|
+
"Content-Security-Policy": [
|
|
184
|
+
"default-src 'none'",
|
|
185
|
+
"script-src 'self'",
|
|
186
|
+
"frame-src 'none'",
|
|
187
|
+
"object-src 'none'",
|
|
188
|
+
"frame-ancestors 'none'",
|
|
189
|
+
"base-uri 'none'"
|
|
190
|
+
].join("; ")
|
|
191
|
+
};
|
|
192
|
+
var secureHeaders = {
|
|
193
|
+
"X-Content-Type-Options": "nosniff",
|
|
194
|
+
"X-Frame-Options": "DENY",
|
|
195
|
+
"Referrer-Policy": "strict-origin-when-cross-origin"
|
|
196
|
+
};
|
|
197
|
+
var secureApiHeaders = {
|
|
198
|
+
...cacheControl,
|
|
199
|
+
...contentSecurityPolicy,
|
|
200
|
+
...secureHeaders
|
|
201
|
+
};
|
|
202
|
+
|
|
203
|
+
// src/api/signOut.ts
|
|
204
|
+
var import_router2 = require("@aura-stack/router");
|
|
205
|
+
var signOut = async ({
|
|
206
|
+
ctx,
|
|
207
|
+
headers: headersInit,
|
|
208
|
+
redirectTo = "/",
|
|
209
|
+
skipCSRFCheck = false
|
|
210
|
+
}) => {
|
|
211
|
+
const headers = new Headers(headersInit);
|
|
212
|
+
const header = headers.get("X-CSRF-Token");
|
|
213
|
+
let session = null;
|
|
214
|
+
let csrfToken = null;
|
|
215
|
+
try {
|
|
216
|
+
session = getCookie(headers, ctx.cookies.sessionToken.name);
|
|
217
|
+
} catch {
|
|
218
|
+
throw new AuthSecurityError("SESSION_TOKEN_MISSING", "The sessionToken is missing.");
|
|
219
|
+
}
|
|
220
|
+
try {
|
|
221
|
+
csrfToken = getCookie(headers, ctx.cookies.csrfToken.name);
|
|
222
|
+
} catch {
|
|
223
|
+
throw new AuthSecurityError("CSRF_TOKEN_MISSING", "The CSRF token is missing.");
|
|
224
|
+
}
|
|
225
|
+
ctx?.logger?.log("SIGN_OUT_ATTEMPT", {
|
|
226
|
+
structuredData: {
|
|
227
|
+
has_session: Boolean(session),
|
|
228
|
+
has_csrf_token: Boolean(csrfToken),
|
|
229
|
+
has_csrf_header: Boolean(header),
|
|
230
|
+
skip_csrf_check: skipCSRFCheck
|
|
231
|
+
}
|
|
232
|
+
});
|
|
233
|
+
if (!session) {
|
|
234
|
+
ctx?.logger?.log("SESSION_TOKEN_MISSING");
|
|
235
|
+
throw new AuthSecurityError("SESSION_TOKEN_MISSING", "The sessionToken is missing.");
|
|
236
|
+
}
|
|
237
|
+
if (!skipCSRFCheck) {
|
|
238
|
+
if (!csrfToken) {
|
|
239
|
+
ctx?.logger?.log("CSRF_TOKEN_MISSING");
|
|
240
|
+
throw new AuthSecurityError("CSRF_TOKEN_MISSING", "The CSRF token is missing.");
|
|
241
|
+
}
|
|
242
|
+
if (!header) {
|
|
243
|
+
ctx?.logger?.log("CSRF_HEADER_MISSING");
|
|
244
|
+
throw new AuthSecurityError("CSRF_HEADER_MISSING", "The CSRF header is missing.");
|
|
245
|
+
}
|
|
246
|
+
try {
|
|
247
|
+
await verifyCSRF(ctx.jose, csrfToken, header);
|
|
248
|
+
} catch (error) {
|
|
249
|
+
ctx?.logger?.log("CSRF_TOKEN_INVALID", { structuredData: { error_type: getErrorName(error) } });
|
|
250
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "CSRF token verification failed");
|
|
251
|
+
}
|
|
252
|
+
ctx?.logger?.log("SIGN_OUT_CSRF_VERIFIED");
|
|
253
|
+
} else {
|
|
254
|
+
try {
|
|
255
|
+
await ctx.jose.verifyJWS(csrfToken);
|
|
256
|
+
} catch (error) {
|
|
257
|
+
ctx?.logger?.log("CSRF_TOKEN_INVALID", { structuredData: { error_type: getErrorName(error) } });
|
|
258
|
+
throw new AuthSecurityError("CSRF_TOKEN_INVALID", "CSRF token verification failed");
|
|
259
|
+
}
|
|
260
|
+
}
|
|
261
|
+
try {
|
|
262
|
+
await ctx.jose.decodeJWT(session);
|
|
263
|
+
ctx?.logger?.log("SIGN_OUT_SUCCESS");
|
|
264
|
+
} catch (error) {
|
|
265
|
+
ctx?.logger?.log("INVALID_JWT_TOKEN", { structuredData: { error_type: getErrorName(error) } });
|
|
266
|
+
}
|
|
267
|
+
const headersList = new import_router2.HeadersBuilder(secureApiHeaders).setHeader("Location", redirectTo).setCookie(ctx.cookies.csrfToken.name, "", expiredCookieAttributes).setCookie(ctx.cookies.sessionToken.name, "", expiredCookieAttributes).toHeaders();
|
|
268
|
+
return Response.json(
|
|
269
|
+
{ redirect: Boolean(redirectTo), url: redirectTo },
|
|
270
|
+
{
|
|
271
|
+
status: 202,
|
|
272
|
+
headers: headersList
|
|
273
|
+
}
|
|
274
|
+
);
|
|
275
|
+
};
|
|
276
|
+
// Annotate the CommonJS export names for ESM import in node:
|
|
277
|
+
0 && (module.exports = {
|
|
278
|
+
signOut
|
|
279
|
+
});
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
import { F as FunctionAPIContext, i as SignOutAPIOptions } from '../index-_aXtxb_s.js';
|
|
2
|
+
import 'zod';
|
|
3
|
+
import '../schemas.js';
|
|
4
|
+
import 'zod/v4';
|
|
5
|
+
import '@aura-stack/jose';
|
|
6
|
+
import '@aura-stack/jose/jose';
|
|
7
|
+
import '@aura-stack/jose/crypto';
|
|
8
|
+
import '@aura-stack/router/cookie';
|
|
9
|
+
import '../@types/utility.js';
|
|
10
|
+
import 'jose';
|
|
11
|
+
import '@aura-stack/router';
|
|
12
|
+
import 'zod/v4/core';
|
|
13
|
+
|
|
14
|
+
declare const signOut: ({ ctx, headers: headersInit, redirectTo, skipCSRFCheck, }: FunctionAPIContext<SignOutAPIOptions>) => Promise<Response>;
|
|
15
|
+
|
|
16
|
+
export { signOut };
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import {
|
|
2
|
+
signOut
|
|
3
|
+
} from "../chunk-KBXWTD6E.js";
|
|
4
|
+
import "../chunk-V6LLEAR4.js";
|
|
5
|
+
import "../chunk-UZQJJD6A.js";
|
|
6
|
+
import "../chunk-LX3TJ2TJ.js";
|
|
7
|
+
import "../chunk-XY5R3EHH.js";
|
|
8
|
+
import "../chunk-WHNDRO3N.js";
|
|
9
|
+
import "../chunk-U5663F2U.js";
|
|
10
|
+
import "../chunk-EBAMFRB7.js";
|
|
11
|
+
export {
|
|
12
|
+
signOut
|
|
13
|
+
};
|
package/dist/assert.cjs
CHANGED
|
@@ -28,20 +28,51 @@ __export(assert_exports, {
|
|
|
28
28
|
isTrustedOrigin: () => isTrustedOrigin,
|
|
29
29
|
isValidURL: () => isValidURL,
|
|
30
30
|
patternToRegex: () => patternToRegex,
|
|
31
|
-
|
|
31
|
+
timingSafeEqual: () => timingSafeEqual,
|
|
32
32
|
unsafeChars: () => unsafeChars
|
|
33
33
|
});
|
|
34
34
|
module.exports = __toCommonJS(assert_exports);
|
|
35
35
|
|
|
36
36
|
// src/utils.ts
|
|
37
37
|
var import_router = require("@aura-stack/router");
|
|
38
|
+
|
|
39
|
+
// src/env.ts
|
|
40
|
+
var import_meta = {};
|
|
41
|
+
var env = new Proxy({}, {
|
|
42
|
+
get(_, prop) {
|
|
43
|
+
if (typeof prop !== "string") return void 0;
|
|
44
|
+
const hasProperty = (process2) => {
|
|
45
|
+
return process2 && Object.prototype.hasOwnProperty.call(process2, prop);
|
|
46
|
+
};
|
|
47
|
+
try {
|
|
48
|
+
if (typeof process !== "undefined" && hasProperty(process.env)) {
|
|
49
|
+
return process.env[prop];
|
|
50
|
+
}
|
|
51
|
+
if (typeof import_meta !== "undefined" && hasProperty(import_meta.env)) {
|
|
52
|
+
return import_meta.env[prop];
|
|
53
|
+
}
|
|
54
|
+
if (typeof Deno !== "undefined" && Deno.env?.get) {
|
|
55
|
+
return Deno.env.get(prop);
|
|
56
|
+
}
|
|
57
|
+
if (typeof Bun !== "undefined" && hasProperty(Bun.env)) {
|
|
58
|
+
return Bun.env[prop];
|
|
59
|
+
}
|
|
60
|
+
const globalValue = globalThis[prop];
|
|
61
|
+
return typeof globalValue === "string" ? globalValue : void 0;
|
|
62
|
+
} catch {
|
|
63
|
+
return void 0;
|
|
64
|
+
}
|
|
65
|
+
}
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
// src/utils.ts
|
|
38
69
|
var equals = (a, b) => {
|
|
39
70
|
if (a === null || b === null || a === void 0 || b === void 0) return false;
|
|
40
71
|
return a === b;
|
|
41
72
|
};
|
|
42
73
|
|
|
43
74
|
// src/assert.ts
|
|
44
|
-
var import_crypto = require("crypto");
|
|
75
|
+
var import_crypto = require("@aura-stack/jose/crypto");
|
|
45
76
|
var isFalsy = (value) => {
|
|
46
77
|
return value === false || value === 0 || value === "" || value === null || value === void 0 || Number.isNaN(value);
|
|
47
78
|
};
|
|
@@ -138,13 +169,15 @@ var isTrustedOrigin = (url, trustedOrigins) => {
|
|
|
138
169
|
}
|
|
139
170
|
return false;
|
|
140
171
|
};
|
|
141
|
-
var
|
|
142
|
-
const bufferA =
|
|
143
|
-
const bufferB =
|
|
144
|
-
|
|
145
|
-
|
|
172
|
+
var timingSafeEqual = (a, b) => {
|
|
173
|
+
const bufferA = import_crypto.encoder.encode(a);
|
|
174
|
+
const bufferB = import_crypto.encoder.encode(b);
|
|
175
|
+
const len = Math.max(bufferA.length, bufferB.length);
|
|
176
|
+
let diff = 0;
|
|
177
|
+
for (let i = 0; i < len; i++) {
|
|
178
|
+
diff |= (bufferA[i] ?? 0) ^ (bufferB[i] ?? 0);
|
|
146
179
|
}
|
|
147
|
-
return
|
|
180
|
+
return diff === 0 && bufferA.length === bufferB.length;
|
|
148
181
|
};
|
|
149
182
|
// Annotate the CommonJS export names for ESM import in node:
|
|
150
183
|
0 && (module.exports = {
|
|
@@ -156,6 +189,6 @@ var safeEquals = (a, b) => {
|
|
|
156
189
|
isTrustedOrigin,
|
|
157
190
|
isValidURL,
|
|
158
191
|
patternToRegex,
|
|
159
|
-
|
|
192
|
+
timingSafeEqual,
|
|
160
193
|
unsafeChars
|
|
161
194
|
});
|
package/dist/assert.d.ts
CHANGED
|
@@ -1,11 +1,15 @@
|
|
|
1
|
-
import { J as JWTPayloadWithToken } from './index-
|
|
1
|
+
import { J as JWTPayloadWithToken } from './index-_aXtxb_s.js';
|
|
2
2
|
import 'zod';
|
|
3
3
|
import './schemas.js';
|
|
4
|
-
import '
|
|
4
|
+
import 'zod/v4';
|
|
5
5
|
import '@aura-stack/jose';
|
|
6
6
|
import '@aura-stack/jose/jose';
|
|
7
|
+
import '@aura-stack/jose/crypto';
|
|
7
8
|
import '@aura-stack/router/cookie';
|
|
8
9
|
import './@types/utility.js';
|
|
10
|
+
import 'jose';
|
|
11
|
+
import '@aura-stack/router';
|
|
12
|
+
import 'zod/v4/core';
|
|
9
13
|
|
|
10
14
|
declare const isFalsy: (value: unknown) => boolean;
|
|
11
15
|
declare const isRequest: (value: unknown) => value is Request;
|
|
@@ -28,6 +32,6 @@ declare const patternToRegex: (pattern: string) => RegExp | null;
|
|
|
28
32
|
* @param trustedOrigins - Array of exact URLs or patterns (e.g. `https://*.example.com`)
|
|
29
33
|
*/
|
|
30
34
|
declare const isTrustedOrigin: (url: string, trustedOrigins: string[]) => boolean;
|
|
31
|
-
declare const
|
|
35
|
+
declare const timingSafeEqual: (a: string, b: string) => boolean;
|
|
32
36
|
|
|
33
|
-
export { isFalsy, isJWTPayloadWithToken, isRelativeURL, isRequest, isSameOrigin, isTrustedOrigin, isValidURL, patternToRegex,
|
|
37
|
+
export { isFalsy, isJWTPayloadWithToken, isRelativeURL, isRequest, isSameOrigin, isTrustedOrigin, isValidURL, patternToRegex, timingSafeEqual, unsafeChars };
|
package/dist/assert.js
CHANGED
|
@@ -7,11 +7,11 @@ import {
|
|
|
7
7
|
isTrustedOrigin,
|
|
8
8
|
isValidURL,
|
|
9
9
|
patternToRegex,
|
|
10
|
-
|
|
10
|
+
timingSafeEqual,
|
|
11
11
|
unsafeChars
|
|
12
|
-
} from "./chunk-
|
|
13
|
-
import "./chunk-
|
|
14
|
-
import "./chunk-
|
|
12
|
+
} from "./chunk-LX3TJ2TJ.js";
|
|
13
|
+
import "./chunk-WHNDRO3N.js";
|
|
14
|
+
import "./chunk-U5663F2U.js";
|
|
15
15
|
export {
|
|
16
16
|
isFalsy,
|
|
17
17
|
isJWTPayloadWithToken,
|
|
@@ -21,6 +21,6 @@ export {
|
|
|
21
21
|
isTrustedOrigin,
|
|
22
22
|
isValidURL,
|
|
23
23
|
patternToRegex,
|
|
24
|
-
|
|
24
|
+
timingSafeEqual,
|
|
25
25
|
unsafeChars
|
|
26
26
|
};
|
|
@@ -1,23 +1,56 @@
|
|
|
1
1
|
// src/schemas.ts
|
|
2
|
-
import { object, string, enum as options, number, z, null as nullable } from "zod";
|
|
2
|
+
import { object, string, enum as options, number, z, null as nullable, union, array } from "zod/v4";
|
|
3
|
+
var AuthorizeConfigSchema = z.union([
|
|
4
|
+
string().url(),
|
|
5
|
+
object({
|
|
6
|
+
url: string().url(),
|
|
7
|
+
params: object({
|
|
8
|
+
responseType: options(["code", "token", "id_token", "refresh_token"]).optional(),
|
|
9
|
+
scope: string().optional()
|
|
10
|
+
})
|
|
11
|
+
})
|
|
12
|
+
]);
|
|
13
|
+
var AccessTokenConfigSchema = z.union([
|
|
14
|
+
string().url(),
|
|
15
|
+
object({
|
|
16
|
+
url: string().url(),
|
|
17
|
+
headers: z.record(string(), string()).optional()
|
|
18
|
+
})
|
|
19
|
+
]);
|
|
20
|
+
var UserInfoConfigSchema = z.union([
|
|
21
|
+
string().url(),
|
|
22
|
+
object({
|
|
23
|
+
url: string().url(),
|
|
24
|
+
headers: z.record(string(), string()).optional(),
|
|
25
|
+
method: string().optional()
|
|
26
|
+
})
|
|
27
|
+
]);
|
|
3
28
|
var OAuthProviderCredentialsSchema = object({
|
|
4
29
|
id: string(),
|
|
5
30
|
name: string(),
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
31
|
+
authorize: AuthorizeConfigSchema.optional(),
|
|
32
|
+
/** @deprecated */
|
|
33
|
+
authorizeURL: string().url().optional(),
|
|
34
|
+
accessToken: AccessTokenConfigSchema,
|
|
35
|
+
/** @deprecated */
|
|
36
|
+
scope: string().optional(),
|
|
37
|
+
userInfo: UserInfoConfigSchema,
|
|
38
|
+
/** @deprecated */
|
|
39
|
+
responseType: options(["code", "token", "id_token", "refresh_token"]).optional(),
|
|
11
40
|
clientId: string(),
|
|
12
41
|
clientSecret: string(),
|
|
13
42
|
profile: z.function().optional()
|
|
14
43
|
});
|
|
15
44
|
var OAuthProviderConfigSchema = object({
|
|
16
|
-
|
|
17
|
-
|
|
45
|
+
authorize: AuthorizeConfigSchema.optional(),
|
|
46
|
+
/** @deprecated */
|
|
47
|
+
authorizeURL: string().url().optional(),
|
|
48
|
+
accessToken: AccessTokenConfigSchema,
|
|
49
|
+
/** @deprecated */
|
|
18
50
|
scope: string().optional(),
|
|
19
|
-
userInfo:
|
|
20
|
-
|
|
51
|
+
userInfo: UserInfoConfigSchema,
|
|
52
|
+
/** @deprecated */
|
|
53
|
+
responseType: options(["code", "token", "id_token", "refresh_token"]).optional(),
|
|
21
54
|
clientId: string(),
|
|
22
55
|
clientSecret: string()
|
|
23
56
|
});
|
|
@@ -55,7 +88,7 @@ var OAuthAccessTokenResponse = object({
|
|
|
55
88
|
token_type: string().optional(),
|
|
56
89
|
expires_in: number().optional(),
|
|
57
90
|
refresh_token: string().optional(),
|
|
58
|
-
scope: string().optional().or(nullable())
|
|
91
|
+
scope: union([string().optional().or(nullable()), array(string()).optional()])
|
|
59
92
|
});
|
|
60
93
|
var OAuthAccessTokenErrorResponse = object({
|
|
61
94
|
error: options([
|
|
@@ -0,0 +1,40 @@
|
|
|
1
|
+
import {
|
|
2
|
+
getEnv
|
|
3
|
+
} from "./chunk-WHNDRO3N.js";
|
|
4
|
+
|
|
5
|
+
// src/oauth/twitch.ts
|
|
6
|
+
var twitch = (options) => {
|
|
7
|
+
const clientId = options?.clientId ?? getEnv("TWITCH_CLIENT_ID");
|
|
8
|
+
return {
|
|
9
|
+
id: "twitch",
|
|
10
|
+
name: "Twitch",
|
|
11
|
+
authorize: {
|
|
12
|
+
url: "https://id.twitch.tv/oauth2/authorize",
|
|
13
|
+
params: { scope: "user:read:email", responseType: "code" }
|
|
14
|
+
},
|
|
15
|
+
accessToken: "https://id.twitch.tv/oauth2/token",
|
|
16
|
+
userInfo: {
|
|
17
|
+
url: "https://api.twitch.tv/helix/users",
|
|
18
|
+
headers: {
|
|
19
|
+
"Client-ID": clientId
|
|
20
|
+
}
|
|
21
|
+
},
|
|
22
|
+
profile(profile) {
|
|
23
|
+
const user = profile.data[0];
|
|
24
|
+
if (!user) {
|
|
25
|
+
throw new Error("No user data found in Twitch profile response");
|
|
26
|
+
}
|
|
27
|
+
return {
|
|
28
|
+
sub: user.id,
|
|
29
|
+
name: user.display_name,
|
|
30
|
+
email: user.email,
|
|
31
|
+
picture: user.profile_image_url
|
|
32
|
+
};
|
|
33
|
+
},
|
|
34
|
+
...options
|
|
35
|
+
};
|
|
36
|
+
};
|
|
37
|
+
|
|
38
|
+
export {
|
|
39
|
+
twitch
|
|
40
|
+
};
|
|
@@ -0,0 +1,44 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createBuiltInOAuthProviders
|
|
3
|
+
} from "./chunk-PDP3PHB3.js";
|
|
4
|
+
import {
|
|
5
|
+
createProxyLogger
|
|
6
|
+
} from "./chunk-U4RK4LKJ.js";
|
|
7
|
+
import {
|
|
8
|
+
createJoseInstance
|
|
9
|
+
} from "./chunk-UZQJJD6A.js";
|
|
10
|
+
import {
|
|
11
|
+
createCookieStore
|
|
12
|
+
} from "./chunk-XY5R3EHH.js";
|
|
13
|
+
import {
|
|
14
|
+
getEnv,
|
|
15
|
+
getEnvArray,
|
|
16
|
+
getEnvBoolean
|
|
17
|
+
} from "./chunk-WHNDRO3N.js";
|
|
18
|
+
|
|
19
|
+
// src/context.ts
|
|
20
|
+
var createContext = (config) => {
|
|
21
|
+
const trustedProxyHeadersEnv = getEnv("TRUSTED_PROXY_HEADERS");
|
|
22
|
+
const useProxyHeaders = trustedProxyHeadersEnv === void 0 ? config?.trustedProxyHeaders ?? false : getEnvBoolean("TRUSTED_PROXY_HEADERS");
|
|
23
|
+
const logger = createProxyLogger(config);
|
|
24
|
+
const cookiePrefix = config?.cookies?.prefix;
|
|
25
|
+
const cookieOverrides = config?.cookies?.overrides ?? {};
|
|
26
|
+
const secureCookieStore = createCookieStore(true, cookiePrefix, cookieOverrides, logger);
|
|
27
|
+
const standardCookieStore = createCookieStore(false, cookiePrefix, cookieOverrides, logger);
|
|
28
|
+
return {
|
|
29
|
+
oauth: createBuiltInOAuthProviders(config?.oauth),
|
|
30
|
+
cookies: standardCookieStore,
|
|
31
|
+
jose: createJoseInstance(config?.secret),
|
|
32
|
+
secret: config?.secret,
|
|
33
|
+
basePath: config?.basePath ?? "/auth",
|
|
34
|
+
trustedProxyHeaders: useProxyHeaders,
|
|
35
|
+
trustedOrigins: getEnvArray("TRUSTED_ORIGINS").length > 0 ? getEnvArray("TRUSTED_ORIGINS") : config?.trustedOrigins,
|
|
36
|
+
logger,
|
|
37
|
+
cookieConfig: { secure: secureCookieStore, standard: standardCookieStore },
|
|
38
|
+
baseURL: config?.baseURL
|
|
39
|
+
};
|
|
40
|
+
};
|
|
41
|
+
|
|
42
|
+
export {
|
|
43
|
+
createContext
|
|
44
|
+
};
|
|
@@ -0,0 +1,50 @@
|
|
|
1
|
+
import {
|
|
2
|
+
createRedirectTo
|
|
3
|
+
} from "./chunk-LATR3NIV.js";
|
|
4
|
+
import {
|
|
5
|
+
signOut
|
|
6
|
+
} from "./chunk-KBXWTD6E.js";
|
|
7
|
+
import {
|
|
8
|
+
getBaseURL
|
|
9
|
+
} from "./chunk-LX3TJ2TJ.js";
|
|
10
|
+
|
|
11
|
+
// src/actions/signOut/signOut.ts
|
|
12
|
+
import { z } from "zod/v4";
|
|
13
|
+
import { createEndpoint, createEndpointConfig } from "@aura-stack/router";
|
|
14
|
+
var config = createEndpointConfig({
|
|
15
|
+
schemas: {
|
|
16
|
+
searchParams: z.object({
|
|
17
|
+
token_type_hint: z.literal("session_token"),
|
|
18
|
+
redirectTo: z.string().optional()
|
|
19
|
+
})
|
|
20
|
+
}
|
|
21
|
+
});
|
|
22
|
+
var signOutAction = createEndpoint(
|
|
23
|
+
"POST",
|
|
24
|
+
"/signOut",
|
|
25
|
+
async (ctx) => {
|
|
26
|
+
const {
|
|
27
|
+
request,
|
|
28
|
+
searchParams: { redirectTo },
|
|
29
|
+
context
|
|
30
|
+
} = ctx;
|
|
31
|
+
const baseURL = getBaseURL(request);
|
|
32
|
+
const location = await createRedirectTo(
|
|
33
|
+
new Request(baseURL, {
|
|
34
|
+
headers: request.headers
|
|
35
|
+
}),
|
|
36
|
+
redirectTo,
|
|
37
|
+
context
|
|
38
|
+
);
|
|
39
|
+
return await signOut({
|
|
40
|
+
ctx: context,
|
|
41
|
+
headers: request.headers,
|
|
42
|
+
redirectTo: location
|
|
43
|
+
});
|
|
44
|
+
},
|
|
45
|
+
config
|
|
46
|
+
);
|
|
47
|
+
|
|
48
|
+
export {
|
|
49
|
+
signOutAction
|
|
50
|
+
};
|