superso-js-sdk 1.0.1 → 1.0.2
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/auth/auth.d.ts +33 -5
- package/dist/auth/auth.js +283 -83
- package/package.json +1 -1
package/dist/auth/auth.d.ts
CHANGED
|
@@ -1,5 +1,28 @@
|
|
|
1
1
|
import { SupersoClient } from "../core/client";
|
|
2
|
-
|
|
2
|
+
export interface AuthUser {
|
|
3
|
+
id?: string;
|
|
4
|
+
email?: string;
|
|
5
|
+
phone?: string;
|
|
6
|
+
display_name?: string;
|
|
7
|
+
avatar_url?: string;
|
|
8
|
+
bio?: string;
|
|
9
|
+
[key: string]: any;
|
|
10
|
+
}
|
|
11
|
+
export interface AuthResponse {
|
|
12
|
+
token?: string;
|
|
13
|
+
refresh_token?: string;
|
|
14
|
+
user?: AuthUser;
|
|
15
|
+
message?: string;
|
|
16
|
+
[key: string]: any;
|
|
17
|
+
}
|
|
18
|
+
export type AuthListener = (payload: {
|
|
19
|
+
user?: AuthUser | null;
|
|
20
|
+
token?: string | null;
|
|
21
|
+
type?: string;
|
|
22
|
+
}) => void;
|
|
23
|
+
declare function parseJwt(token: string): any;
|
|
24
|
+
declare function isTokenExpired(token: string): boolean;
|
|
25
|
+
declare function saveSession(data: AuthResponse): void;
|
|
3
26
|
export declare function clearSession(): void;
|
|
4
27
|
export declare function getAccessToken(): string | null;
|
|
5
28
|
export declare function getRefreshToken(): string | null;
|
|
@@ -9,13 +32,13 @@ export declare function register(client: SupersoClient, payload: {
|
|
|
9
32
|
display_name?: string;
|
|
10
33
|
email: string;
|
|
11
34
|
password: string;
|
|
12
|
-
}): Promise<
|
|
35
|
+
}): Promise<AuthResponse>;
|
|
13
36
|
export declare function login(client: SupersoClient, payload: {
|
|
14
37
|
email: string;
|
|
15
38
|
password: string;
|
|
16
|
-
}): Promise<
|
|
39
|
+
}): Promise<AuthResponse>;
|
|
17
40
|
export declare function logout(client: SupersoClient): Promise<void>;
|
|
18
|
-
export declare function refreshToken(client: SupersoClient): Promise<
|
|
41
|
+
export declare function refreshToken(client: SupersoClient): Promise<AuthResponse>;
|
|
19
42
|
export declare function restoreSession(client: SupersoClient): Promise<any>;
|
|
20
43
|
export declare function getCurrentUser(client: SupersoClient): Promise<any>;
|
|
21
44
|
export declare function updateProfile(client: SupersoClient, data: {
|
|
@@ -63,4 +86,9 @@ export declare function verifyMagicLink(client: SupersoClient, payload: {
|
|
|
63
86
|
export declare function getSessions(client: SupersoClient): Promise<any>;
|
|
64
87
|
export declare function revokeSession(client: SupersoClient, sessionId: string): Promise<any>;
|
|
65
88
|
export declare function revokeOtherSessions(client: SupersoClient): Promise<any>;
|
|
66
|
-
export
|
|
89
|
+
export declare function signInWithGoogle(client: SupersoClient): Promise<any>;
|
|
90
|
+
export declare function signInWithFacebook(client: SupersoClient, options: {
|
|
91
|
+
appId: string;
|
|
92
|
+
redirectUri?: string;
|
|
93
|
+
}): Promise<any>;
|
|
94
|
+
export { saveSession, parseJwt, isTokenExpired, };
|
package/dist/auth/auth.js
CHANGED
|
@@ -1,19 +1,43 @@
|
|
|
1
|
-
//
|
|
1
|
+
// ========================================
|
|
2
2
|
// CONSTANTS
|
|
3
|
-
//
|
|
3
|
+
// ========================================
|
|
4
4
|
const ACCESS_TOKEN_KEY = "superso_access_token";
|
|
5
5
|
const REFRESH_TOKEN_KEY = "superso_refresh_token";
|
|
6
6
|
const USER_KEY = "superso_auth_user";
|
|
7
|
+
const FACEBOOK_STATE_KEY = "superso_fb_state";
|
|
8
|
+
// ========================================
|
|
9
|
+
// HELPERS
|
|
10
|
+
// ========================================
|
|
11
|
+
function isBrowser() {
|
|
12
|
+
return (typeof window !==
|
|
13
|
+
"undefined");
|
|
14
|
+
}
|
|
15
|
+
function safeLocalStorage() {
|
|
16
|
+
if (!isBrowser())
|
|
17
|
+
return null;
|
|
18
|
+
return localStorage;
|
|
19
|
+
}
|
|
20
|
+
// ========================================
|
|
21
|
+
// AUTH LISTENERS
|
|
22
|
+
// ========================================
|
|
7
23
|
const listeners = new Set();
|
|
8
24
|
function emitAuth(payload) {
|
|
9
|
-
listeners.forEach((callback) =>
|
|
25
|
+
listeners.forEach((callback) => {
|
|
26
|
+
try {
|
|
27
|
+
callback(payload);
|
|
28
|
+
}
|
|
29
|
+
catch (error) {
|
|
30
|
+
console.error("Auth listener error:", error);
|
|
31
|
+
}
|
|
32
|
+
});
|
|
10
33
|
}
|
|
11
|
-
//
|
|
34
|
+
// ========================================
|
|
12
35
|
// JWT HELPERS
|
|
13
|
-
//
|
|
36
|
+
// ========================================
|
|
14
37
|
function parseJwt(token) {
|
|
15
38
|
try {
|
|
16
|
-
|
|
39
|
+
const payload = token.split(".")[1];
|
|
40
|
+
return JSON.parse(atob(payload));
|
|
17
41
|
}
|
|
18
42
|
catch (_a) {
|
|
19
43
|
return null;
|
|
@@ -28,42 +52,59 @@ function isTokenExpired(token) {
|
|
|
28
52
|
1000 -
|
|
29
53
|
5 * 60 * 1000);
|
|
30
54
|
}
|
|
31
|
-
//
|
|
55
|
+
// ========================================
|
|
32
56
|
// SESSION HELPERS
|
|
33
|
-
//
|
|
57
|
+
// ========================================
|
|
34
58
|
function saveSession(data) {
|
|
59
|
+
const storage = safeLocalStorage();
|
|
60
|
+
if (!storage)
|
|
61
|
+
return;
|
|
35
62
|
const token = data === null || data === void 0 ? void 0 : data.token;
|
|
36
63
|
const refreshToken = data === null || data === void 0 ? void 0 : data.refresh_token;
|
|
37
64
|
const user = data === null || data === void 0 ? void 0 : data.user;
|
|
38
65
|
if (token) {
|
|
39
|
-
|
|
66
|
+
storage.setItem(ACCESS_TOKEN_KEY, token);
|
|
40
67
|
}
|
|
41
68
|
if (refreshToken) {
|
|
42
|
-
|
|
69
|
+
storage.setItem(REFRESH_TOKEN_KEY, refreshToken);
|
|
43
70
|
}
|
|
44
71
|
if (user) {
|
|
45
|
-
|
|
72
|
+
storage.setItem(USER_KEY, JSON.stringify(user));
|
|
46
73
|
}
|
|
47
74
|
emitAuth({
|
|
48
75
|
user,
|
|
76
|
+
token,
|
|
49
77
|
});
|
|
50
78
|
}
|
|
51
79
|
export function clearSession() {
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
80
|
+
const storage = safeLocalStorage();
|
|
81
|
+
if (!storage)
|
|
82
|
+
return;
|
|
83
|
+
storage.removeItem(ACCESS_TOKEN_KEY);
|
|
84
|
+
storage.removeItem(REFRESH_TOKEN_KEY);
|
|
85
|
+
storage.removeItem(USER_KEY);
|
|
55
86
|
emitAuth({
|
|
56
87
|
user: null,
|
|
88
|
+
token: null,
|
|
57
89
|
});
|
|
58
90
|
}
|
|
59
91
|
export function getAccessToken() {
|
|
60
|
-
|
|
92
|
+
const storage = safeLocalStorage();
|
|
93
|
+
if (!storage)
|
|
94
|
+
return null;
|
|
95
|
+
return storage.getItem(ACCESS_TOKEN_KEY);
|
|
61
96
|
}
|
|
62
97
|
export function getRefreshToken() {
|
|
63
|
-
|
|
98
|
+
const storage = safeLocalStorage();
|
|
99
|
+
if (!storage)
|
|
100
|
+
return null;
|
|
101
|
+
return storage.getItem(REFRESH_TOKEN_KEY);
|
|
64
102
|
}
|
|
65
103
|
export function getStoredUser() {
|
|
66
|
-
const
|
|
104
|
+
const storage = safeLocalStorage();
|
|
105
|
+
if (!storage)
|
|
106
|
+
return null;
|
|
107
|
+
const raw = storage.getItem(USER_KEY);
|
|
67
108
|
if (!raw)
|
|
68
109
|
return null;
|
|
69
110
|
try {
|
|
@@ -73,21 +114,51 @@ export function getStoredUser() {
|
|
|
73
114
|
return null;
|
|
74
115
|
}
|
|
75
116
|
}
|
|
76
|
-
//
|
|
117
|
+
// ========================================
|
|
118
|
+
// GOOGLE SDK LOADER
|
|
119
|
+
// ========================================
|
|
120
|
+
async function loadGoogleSdk() {
|
|
121
|
+
if (!isBrowser())
|
|
122
|
+
return;
|
|
123
|
+
if (window.google) {
|
|
124
|
+
return;
|
|
125
|
+
}
|
|
126
|
+
return new Promise((resolve, reject) => {
|
|
127
|
+
const existing = document.getElementById("superso-google-sdk");
|
|
128
|
+
if (existing) {
|
|
129
|
+
resolve(true);
|
|
130
|
+
return;
|
|
131
|
+
}
|
|
132
|
+
const script = document.createElement("script");
|
|
133
|
+
script.id =
|
|
134
|
+
"superso-google-sdk";
|
|
135
|
+
script.src =
|
|
136
|
+
"https://accounts.google.com/gsi/client";
|
|
137
|
+
script.async = true;
|
|
138
|
+
script.defer = true;
|
|
139
|
+
script.onload =
|
|
140
|
+
() => resolve(true);
|
|
141
|
+
script.onerror =
|
|
142
|
+
() => reject(new Error("Failed to load Google SDK"));
|
|
143
|
+
document.body.appendChild(script);
|
|
144
|
+
});
|
|
145
|
+
}
|
|
146
|
+
// ========================================
|
|
77
147
|
// CORE REQUEST
|
|
78
|
-
//
|
|
148
|
+
// ========================================
|
|
79
149
|
async function request(client, endpoint, method = "GET", body = null, auth = false) {
|
|
80
150
|
let token = getAccessToken();
|
|
81
|
-
// auto refresh
|
|
151
|
+
// auto refresh token
|
|
82
152
|
if (auth &&
|
|
83
153
|
token &&
|
|
84
154
|
isTokenExpired(token)) {
|
|
85
155
|
try {
|
|
86
156
|
const refreshed = await refreshToken(client);
|
|
87
157
|
token =
|
|
88
|
-
refreshed === null || refreshed === void 0 ? void 0 : refreshed.token;
|
|
158
|
+
(refreshed === null || refreshed === void 0 ? void 0 : refreshed.token) || null;
|
|
89
159
|
}
|
|
90
|
-
catch (
|
|
160
|
+
catch (error) {
|
|
161
|
+
console.error("Token refresh failed:", error);
|
|
91
162
|
clearSession();
|
|
92
163
|
}
|
|
93
164
|
}
|
|
@@ -95,14 +166,15 @@ async function request(client, endpoint, method = "GET", body = null, auth = fal
|
|
|
95
166
|
"Content-Type": "application/json",
|
|
96
167
|
"X-Superso-Project-Key": client.apiKey,
|
|
97
168
|
};
|
|
98
|
-
if (auth &&
|
|
99
|
-
|
|
169
|
+
if (auth &&
|
|
170
|
+
token) {
|
|
171
|
+
headers.Authorization =
|
|
100
172
|
`Bearer ${token}`;
|
|
101
173
|
}
|
|
102
174
|
const response = await fetch(`${client.baseUrl}/api/project/${client.projectId}${endpoint}`, {
|
|
103
175
|
method,
|
|
104
176
|
headers,
|
|
105
|
-
body: body
|
|
177
|
+
body: body !== null
|
|
106
178
|
? JSON.stringify(body)
|
|
107
179
|
: undefined,
|
|
108
180
|
});
|
|
@@ -111,86 +183,94 @@ async function request(client, endpoint, method = "GET", body = null, auth = fal
|
|
|
111
183
|
data =
|
|
112
184
|
await response.json();
|
|
113
185
|
}
|
|
114
|
-
catch (
|
|
186
|
+
catch (_a) {
|
|
115
187
|
data = {};
|
|
116
188
|
}
|
|
117
189
|
if (!response.ok) {
|
|
118
190
|
throw new Error((data === null || data === void 0 ? void 0 : data.message) ||
|
|
191
|
+
(data === null || data === void 0 ? void 0 : data.error) ||
|
|
119
192
|
"Request failed");
|
|
120
193
|
}
|
|
121
194
|
return data;
|
|
122
195
|
}
|
|
123
|
-
//
|
|
196
|
+
// ========================================
|
|
124
197
|
// AUTH STATE
|
|
125
|
-
//
|
|
198
|
+
// ========================================
|
|
126
199
|
export function onAuthChange(callback) {
|
|
127
200
|
listeners.add(callback);
|
|
128
201
|
return () => {
|
|
129
202
|
listeners.delete(callback);
|
|
130
203
|
};
|
|
131
204
|
}
|
|
132
|
-
//
|
|
133
|
-
// MULTI TAB
|
|
134
|
-
//
|
|
135
|
-
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
205
|
+
// ========================================
|
|
206
|
+
// MULTI TAB SYNC
|
|
207
|
+
// ========================================
|
|
208
|
+
if (isBrowser()) {
|
|
209
|
+
window.addEventListener("storage", (event) => {
|
|
210
|
+
if (event.key ===
|
|
211
|
+
ACCESS_TOKEN_KEY ||
|
|
212
|
+
event.key ===
|
|
213
|
+
USER_KEY) {
|
|
214
|
+
emitAuth({
|
|
215
|
+
user: getStoredUser(),
|
|
216
|
+
token: getAccessToken(),
|
|
217
|
+
});
|
|
218
|
+
}
|
|
219
|
+
});
|
|
220
|
+
}
|
|
221
|
+
// ========================================
|
|
144
222
|
// REGISTER
|
|
145
|
-
//
|
|
223
|
+
// ========================================
|
|
146
224
|
export async function register(client, payload) {
|
|
147
|
-
const
|
|
148
|
-
if (
|
|
149
|
-
saveSession(
|
|
225
|
+
const result = await request(client, "/auth/register", "POST", payload);
|
|
226
|
+
if (result === null || result === void 0 ? void 0 : result.token) {
|
|
227
|
+
saveSession(result);
|
|
150
228
|
}
|
|
151
|
-
return
|
|
229
|
+
return result;
|
|
152
230
|
}
|
|
153
|
-
//
|
|
231
|
+
// ========================================
|
|
154
232
|
// LOGIN
|
|
155
|
-
//
|
|
233
|
+
// ========================================
|
|
156
234
|
export async function login(client, payload) {
|
|
157
|
-
const
|
|
158
|
-
saveSession(
|
|
159
|
-
return
|
|
235
|
+
const result = await request(client, "/auth/login", "POST", payload);
|
|
236
|
+
saveSession(result);
|
|
237
|
+
return result;
|
|
160
238
|
}
|
|
161
|
-
//
|
|
239
|
+
// ========================================
|
|
162
240
|
// LOGOUT
|
|
163
|
-
//
|
|
241
|
+
// ========================================
|
|
164
242
|
export async function logout(client) {
|
|
165
243
|
try {
|
|
166
244
|
await request(client, "/auth/logout", "POST", {
|
|
167
245
|
refresh_token: getRefreshToken(),
|
|
168
246
|
}, true);
|
|
169
247
|
}
|
|
170
|
-
catch (
|
|
248
|
+
catch (error) {
|
|
249
|
+
console.error(error);
|
|
250
|
+
}
|
|
171
251
|
clearSession();
|
|
172
252
|
}
|
|
173
|
-
//
|
|
253
|
+
// ========================================
|
|
174
254
|
// REFRESH TOKEN
|
|
175
|
-
//
|
|
255
|
+
// ========================================
|
|
176
256
|
export async function refreshToken(client) {
|
|
177
257
|
const refresh_token = getRefreshToken();
|
|
178
258
|
if (!refresh_token) {
|
|
179
259
|
throw new Error("Missing refresh token");
|
|
180
260
|
}
|
|
181
|
-
const
|
|
261
|
+
const result = await request(client, "/auth/refresh-token", "POST", {
|
|
182
262
|
refresh_token,
|
|
183
263
|
});
|
|
184
|
-
saveSession(
|
|
264
|
+
saveSession(result);
|
|
185
265
|
emitAuth({
|
|
186
266
|
type: "token_rotated",
|
|
187
|
-
token:
|
|
267
|
+
token: result === null || result === void 0 ? void 0 : result.token,
|
|
188
268
|
});
|
|
189
|
-
return
|
|
269
|
+
return result;
|
|
190
270
|
}
|
|
191
|
-
//
|
|
271
|
+
// ========================================
|
|
192
272
|
// RESTORE SESSION
|
|
193
|
-
//
|
|
273
|
+
// ========================================
|
|
194
274
|
export async function restoreSession(client) {
|
|
195
275
|
const token = getAccessToken();
|
|
196
276
|
if (!token)
|
|
@@ -206,74 +286,83 @@ export async function restoreSession(client) {
|
|
|
206
286
|
});
|
|
207
287
|
return me;
|
|
208
288
|
}
|
|
209
|
-
catch (
|
|
289
|
+
catch (error) {
|
|
290
|
+
console.error(error);
|
|
210
291
|
clearSession();
|
|
211
292
|
return null;
|
|
212
293
|
}
|
|
213
294
|
}
|
|
214
|
-
//
|
|
295
|
+
// ========================================
|
|
215
296
|
// CURRENT USER
|
|
216
|
-
//
|
|
297
|
+
// ========================================
|
|
217
298
|
export async function getCurrentUser(client) {
|
|
218
299
|
return await request(client, "/auth/user/me", "GET", null, true);
|
|
219
300
|
}
|
|
220
|
-
//
|
|
301
|
+
// ========================================
|
|
221
302
|
// UPDATE PROFILE
|
|
222
|
-
//
|
|
303
|
+
// ========================================
|
|
223
304
|
export async function updateProfile(client, data) {
|
|
224
|
-
|
|
305
|
+
const result = await request(client, "/auth/user/profile", "PUT", data, true);
|
|
306
|
+
if (result === null || result === void 0 ? void 0 : result.user) {
|
|
307
|
+
const storage = safeLocalStorage();
|
|
308
|
+
storage === null || storage === void 0 ? void 0 : storage.setItem(USER_KEY, JSON.stringify(result.user));
|
|
309
|
+
emitAuth({
|
|
310
|
+
user: result.user,
|
|
311
|
+
});
|
|
312
|
+
}
|
|
313
|
+
return result;
|
|
225
314
|
}
|
|
226
|
-
//
|
|
315
|
+
// ========================================
|
|
227
316
|
// CHANGE PASSWORD
|
|
228
|
-
//
|
|
317
|
+
// ========================================
|
|
229
318
|
export async function changePassword(client, data) {
|
|
230
319
|
return await request(client, "/auth/user/change-password", "POST", data, true);
|
|
231
320
|
}
|
|
232
|
-
//
|
|
321
|
+
// ========================================
|
|
233
322
|
// CHANGE EMAIL
|
|
234
|
-
//
|
|
323
|
+
// ========================================
|
|
235
324
|
export async function changeEmail(client, data) {
|
|
236
325
|
return await request(client, "/auth/user/change-email", "POST", data, true);
|
|
237
326
|
}
|
|
238
|
-
//
|
|
327
|
+
// ========================================
|
|
239
328
|
// OTP LOGIN
|
|
240
|
-
//
|
|
329
|
+
// ========================================
|
|
241
330
|
export async function sendOtpLogin(client, payload) {
|
|
242
331
|
return await request(client, "/auth/otp-login", "POST", payload);
|
|
243
332
|
}
|
|
244
|
-
//
|
|
333
|
+
// ========================================
|
|
245
334
|
// VERIFY EMAIL
|
|
246
|
-
//
|
|
335
|
+
// ========================================
|
|
247
336
|
export async function verifyEmail(client, payload) {
|
|
248
337
|
return await request(client, "/auth/verify-email", "POST", payload);
|
|
249
338
|
}
|
|
250
|
-
//
|
|
339
|
+
// ========================================
|
|
251
340
|
// VERIFY PHONE
|
|
252
|
-
//
|
|
341
|
+
// ========================================
|
|
253
342
|
export async function verifyPhone(client, payload) {
|
|
254
343
|
return await request(client, "/auth/verify-phone", "POST", payload);
|
|
255
344
|
}
|
|
256
|
-
//
|
|
345
|
+
// ========================================
|
|
257
346
|
// PASSWORD RESET
|
|
258
|
-
//
|
|
347
|
+
// ========================================
|
|
259
348
|
export async function sendPasswordReset(client, payload) {
|
|
260
349
|
return await request(client, "/auth/send-reset", "POST", payload);
|
|
261
350
|
}
|
|
262
351
|
export async function confirmPasswordReset(client, payload) {
|
|
263
352
|
return await request(client, "/auth/confirm-reset", "POST", payload);
|
|
264
353
|
}
|
|
265
|
-
//
|
|
354
|
+
// ========================================
|
|
266
355
|
// MAGIC LINK
|
|
267
|
-
//
|
|
356
|
+
// ========================================
|
|
268
357
|
export async function sendMagicLink(client, payload) {
|
|
269
358
|
return await request(client, "/auth/magic-link/send", "POST", payload);
|
|
270
359
|
}
|
|
271
360
|
export async function verifyMagicLink(client, payload) {
|
|
272
361
|
return await request(client, "/auth/magic-link/verify", "POST", payload);
|
|
273
362
|
}
|
|
274
|
-
//
|
|
363
|
+
// ========================================
|
|
275
364
|
// SESSIONS
|
|
276
|
-
//
|
|
365
|
+
// ========================================
|
|
277
366
|
export async function getSessions(client) {
|
|
278
367
|
return await request(client, "/auth/user/sessions", "GET", null, true);
|
|
279
368
|
}
|
|
@@ -283,3 +372,114 @@ export async function revokeSession(client, sessionId) {
|
|
|
283
372
|
export async function revokeOtherSessions(client) {
|
|
284
373
|
return await request(client, "/auth/user/sessions", "DELETE", null, true);
|
|
285
374
|
}
|
|
375
|
+
// ========================================
|
|
376
|
+
// GOOGLE LOGIN
|
|
377
|
+
// ========================================
|
|
378
|
+
export async function signInWithGoogle(client) {
|
|
379
|
+
await loadGoogleSdk();
|
|
380
|
+
const config = await request(client, "/auth/providers/google/config", "GET");
|
|
381
|
+
const googleClientId = config === null || config === void 0 ? void 0 : config.client_id;
|
|
382
|
+
if (!googleClientId) {
|
|
383
|
+
throw new Error("Google auth not configured");
|
|
384
|
+
}
|
|
385
|
+
return new Promise((resolve, reject) => {
|
|
386
|
+
const google = window.google;
|
|
387
|
+
if (!google) {
|
|
388
|
+
reject(new Error("Google SDK not loaded"));
|
|
389
|
+
return;
|
|
390
|
+
}
|
|
391
|
+
google.accounts.id.initialize({
|
|
392
|
+
client_id: googleClientId,
|
|
393
|
+
callback: async (credentialResponse) => {
|
|
394
|
+
try {
|
|
395
|
+
const result = await request(client, "/auth/providers/google/credential", "POST", {
|
|
396
|
+
credential: credentialResponse.credential,
|
|
397
|
+
});
|
|
398
|
+
saveSession(result);
|
|
399
|
+
resolve(result);
|
|
400
|
+
}
|
|
401
|
+
catch (error) {
|
|
402
|
+
reject(error);
|
|
403
|
+
}
|
|
404
|
+
},
|
|
405
|
+
});
|
|
406
|
+
google.accounts.id.prompt();
|
|
407
|
+
});
|
|
408
|
+
}
|
|
409
|
+
// ========================================
|
|
410
|
+
// FACEBOOK LOGIN
|
|
411
|
+
// ========================================
|
|
412
|
+
export async function signInWithFacebook(client, options) {
|
|
413
|
+
if (!isBrowser()) {
|
|
414
|
+
throw new Error("Browser environment required");
|
|
415
|
+
}
|
|
416
|
+
const appId = options === null || options === void 0 ? void 0 : options.appId;
|
|
417
|
+
if (!appId) {
|
|
418
|
+
throw new Error("Facebook App ID required");
|
|
419
|
+
}
|
|
420
|
+
const redirectUri = (options === null || options === void 0 ? void 0 : options.redirectUri) ||
|
|
421
|
+
window.location.origin;
|
|
422
|
+
const state = crypto.randomUUID();
|
|
423
|
+
localStorage.setItem(FACEBOOK_STATE_KEY, state);
|
|
424
|
+
const authUrl = `https://www.facebook.com/v19.0/dialog/oauth` +
|
|
425
|
+
`?client_id=${appId}` +
|
|
426
|
+
`&redirect_uri=${encodeURIComponent(redirectUri)}` +
|
|
427
|
+
`&scope=email,public_profile` +
|
|
428
|
+
`&response_type=token` +
|
|
429
|
+
`&state=${state}`;
|
|
430
|
+
const popup = window.open(authUrl, "facebook-login", "width=600,height=700");
|
|
431
|
+
return new Promise((resolve, reject) => {
|
|
432
|
+
let stopped = false;
|
|
433
|
+
const stop = () => {
|
|
434
|
+
if (stopped)
|
|
435
|
+
return;
|
|
436
|
+
stopped =
|
|
437
|
+
true;
|
|
438
|
+
clearInterval(interval);
|
|
439
|
+
};
|
|
440
|
+
const interval = setInterval(async () => {
|
|
441
|
+
try {
|
|
442
|
+
if (!popup ||
|
|
443
|
+
popup.closed) {
|
|
444
|
+
stop();
|
|
445
|
+
reject(new Error("Facebook login cancelled"));
|
|
446
|
+
return;
|
|
447
|
+
}
|
|
448
|
+
const hash = popup.location
|
|
449
|
+
.hash;
|
|
450
|
+
if (hash &&
|
|
451
|
+
hash.includes("access_token")) {
|
|
452
|
+
stop();
|
|
453
|
+
const params = new URLSearchParams(hash.replace("#", ""));
|
|
454
|
+
const accessToken = params.get("access_token");
|
|
455
|
+
const returnedState = params.get("state");
|
|
456
|
+
const savedState = localStorage.getItem(FACEBOOK_STATE_KEY);
|
|
457
|
+
if (returnedState !==
|
|
458
|
+
savedState) {
|
|
459
|
+
popup.close();
|
|
460
|
+
reject(new Error("Invalid Facebook state"));
|
|
461
|
+
return;
|
|
462
|
+
}
|
|
463
|
+
popup.close();
|
|
464
|
+
localStorage.removeItem(FACEBOOK_STATE_KEY);
|
|
465
|
+
const result = await request(client, "/auth/providers/facebook/login", "POST", {
|
|
466
|
+
access_token: accessToken,
|
|
467
|
+
});
|
|
468
|
+
saveSession(result);
|
|
469
|
+
resolve(result);
|
|
470
|
+
}
|
|
471
|
+
}
|
|
472
|
+
catch (_a) { }
|
|
473
|
+
}, 1000);
|
|
474
|
+
setTimeout(() => {
|
|
475
|
+
stop();
|
|
476
|
+
reject(new Error("Facebook login timeout"));
|
|
477
|
+
}, 1000 *
|
|
478
|
+
60 *
|
|
479
|
+
5);
|
|
480
|
+
});
|
|
481
|
+
}
|
|
482
|
+
// ========================================
|
|
483
|
+
// EXPORTS
|
|
484
|
+
// ========================================
|
|
485
|
+
export { saveSession, parseJwt, isTokenExpired, };
|