@rttnd/gau 0.5.0 → 0.7.1

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 (68) hide show
  1. package/README.md +48 -44
  2. package/dist/chunk-4PR5RWHE.js +1 -0
  3. package/dist/chunk-4PR5RWHE.js.map +1 -0
  4. package/dist/chunk-7SEBXKP6.js +1 -0
  5. package/dist/chunk-7SEBXKP6.js.map +1 -0
  6. package/dist/chunk-BAIUBBG4.js +1 -0
  7. package/dist/chunk-BAIUBBG4.js.map +1 -0
  8. package/dist/chunk-ZJEC3NLU.js +1 -0
  9. package/dist/chunk-ZJEC3NLU.js.map +1 -0
  10. package/dist/src/adapters/drizzle/index.d.ts.map +1 -1
  11. package/dist/src/adapters/drizzle/index.js +1 -1
  12. package/dist/src/adapters/drizzle/mysql.d.ts +0 -1
  13. package/dist/src/adapters/drizzle/mysql.d.ts.map +1 -1
  14. package/dist/src/adapters/drizzle/pg.d.ts +27 -2
  15. package/dist/src/adapters/drizzle/pg.d.ts.map +1 -1
  16. package/dist/src/adapters/drizzle/sqlite.d.ts +8 -6
  17. package/dist/src/adapters/drizzle/sqlite.d.ts.map +1 -1
  18. package/dist/src/adapters/index.js +1 -1
  19. package/dist/src/client/solid/Protected.d.ts +4 -0
  20. package/dist/src/client/solid/Protected.d.ts.map +1 -0
  21. package/dist/src/client/solid/index.d.ts +3 -3
  22. package/dist/src/client/solid/index.d.ts.map +1 -1
  23. package/dist/src/client/solid/index.jsx +277 -125
  24. package/dist/src/client/svelte/Protected/index.svelte +32 -0
  25. package/dist/src/client/svelte/index.svelte.js +1 -1
  26. package/dist/src/client/svelte/index.svelte.js.map +1 -1
  27. package/dist/src/client/vanilla/index.d.ts +25 -0
  28. package/dist/src/client/vanilla/index.d.ts.map +1 -0
  29. package/dist/src/client/vanilla/index.js +1 -0
  30. package/dist/src/client/vanilla/index.js.map +1 -0
  31. package/dist/src/core/cookies.d.ts +1 -1
  32. package/dist/src/core/cookies.d.ts.map +1 -1
  33. package/dist/src/core/createAuth.d.ts.map +1 -1
  34. package/dist/src/core/handler.d.ts.map +1 -1
  35. package/dist/src/core/handlers/callback.d.ts.map +1 -1
  36. package/dist/src/core/handlers/index.js +1 -1
  37. package/dist/src/core/handlers/login.d.ts.map +1 -1
  38. package/dist/src/core/handlers/utils.d.ts.map +1 -1
  39. package/dist/src/core/index.d.ts +2 -2
  40. package/dist/src/core/index.d.ts.map +1 -1
  41. package/dist/src/core/index.js +1 -1
  42. package/dist/src/index.js +1 -1
  43. package/dist/src/jwt/index.js +1 -1
  44. package/dist/src/oauth/index.d.ts +2 -0
  45. package/dist/src/oauth/index.d.ts.map +1 -1
  46. package/dist/src/oauth/index.js +1 -1
  47. package/dist/src/oauth/index.js.map +1 -1
  48. package/dist/src/oauth/providers/discord.d.ts +3 -0
  49. package/dist/src/oauth/providers/discord.d.ts.map +1 -0
  50. package/dist/src/oauth/providers/facebook.d.ts +3 -0
  51. package/dist/src/oauth/providers/facebook.d.ts.map +1 -0
  52. package/dist/src/oauth/providers/microsoft.d.ts +0 -1
  53. package/dist/src/oauth/providers/microsoft.d.ts.map +1 -1
  54. package/dist/src/runtimes/index.js +1 -1
  55. package/dist/src/runtimes/tauri/index.d.ts +4 -2
  56. package/dist/src/runtimes/tauri/index.d.ts.map +1 -1
  57. package/dist/src/runtimes/tauri/index.js +1 -1
  58. package/dist/src/solidstart/index.js +1 -1
  59. package/dist/src/sveltekit/index.js +1 -1
  60. package/package.json +42 -14
  61. package/dist/chunk-3NKNADKP.js +0 -1
  62. package/dist/chunk-3NKNADKP.js.map +0 -1
  63. package/dist/chunk-GV4FQQFM.js +0 -1
  64. package/dist/chunk-GV4FQQFM.js.map +0 -1
  65. package/dist/chunk-Z35ZTMGZ.js +0 -1
  66. package/dist/chunk-Z35ZTMGZ.js.map +0 -1
  67. package/dist/src/client/svelte/index.svelte.d.ts +0 -22
  68. package/dist/src/client/svelte/index.svelte.d.ts.map +0 -1
@@ -0,0 +1,4 @@
1
+ import type { Accessor, JSXElement, VoidComponent } from 'solid-js';
2
+ import type { GauSession, ProviderIds } from '../../core';
3
+ export declare function Protected<const TAuth = unknown>(page: (session: Accessor<GauSession<ProviderIds<TAuth>>>) => JSXElement, fallbackOrRedirect?: (() => JSXElement) | string): VoidComponent;
4
+ //# sourceMappingURL=Protected.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"Protected.d.ts","sourceRoot":"","sources":["../../../../src/client/solid/Protected.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,UAAU,EAAE,aAAa,EAAE,MAAM,UAAU,CAAA;AACnE,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAMzD,wBAAgB,SAAS,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,EAC7C,IAAI,EAAE,CAAC,OAAO,EAAE,QAAQ,CAAC,UAAU,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,UAAU,EACvE,kBAAkB,CAAC,EAAE,CAAC,MAAM,UAAU,CAAC,GAAG,MAAM,GAC/C,aAAa,CA0Bf"}
@@ -1,4 +1,4 @@
1
- import type { Accessor, JSXElement, ParentProps, VoidComponent } from 'solid-js';
1
+ import type { Accessor, ParentProps } from 'solid-js';
2
2
  import type { GauSession, ProfileName, ProviderIds } from '../../core';
3
3
  interface AuthContextValue<TAuth = unknown> {
4
4
  session: Accessor<GauSession<ProviderIds<TAuth>>>;
@@ -12,6 +12,7 @@ interface AuthContextValue<TAuth = unknown> {
12
12
  }) => Promise<void>;
13
13
  unlinkAccount: (provider: ProviderIds<TAuth>) => Promise<void>;
14
14
  signOut: () => Promise<void>;
15
+ refresh: () => Promise<void>;
15
16
  }
16
17
  export declare function AuthProvider<const TAuth = unknown>(props: ParentProps & {
17
18
  auth?: TAuth;
@@ -20,6 +21,5 @@ export declare function AuthProvider<const TAuth = unknown>(props: ParentProps &
20
21
  redirectTo?: string;
21
22
  }): import("solid-js").JSX.Element;
22
23
  export declare function useAuth<const TAuth = unknown>(): AuthContextValue<TAuth>;
23
- export declare function Protected<const TAuth = unknown>(page: (session: Accessor<GauSession<ProviderIds<TAuth>>>) => JSXElement, fallbackOrRedirect?: (() => JSXElement) | string): VoidComponent;
24
- export {};
24
+ export { Protected } from './Protected';
25
25
  //# sourceMappingURL=index.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/client/solid/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,UAAU,EAAE,WAAW,EAAE,aAAa,EAAE,MAAM,UAAU,CAAA;AAChF,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAOtE,UAAU,gBAAgB,CAAC,KAAK,GAAG,OAAO;IACxC,OAAO,EAAE,QAAQ,CAAC,UAAU,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,CAAA;IACjD,MAAM,EAAE,CAAC,CAAC,SAAS,WAAW,CAAC,KAAK,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,WAAW,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IACxI,WAAW,EAAE,CAAC,CAAC,SAAS,WAAW,CAAC,KAAK,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,WAAW,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC7I,aAAa,EAAE,CAAC,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC9D,OAAO,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAA;CAC7B;AAID,wBAAgB,YAAY,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,EAAE,KAAK,EAAE,WAAW,GAAG;IAAE,IAAI,CAAC,EAAE,KAAK,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IAAC,UAAU,CAAC,EAAE,MAAM,CAAA;CAAE,kCA6IhJ;AAED,wBAAgB,OAAO,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,KAAK,gBAAgB,CAAC,KAAK,CAAC,CAKxE;AAED,wBAAgB,SAAS,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,EAC7C,IAAI,EAAE,CAAC,OAAO,EAAE,QAAQ,CAAC,UAAU,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,KAAK,UAAU,EACvE,kBAAkB,CAAC,EAAE,CAAC,MAAM,UAAU,CAAC,GAAG,MAAM,GAC/C,aAAa,CAyBf"}
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../../../src/client/solid/index.tsx"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,QAAQ,EAAE,WAAW,EAAE,MAAM,UAAU,CAAA;AACrD,OAAO,KAAK,EAAE,UAAU,EAAE,WAAW,EAAE,WAAW,EAAE,MAAM,YAAY,CAAA;AAOtE,UAAU,gBAAgB,CAAC,KAAK,GAAG,OAAO;IACxC,OAAO,EAAE,QAAQ,CAAC,UAAU,CAAC,WAAW,CAAC,KAAK,CAAC,CAAC,CAAC,CAAA;IACjD,MAAM,EAAE,CAAC,CAAC,SAAS,WAAW,CAAC,KAAK,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,WAAW,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IACxI,WAAW,EAAE,CAAC,CAAC,SAAS,WAAW,CAAC,KAAK,CAAC,EAAE,QAAQ,EAAE,CAAC,EAAE,OAAO,CAAC,EAAE;QAAE,UAAU,CAAC,EAAE,MAAM,CAAC;QAAC,OAAO,CAAC,EAAE,WAAW,CAAC,KAAK,EAAE,CAAC,CAAC,CAAA;KAAE,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC7I,aAAa,EAAE,CAAC,QAAQ,EAAE,WAAW,CAAC,KAAK,CAAC,KAAK,OAAO,CAAC,IAAI,CAAC,CAAA;IAC9D,OAAO,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAA;IAC5B,OAAO,EAAE,MAAM,OAAO,CAAC,IAAI,CAAC,CAAA;CAC7B;AAID,wBAAgB,YAAY,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,EAAE,KAAK,EAAE,WAAW,GAAG;IAAE,IAAI,CAAC,EAAE,KAAK,CAAC;IAAC,OAAO,CAAC,EAAE,MAAM,CAAC;IAAC,MAAM,CAAC,EAAE,MAAM,CAAC;IAAC,UAAU,CAAC,EAAE,MAAM,CAAA;CAAE,kCAgGhJ;AAED,wBAAgB,OAAO,CAAC,KAAK,CAAC,KAAK,GAAG,OAAO,KAAK,gBAAgB,CAAC,KAAK,CAAC,CAKxE;AAED,OAAO,EAAE,SAAS,EAAE,MAAM,aAAa,CAAA"}
@@ -1,32 +1,12 @@
1
- // src/client/solid/index.tsx
2
- import { createContext, createResource, onCleanup, onMount, Show, untrack, useContext } from "solid-js";
3
- import { isServer } from "solid-js/web";
4
-
5
- // src/core/cookies.ts
6
- import { parse, serialize } from "cookie";
7
- var CSRF_MAX_AGE = 60 * 10;
8
-
9
- // src/jwt/jwt.ts
10
- import {
11
- createJWTSignatureMessage,
12
- encodeJWT,
13
- JWSRegisteredHeaders,
14
- JWTRegisteredClaims,
15
- parseJWT
16
- } from "@oslojs/jwt";
17
-
18
- // src/oauth/utils.ts
19
- import { generateCodeVerifier, generateState } from "arctic";
20
-
21
- // src/core/index.ts
22
- var NULL_SESSION = {
23
- user: null,
24
- session: null,
25
- accounts: null
1
+ var __defProp = Object.defineProperty;
2
+ var __getOwnPropNames = Object.getOwnPropertyNames;
3
+ var __esm = (fn, res) => function __init() {
4
+ return fn && (res = (0, fn[__getOwnPropNames(fn)[0]])(fn = 0)), res;
5
+ };
6
+ var __export = (target, all) => {
7
+ for (var name in all)
8
+ __defProp(target, name, { get: all[name], enumerable: true });
26
9
  };
27
-
28
- // src/runtimes/tauri/index.ts
29
- import { BROWSER as BROWSER2 } from "esm-env";
30
10
 
31
11
  // src/client/token.ts
32
12
  import { BROWSER } from "esm-env";
@@ -53,8 +33,23 @@ function clearSessionToken() {
53
33
  } catch {
54
34
  }
55
35
  }
36
+ var init_token = __esm({
37
+ "src/client/token.ts"() {
38
+ "use strict";
39
+ }
40
+ });
56
41
 
57
42
  // src/runtimes/tauri/index.ts
43
+ var tauri_exports = {};
44
+ __export(tauri_exports, {
45
+ handleTauriDeepLink: () => handleTauriDeepLink,
46
+ isTauri: () => isTauri,
47
+ linkAccountWithTauri: () => linkAccountWithTauri,
48
+ setupTauriListener: () => setupTauriListener,
49
+ signInWithTauri: () => signInWithTauri,
50
+ startAuthBridge: () => startAuthBridge
51
+ });
52
+ import { BROWSER as BROWSER2 } from "esm-env";
58
53
  function isTauri() {
59
54
  return BROWSER2 && "__TAURI_INTERNALS__" in globalThis;
60
55
  }
@@ -62,7 +57,7 @@ async function signInWithTauri(provider, baseUrl, scheme = "gau", redirectOverri
62
57
  if (!isTauri())
63
58
  return;
64
59
  const { platform } = await import("@tauri-apps/plugin-os");
65
- const { open } = await import("@tauri-apps/plugin-shell");
60
+ const { openUrl } = await import("@tauri-apps/plugin-opener");
66
61
  const currentPlatform = platform();
67
62
  let redirectTo;
68
63
  if (redirectOverride)
@@ -74,9 +69,9 @@ async function signInWithTauri(provider, baseUrl, scheme = "gau", redirectOverri
74
69
  const params = new URLSearchParams();
75
70
  params.set("redirectTo", redirectTo);
76
71
  if (profile)
77
- params.set("profile", profile);
72
+ params.set("profile", String(profile));
78
73
  const authUrl = `${baseUrl}/${provider}?${params.toString()}`;
79
- await open(authUrl);
74
+ await openUrl(authUrl);
80
75
  }
81
76
  async function setupTauriListener(handler) {
82
77
  if (!isTauri())
@@ -104,7 +99,7 @@ async function linkAccountWithTauri(provider, baseUrl, scheme = "gau", redirectO
104
99
  if (!isTauri())
105
100
  return;
106
101
  const { platform } = await import("@tauri-apps/plugin-os");
107
- const { open } = await import("@tauri-apps/plugin-shell");
102
+ const { openUrl } = await import("@tauri-apps/plugin-opener");
108
103
  const currentPlatform = platform();
109
104
  let redirectTo;
110
105
  if (redirectOverride)
@@ -122,9 +117,217 @@ async function linkAccountWithTauri(provider, baseUrl, scheme = "gau", redirectO
122
117
  params.set("redirectTo", redirectTo);
123
118
  params.set("token", token);
124
119
  if (profile)
125
- params.set("profile", profile);
120
+ params.set("profile", String(profile));
126
121
  const linkUrl = `${baseUrl}/link/${provider}?${params.toString()}`;
127
- await open(linkUrl);
122
+ await openUrl(linkUrl);
123
+ }
124
+ async function startAuthBridge(baseUrl, scheme, onToken) {
125
+ if (!isTauri())
126
+ return;
127
+ const unlisten = await setupTauriListener(async (url) => {
128
+ handleTauriDeepLink(url, baseUrl, scheme, onToken);
129
+ });
130
+ return unlisten;
131
+ }
132
+ var init_tauri = __esm({
133
+ "src/runtimes/tauri/index.ts"() {
134
+ "use strict";
135
+ init_token();
136
+ }
137
+ });
138
+
139
+ // src/client/solid/index.tsx
140
+ import { createContext, createResource, onCleanup, onMount as onMount2, untrack, useContext } from "solid-js";
141
+ import { isServer as isServer2 } from "solid-js/web";
142
+
143
+ // src/core/cookies.ts
144
+ import { parse, serialize } from "cookie";
145
+ var CSRF_MAX_AGE = 60 * 10;
146
+
147
+ // src/jwt/jwt.ts
148
+ import {
149
+ createJWTSignatureMessage,
150
+ encodeJWT,
151
+ JWSRegisteredHeaders,
152
+ JWTRegisteredClaims,
153
+ parseJWT
154
+ } from "@oslojs/jwt";
155
+
156
+ // src/oauth/utils.ts
157
+ import { generateCodeVerifier, generateState } from "arctic";
158
+
159
+ // src/core/index.ts
160
+ var NULL_SESSION = {
161
+ user: null,
162
+ session: null,
163
+ accounts: null
164
+ };
165
+
166
+ // src/client/solid/index.tsx
167
+ init_tauri();
168
+
169
+ // src/client/vanilla/index.ts
170
+ init_token();
171
+ function buildQuery(params) {
172
+ const q = new URLSearchParams();
173
+ for (const [k, v] of Object.entries(params)) {
174
+ if (v != null && v !== "")
175
+ q.set(k, String(v));
176
+ }
177
+ const s = q.toString();
178
+ return s ? `?${s}` : "";
179
+ }
180
+ function createAuthClient({ baseUrl }) {
181
+ let currentSession = { user: null, session: null, accounts: null, providers: [] };
182
+ const listeners = /* @__PURE__ */ new Set();
183
+ const notify = () => {
184
+ for (const l of listeners)
185
+ l(currentSession);
186
+ };
187
+ async function fetchSession() {
188
+ const token = getSessionToken();
189
+ const headers = token ? { Authorization: `Bearer ${token}` } : void 0;
190
+ const res = await fetch(`${baseUrl}/session`, token ? { headers } : { credentials: "include" });
191
+ const contentType = res.headers.get("content-type");
192
+ if (contentType?.includes("application/json"))
193
+ return await res.json();
194
+ return { user: null, session: null, accounts: null, providers: [] };
195
+ }
196
+ async function refreshSession() {
197
+ const next = await fetchSession();
198
+ currentSession = next;
199
+ notify();
200
+ return next;
201
+ }
202
+ async function applySessionToken(token) {
203
+ try {
204
+ storeSessionToken(token);
205
+ } finally {
206
+ await refreshSession();
207
+ }
208
+ }
209
+ function onSessionChange(listener) {
210
+ listeners.add(listener);
211
+ return () => listeners.delete(listener);
212
+ }
213
+ async function handleRedirectCallback(replaceUrl) {
214
+ if (typeof window === "undefined")
215
+ return false;
216
+ if (window.location.hash === "#_=_") {
217
+ const cleanUrl2 = window.location.pathname + window.location.search;
218
+ if (replaceUrl)
219
+ replaceUrl(cleanUrl2);
220
+ else
221
+ window.history.replaceState(null, "", cleanUrl2);
222
+ return false;
223
+ }
224
+ const hash = window.location.hash?.substring(1) ?? "";
225
+ if (!hash)
226
+ return false;
227
+ const params = new URLSearchParams(hash);
228
+ const token = params.get("token");
229
+ if (!token)
230
+ return false;
231
+ await applySessionToken(token);
232
+ const cleanUrl = window.location.pathname + window.location.search;
233
+ if (replaceUrl)
234
+ replaceUrl(cleanUrl);
235
+ else
236
+ window.history.replaceState(null, "", cleanUrl);
237
+ return true;
238
+ }
239
+ function makeProviderUrl(provider, params) {
240
+ const q = buildQuery({
241
+ redirectTo: params?.redirectTo,
242
+ profile: params?.profile != null ? String(params.profile) : void 0
243
+ });
244
+ return `${baseUrl}/${provider}${q}`;
245
+ }
246
+ function makeLinkUrl(provider, params) {
247
+ const q = buildQuery({
248
+ redirectTo: params.redirectTo,
249
+ profile: params.profile != null ? String(params.profile) : void 0,
250
+ redirect: params.redirect
251
+ });
252
+ return `${baseUrl}/link/${provider}${q}`;
253
+ }
254
+ async function signIn(provider, options) {
255
+ const url = makeProviderUrl(provider, options);
256
+ return url;
257
+ }
258
+ async function linkAccount(provider, options) {
259
+ const linkUrl = makeLinkUrl(provider, { redirectTo: options?.redirectTo, profile: options?.profile, redirect: "false" });
260
+ const token = getSessionToken();
261
+ const fetchOptions = token ? { headers: { Authorization: `Bearer ${token}` } } : { credentials: "include" };
262
+ const res = await fetch(linkUrl, fetchOptions);
263
+ if (res.redirected)
264
+ return res.url;
265
+ try {
266
+ const data = await res.json();
267
+ if (data?.url)
268
+ return data.url;
269
+ } catch {
270
+ }
271
+ return linkUrl;
272
+ }
273
+ async function unlinkAccount(provider) {
274
+ const token = getSessionToken();
275
+ const fetchOptions = token ? { headers: { Authorization: `Bearer ${token}` } } : { credentials: "include" };
276
+ const res = await fetch(`${baseUrl}/unlink/${provider}`, { method: "POST", ...fetchOptions });
277
+ if (res.ok) {
278
+ await refreshSession();
279
+ return true;
280
+ }
281
+ return false;
282
+ }
283
+ async function signOut() {
284
+ clearSessionToken();
285
+ const token = getSessionToken();
286
+ const headers = token ? { Authorization: `Bearer ${token}` } : void 0;
287
+ await fetch(`${baseUrl}/signout`, token ? { method: "POST", headers } : { method: "POST", credentials: "include" });
288
+ await refreshSession();
289
+ }
290
+ return {
291
+ get session() {
292
+ return currentSession;
293
+ },
294
+ fetchSession,
295
+ refreshSession,
296
+ applySessionToken,
297
+ handleRedirectCallback,
298
+ onSessionChange,
299
+ signIn,
300
+ linkAccount,
301
+ unlinkAccount,
302
+ signOut
303
+ };
304
+ }
305
+
306
+ // src/client/solid/Protected.tsx
307
+ import { useNavigate } from "@solidjs/router";
308
+ import { onMount, Show } from "solid-js";
309
+ import { isServer } from "solid-js/web";
310
+ function Protected(page, fallbackOrRedirect) {
311
+ return () => {
312
+ const auth = useAuth();
313
+ const navigate = useNavigate();
314
+ const isRedirectMode = typeof fallbackOrRedirect === "string" || fallbackOrRedirect === void 0;
315
+ const redirectTo = isRedirectMode ? fallbackOrRedirect ?? "/" : void 0;
316
+ const Fallback = !isRedirectMode ? fallbackOrRedirect : void 0;
317
+ const Redirect = () => {
318
+ onMount(() => {
319
+ if (!isServer && redirectTo)
320
+ navigate(redirectTo, { replace: true });
321
+ });
322
+ return null;
323
+ };
324
+ return <Show
325
+ when={auth.session().user}
326
+ fallback={isRedirectMode ? <Redirect /> : Fallback ? <Fallback /> : null}
327
+ >
328
+ {page(auth.session)}
329
+ </Show>;
330
+ };
128
331
  }
129
332
 
130
333
  // src/client/solid/index.tsx
@@ -132,16 +335,13 @@ var AuthContext = createContext();
132
335
  function AuthProvider(props) {
133
336
  const scheme = untrack(() => props.scheme ?? "gau");
134
337
  const baseUrl = untrack(() => props.baseUrl ?? "/api/auth");
338
+ const client = createAuthClient({
339
+ baseUrl
340
+ });
135
341
  const fetchSession = async () => {
136
- if (isServer)
342
+ if (isServer2)
137
343
  return { ...NULL_SESSION, providers: [] };
138
- const token = getSessionToken();
139
- const headers = token ? { Authorization: `Bearer ${token}` } : void 0;
140
- const res = await fetch(`${baseUrl}/session`, token ? { headers } : { credentials: "include" });
141
- const contentType = res.headers.get("content-type");
142
- if (contentType?.includes("application/json"))
143
- return res.json();
144
- return { ...NULL_SESSION, providers: [] };
344
+ return client.refreshSession();
145
345
  };
146
346
  const [session, { refetch }] = createResource(
147
347
  fetchSession,
@@ -149,96 +349,69 @@ function AuthProvider(props) {
149
349
  );
150
350
  async function signIn(provider, { redirectTo, profile } = {}) {
151
351
  let finalRedirectTo = redirectTo ?? props.redirectTo;
152
- if (isTauri()) {
153
- await signInWithTauri(provider, baseUrl, scheme, finalRedirectTo, profile);
154
- } else {
155
- if (!finalRedirectTo && !isServer)
156
- finalRedirectTo = window.location.origin;
157
- const params = new URLSearchParams();
158
- if (finalRedirectTo)
159
- params.set("redirectTo", finalRedirectTo);
160
- if (profile)
161
- params.set("profile", String(profile));
162
- const q = params.toString();
163
- const authUrl = `${baseUrl}/${provider}${q ? `?${q}` : ""}`;
164
- window.location.href = authUrl;
352
+ if (!finalRedirectTo && !isServer2)
353
+ finalRedirectTo = window.location.origin;
354
+ if (!isServer2 && isTauri()) {
355
+ const { signInWithTauri: signInWithTauri2 } = await Promise.resolve().then(() => (init_tauri(), tauri_exports));
356
+ await signInWithTauri2(provider, baseUrl, scheme, finalRedirectTo, profile);
357
+ return;
165
358
  }
359
+ const url = await client.signIn(provider, { redirectTo: finalRedirectTo, profile });
360
+ if (!isServer2)
361
+ window.location.href = url;
166
362
  }
167
363
  async function linkAccount(provider, { redirectTo, profile } = {}) {
168
- if (isTauri()) {
169
- await linkAccountWithTauri(provider, baseUrl, scheme, redirectTo, profile);
364
+ if (!isServer2 && isTauri()) {
365
+ const { linkAccountWithTauri: linkAccountWithTauri2 } = await Promise.resolve().then(() => (init_tauri(), tauri_exports));
366
+ await linkAccountWithTauri2(provider, baseUrl, scheme, redirectTo, profile);
170
367
  return;
171
368
  }
172
369
  let finalRedirectTo = redirectTo ?? props.redirectTo;
173
- if (!finalRedirectTo && !isServer)
370
+ if (!finalRedirectTo && !isServer2)
174
371
  finalRedirectTo = window.location.href;
175
- const params = new URLSearchParams();
176
- if (finalRedirectTo)
177
- params.set("redirectTo", finalRedirectTo);
178
- if (profile)
179
- params.set("profile", String(profile));
180
- params.set("redirect", "false");
181
- const linkUrl = `${baseUrl}/link/${provider}?${params.toString()}`;
182
- const token = getSessionToken();
183
- const fetchOptions = token ? { headers: { Authorization: `Bearer ${token}` } } : { credentials: "include" };
184
- const res = await fetch(linkUrl, fetchOptions);
185
- if (res.redirected) {
186
- window.location.href = res.url;
187
- } else {
188
- const data = await res.json();
189
- if (data.url)
190
- window.location.href = data.url;
191
- }
372
+ const url = await client.linkAccount(provider, { redirectTo: finalRedirectTo, profile });
373
+ if (!isServer2)
374
+ window.location.href = url;
192
375
  }
193
376
  async function unlinkAccount(provider) {
194
- const token = getSessionToken();
195
- const fetchOptions = token ? { headers: { Authorization: `Bearer ${token}` } } : { credentials: "include" };
196
- const res = await fetch(`${baseUrl}/unlink/${provider}`, {
197
- method: "POST",
198
- ...fetchOptions
199
- });
200
- if (res.ok)
377
+ const ok = await client.unlinkAccount(provider);
378
+ if (ok)
201
379
  refetch();
202
380
  else
203
- console.error("Failed to unlink account", await res.json());
381
+ console.error("Failed to unlink account");
204
382
  }
205
383
  const signOut = async () => {
206
- clearSessionToken();
207
- const token = getSessionToken();
208
- const headers = token ? { Authorization: `Bearer ${token}` } : void 0;
209
- await fetch(`${baseUrl}/signout`, token ? { method: "POST", headers } : { method: "POST", credentials: "include" });
384
+ await client.signOut();
210
385
  refetch();
211
386
  };
212
- onMount(() => {
387
+ onMount2(() => {
213
388
  if (!isTauri()) {
214
- const hash = new URL(window.location.href).hash.substring(1);
215
- const params = new URLSearchParams(hash);
216
- const tokenParam = params.get("token");
217
- if (tokenParam) {
218
- storeSessionToken(tokenParam);
219
- refetch();
220
- window.history.replaceState(null, "", window.location.pathname + window.location.search);
221
- }
222
- }
223
- if (!isTauri())
389
+ void (async () => {
390
+ const handled = await client.handleRedirectCallback();
391
+ if (handled)
392
+ refetch();
393
+ })();
224
394
  return;
395
+ }
225
396
  let disposed = false;
226
- setupTauriListener(async (url) => {
227
- handleTauriDeepLink(url, baseUrl, scheme, (token) => {
228
- storeSessionToken(token);
397
+ void (async () => {
398
+ const { startAuthBridge: startAuthBridge2 } = await Promise.resolve().then(() => (init_tauri(), tauri_exports));
399
+ const unlisten = await startAuthBridge2(baseUrl, scheme, async (token) => {
400
+ await client.applySessionToken(token);
229
401
  refetch();
230
402
  });
231
- }).then((unlisten) => {
232
403
  if (disposed)
233
404
  unlisten?.();
234
405
  else if (unlisten)
235
406
  onCleanup(() => unlisten());
236
- });
407
+ })();
237
408
  onCleanup(() => {
238
409
  disposed = true;
239
410
  });
240
411
  });
241
- return <AuthContext.Provider value={{ session, signIn, linkAccount, unlinkAccount, signOut }}>
412
+ return <AuthContext.Provider value={{ session, signIn, linkAccount, unlinkAccount, signOut, refresh: async () => {
413
+ await refetch();
414
+ } }}>
242
415
  {props.children}
243
416
  </AuthContext.Provider>;
244
417
  }
@@ -248,27 +421,6 @@ function useAuth() {
248
421
  throw new Error("useAuth must be used within an AuthProvider");
249
422
  return context;
250
423
  }
251
- function Protected(page, fallbackOrRedirect) {
252
- return () => {
253
- const auth = useAuth();
254
- const isRedirectMode = typeof fallbackOrRedirect === "string" || fallbackOrRedirect === void 0;
255
- const redirectTo = isRedirectMode ? fallbackOrRedirect ?? "/" : void 0;
256
- const Fallback = !isRedirectMode ? fallbackOrRedirect : void 0;
257
- const Redirect = () => {
258
- onMount(() => {
259
- if (!isServer && redirectTo)
260
- window.location.replace(redirectTo);
261
- });
262
- return null;
263
- };
264
- return <Show
265
- when={auth.session().user}
266
- fallback={isRedirectMode ? <Redirect /> : Fallback ? <Fallback /> : null}
267
- >
268
- {page(auth.session)}
269
- </Show>;
270
- };
271
- }
272
424
  export {
273
425
  AuthProvider,
274
426
  Protected,
@@ -0,0 +1,32 @@
1
+ <script lang='ts'>
2
+ import type { Snippet } from 'svelte'
3
+ // @ts-expect-error svelte-kit
4
+ import { goto } from '$app/navigation'
5
+ import { BROWSER } from 'esm-env'
6
+ import { useAuth } from '../index.svelte'
7
+
8
+ type Props = {
9
+ redirectTo?: string
10
+ fallback?: Snippet
11
+ children: Snippet
12
+ }
13
+
14
+ const { redirectTo = '/', fallback, children }: Props = $props()
15
+
16
+ const auth = useAuth()
17
+
18
+ $effect(() => {
19
+ if (BROWSER && !auth.isLoading && !auth.session?.user)
20
+ goto(redirectTo)
21
+ })
22
+ </script>
23
+
24
+ {#if auth.isLoading}
25
+ {#if fallback}
26
+ {@render fallback()}
27
+ {/if}
28
+ {:else if auth.session?.user}
29
+ {@render children()}
30
+ {:else if fallback}
31
+ {@render fallback()}
32
+ {/if}
@@ -1 +1 @@
1
- import{BROWSER as t}from"esm-env";import{getContext as e,setContext as n}from"svelte";import{parse as o,serialize as i}from"cookie";import{createJWTSignatureMessage as a,encodeJWT as r,JWSRegisteredHeaders as s,JWTRegisteredClaims as c,parseJWT as l}from"@oslojs/jwt";import{generateCodeVerifier as u,generateState as p}from"arctic";var d={user:null,session:null,accounts:null};import{BROWSER as f}from"esm-env";import{BROWSER as w}from"esm-env";function h(t){if(w)try{localStorage.setItem("gau-token",t),document.cookie=`__gau-session-token=${t}; path=/; max-age=31536000; samesite=lax; secure`}catch{}}function m(){return w?localStorage.getItem("gau-token"):null}function g(){return f&&"__TAURI_INTERNALS__"in globalThis}var k=Symbol("gau-auth");function S({baseUrl:e="/api/auth",scheme:o="gau",redirectTo:i}={}){let a=$state({...d,providers:[]});async function r(){if(!t)return void(a={...d,providers:[]});const n=m(),o=n?{Authorization:`Bearer ${n}`}:void 0,i=await fetch(`${e}/session`,n?{headers:o}:{credentials:"include"}),r=i.headers.get("content-type");a=r?.includes("application/json")?await i.json():{...d,providers:[]}}if(t){const t=new URL(window.location.href).hash.substring(1),e=new URLSearchParams(t).get("token");e?(h(e),(async()=>{let t=t=>window.history.replaceState(null,"",t);try{const e="$app/navigation",{replaceState:n}=await import(e);t=t=>n(t,{})}catch{}t(window.location.pathname+window.location.search),await r()})()):r()}$effect(()=>{if(!t||!g())return;let n,i=!1;return async function(t){if(!g())return;const{listen:e}=await import("@tauri-apps/api/event");try{return await e("deep-link",async e=>{await t(e.payload)})}catch(t){console.error(t)}}(async t=>{!function(t,e,n,o){const i=new URL(t);if(i.protocol!==`${n}:`&&i.origin!==new URL(e).origin)return;const a=new URLSearchParams(i.hash.substring(1)).get("token");a&&o(a)}(t,e,o,async t=>{h(t),await r()})}).then(t=>{i?t?.():n=t}),()=>{i=!0,n?.()}});const s={get session(){return a},signIn:async function(n,{redirectTo:a,profile:r}={}){let s=a??i;if(g())await async function(t,e,n="gau",o,i){if(!g())return;const{platform:a}=await import("@tauri-apps/plugin-os"),{open:r}=await import("@tauri-apps/plugin-shell"),s=a();let c;c=o||("android"===s||"ios"===s?new URL(e).origin:`${n}://oauth/callback`);const l=new URLSearchParams;l.set("redirectTo",c),i&&l.set("profile",i);const u=`${e}/${t}?${l.toString()}`;await r(u)}(n,e,o,s,r);else{!s&&t&&(s=window.location.origin);const o=new URLSearchParams;s&&o.set("redirectTo",s),r&&o.set("profile",String(r));const i=o.toString();window.location.href=`${e}/${n}${i?`?${i}`:""}`}},linkAccount:async function(n,{redirectTo:a,profile:r}={}){if(g())return void await async function(t,e,n="gau",o,i){if(!g())return;const{platform:a}=await import("@tauri-apps/plugin-os"),{open:r}=await import("@tauri-apps/plugin-shell"),s=a();let c;c=o||("android"===s||"ios"===s?new URL(e).origin:`${n}://oauth/callback`);const l=m();if(!l)return void console.error("No session token found, cannot link account.");const u=new URLSearchParams;u.set("redirectTo",c),u.set("token",l),i&&u.set("profile",i);const p=`${e}/link/${t}?${u.toString()}`;await r(p)}(n,e,o,a,r);let s=a??i;!s&&t&&(s=window.location.href);const c=new URLSearchParams;s&&c.set("redirectTo",s),r&&c.set("profile",String(r)),c.set("redirect","false");const l=`${e}/link/${n}?${c.toString()}`,u=m(),p=u?{headers:{Authorization:`Bearer ${u}`}}:{credentials:"include"},d=await fetch(l,p);if(d.redirected)window.location.href=d.url;else try{const t=await d.json();t.url&&(window.location.href=t.url)}catch(t){console.error("Failed to parse response from link endpoint",t)}},unlinkAccount:async function(t){const n=m(),o=n?{headers:{Authorization:`Bearer ${n}`}}:{credentials:"include"},i=await fetch(`${e}/unlink/${t}`,{method:"POST",...o});i.ok?await r():console.error("Failed to unlink account",await i.json())},signOut:async function(){!function(){if(w)try{localStorage.removeItem("gau-token"),document.cookie="__gau-session-token=; path=/; max-age=0"}catch{}}();const t=m(),n=t?{Authorization:`Bearer ${t}`}:void 0;await fetch(`${e}/signout`,t?{method:"POST",headers:n}:{method:"POST",credentials:"include"}),await r()}};n(k,s)}function y(){const t=e(k);if(!t)throw new Error("useAuth must be used within an AuthProvider");return t}export{S as createSvelteAuth,y as useAuth};//# sourceMappingURL=index.svelte.js.map
1
+ var n=Object.defineProperty,t=Object.getOwnPropertyNames,e=(n,e)=>function(){return n&&(e=(0,n[t(n)[0]])(n=0)),e};import{BROWSER as i}from"esm-env";function r(){return i?localStorage.getItem("gau-token"):null}var o=e({"src/client/token.ts"(){}}),a={};((t,e)=>{for(var i in e)n(t,i,{get:e[i],enumerable:!0})})(a,{handleTauriDeepLink:()=>f,isTauri:()=>c,linkAccountWithTauri:()=>d,setupTauriListener:()=>l,signInWithTauri:()=>u,startAuthBridge:()=>w});import{BROWSER as s}from"esm-env";function c(){return s&&"__TAURI_INTERNALS__"in globalThis}async function u(n,t,e="gau",i,r){if(!c())return;const{platform:o}=await import("@tauri-apps/plugin-os"),{openUrl:a}=await import("@tauri-apps/plugin-opener"),s=o();let u;u=i||("android"===s||"ios"===s?new URL(t).origin:`${e}://oauth/callback`);const l=new URLSearchParams;l.set("redirectTo",u),r&&l.set("profile",String(r));const f=`${t}/${n}?${l.toString()}`;await a(f)}async function l(n){if(!c())return;const{listen:t}=await import("@tauri-apps/api/event");try{return await t("deep-link",async t=>{await n(t.payload)})}catch(n){console.error(n)}}function f(n,t,e,i){const r=new URL(n);if(r.protocol!==`${e}:`&&r.origin!==new URL(t).origin)return;const o=new URLSearchParams(r.hash.substring(1)).get("token");o&&i(o)}async function d(n,t,e="gau",i,o){if(!c())return;const{platform:a}=await import("@tauri-apps/plugin-os"),{openUrl:s}=await import("@tauri-apps/plugin-opener"),u=a();let l;l=i||("android"===u||"ios"===u?new URL(t).origin:`${e}://oauth/callback`);const f=r();if(!f)return void console.error("No session token found, cannot link account.");const d=new URLSearchParams;d.set("redirectTo",l),d.set("token",f),o&&d.set("profile",String(o));const w=`${t}/link/${n}?${d.toString()}`;await s(w)}async function w(n,t,e){if(!c())return;return await l(async i=>{f(i,n,t,e)})}var p=e({"src/runtimes/tauri/index.ts"(){o()}});import{replaceState as h}from"$app/navigation";import{BROWSER as g}from"esm-env";import{getContext as m,onMount as y,setContext as k}from"svelte";import{parse as S,serialize as v}from"cookie";import{createJWTSignatureMessage as T,encodeJWT as A,JWSRegisteredHeaders as R,JWTRegisteredClaims as b,parseJWT as U}from"@oslojs/jwt";import{generateCodeVerifier as P,generateState as L}from"arctic";var O={user:null,session:null,accounts:null};function _(n){const t=new URLSearchParams;for(const[e,i]of Object.entries(n))null!=i&&""!==i&&t.set(e,String(i));const e=t.toString();return e?`?${e}`:""}function I({baseUrl:n}){let t={user:null,session:null,accounts:null,providers:[]};const e=new Set;async function o(){const t=r(),e=t?{Authorization:`Bearer ${t}`}:void 0,i=await fetch(`${n}/session`,t?{headers:e}:{credentials:"include"}),o=i.headers.get("content-type");return o?.includes("application/json")?await i.json():{user:null,session:null,accounts:null,providers:[]}}async function a(){const n=await o();return t=n,(()=>{for(const n of e)n(t)})(),n}async function s(n){try{!function(n){if(i)try{localStorage.setItem("gau-token",n),document.cookie=`__gau-session-token=${n}; path=/; max-age=31536000; samesite=lax; secure`}catch{}}(n)}finally{await a()}}return{get session(){return t},fetchSession:o,refreshSession:a,applySessionToken:s,handleRedirectCallback:async function(n){if("undefined"==typeof window)return!1;if("#_=_"===window.location.hash){const t=window.location.pathname+window.location.search;return n?n(t):window.history.replaceState(null,"",t),!1}const t=window.location.hash?.substring(1)??"";if(!t)return!1;const e=new URLSearchParams(t).get("token");if(!e)return!1;await s(e);const i=window.location.pathname+window.location.search;return n?n(i):window.history.replaceState(null,"",i),!0},onSessionChange:function(n){return e.add(n),()=>e.delete(n)},signIn:async function(t,e){return function(t,e){const i=_({redirectTo:e?.redirectTo,profile:null!=e?.profile?String(e.profile):void 0});return`${n}/${t}${i}`}(t,e)},linkAccount:async function(t,e){const i=function(t,e){const i=_({redirectTo:e.redirectTo,profile:null!=e.profile?String(e.profile):void 0,redirect:e.redirect});return`${n}/link/${t}${i}`}(t,{redirectTo:e?.redirectTo,profile:e?.profile,redirect:"false"}),o=r(),a=o?{headers:{Authorization:`Bearer ${o}`}}:{credentials:"include"},s=await fetch(i,a);if(s.redirected)return s.url;try{const n=await s.json();if(n?.url)return n.url}catch{}return i},unlinkAccount:async function(t){const e=r(),i=e?{headers:{Authorization:`Bearer ${e}`}}:{credentials:"include"};return!!(await fetch(`${n}/unlink/${t}`,{method:"POST",...i})).ok&&(await a(),!0)},signOut:async function(){!function(){if(i)try{localStorage.removeItem("gau-token"),document.cookie="__gau-session-token=; path=/; max-age=0"}catch{}}();const t=r(),e=t?{Authorization:`Bearer ${t}`}:void 0;await fetch(`${n}/signout`,t?{method:"POST",headers:e}:{method:"POST",credentials:"include"}),await a()}}}p(),o();var j=Symbol("gau-auth");function B({baseUrl:n="/api/auth",scheme:t="gau",redirectTo:e}={}){const i=I({baseUrl:n}),r=async()=>g?i.refreshSession():{...O,providers:[]};let o=$state({...O,providers:[]}),s=$state(!0);y(()=>{if(!g)return;let e;(async()=>{await i.handleRedirectCallback(async n=>async function(n){try{h(n,{})}catch{g&&window.history.replaceState(null,"",n)}}(n))||(o=await r()),s=!1})();let u=!1;return c()?((async()=>{const{startAuthBridge:s}=await Promise.resolve().then(()=>(p(),a)),c=await s(n,t,async n=>{await i.applySessionToken(n),o=await r()});u?c?.():e=c})(),()=>{u=!0,e?.()}):void 0});k(j,{get session(){return o},get isLoading(){return s},signIn:async function(r,{redirectTo:o,profile:s}={}){let u=o??e;if(!u&&g&&(u=window.location.origin),c()){const{signInWithTauri:e}=await Promise.resolve().then(()=>(p(),a));return void await e(r,n,t,u,s)}const l=await i.signIn(r,{redirectTo:u,profile:s});g&&(window.location.href=l)},linkAccount:async function(r,{redirectTo:o,profile:s}={}){if(c()){const{linkAccountWithTauri:e}=await Promise.resolve().then(()=>(p(),a));return void await e(r,n,t,o,s)}let u=o??e;!u&&g&&(u=window.location.href);const l=await i.linkAccount(r,{redirectTo:u,profile:s});g&&(window.location.href=l)},unlinkAccount:async function(n){await i.unlinkAccount(n)?o=await r():console.error("Failed to unlink account")},signOut:async function(){await i.signOut(),o=await r()},refresh:async()=>{o=await r()}})}function W(){const n=m(j);if(!n)throw new Error("useAuth must be used within an AuthProvider");return n}export{B as createSvelteAuth,W as useAuth};//# sourceMappingURL=index.svelte.js.map