@djangocfg/api 2.1.602 → 2.1.604
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.cjs +94 -13
- package/dist/auth.cjs.map +1 -1
- package/dist/auth.mjs +94 -13
- package/dist/auth.mjs.map +1 -1
- package/dist/clients.cjs +94 -13
- package/dist/clients.cjs.map +1 -1
- package/dist/clients.mjs +94 -13
- package/dist/clients.mjs.map +1 -1
- package/dist/hooks.cjs +94 -13
- package/dist/hooks.cjs.map +1 -1
- package/dist/hooks.mjs +94 -13
- package/dist/hooks.mjs.map +1 -1
- package/dist/index.cjs +94 -13
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +20 -1
- package/dist/index.d.ts +20 -1
- package/dist/index.mjs +94 -13
- package/dist/index.mjs.map +1 -1
- package/dist/storage.cjs +67 -9
- package/dist/storage.cjs.map +1 -1
- package/dist/storage.d.cts +24 -2
- package/dist/storage.d.ts +24 -2
- package/dist/storage.mjs +67 -9
- package/dist/storage.mjs.map +1 -1
- package/package.json +2 -2
- package/src/__tests__/sharedCookie.test.ts +112 -0
- package/src/_api/generated/helpers/auth.ts +58 -9
- package/src/_api/generated/helpers/keys.ts +74 -9
- package/src/cookies.ts +22 -0
- package/src/storage.ts +2 -0
package/dist/clients.mjs
CHANGED
|
@@ -70,8 +70,8 @@ var APIError = class extends Error {
|
|
|
70
70
|
var k = /* @__PURE__ */ __name((key, store, personal) => ({ key, store, personal }), "k");
|
|
71
71
|
var f = /* @__PURE__ */ __name((prefix, store, personal) => ({ prefix, store, personal }), "f");
|
|
72
72
|
var CFG_KEYS = {
|
|
73
|
-
accessToken: k("cfg.auth.access_token", "
|
|
74
|
-
refreshToken: k("cfg.auth.refresh_token", "
|
|
73
|
+
accessToken: k("cfg.auth.access_token", "cookie", true),
|
|
74
|
+
refreshToken: k("cfg.auth.refresh_token", "cookie", true),
|
|
75
75
|
apiKey: k("cfg.auth.api_key", "local", true),
|
|
76
76
|
email: k("cfg.auth.email", "local", false),
|
|
77
77
|
emailTs: k("cfg.auth.email_ts", "local", false),
|
|
@@ -106,6 +106,31 @@ function normalizeSegment(raw) {
|
|
|
106
106
|
}
|
|
107
107
|
__name(normalizeSegment, "normalizeSegment");
|
|
108
108
|
var hasWindow = /* @__PURE__ */ __name(() => typeof window !== "undefined", "hasWindow");
|
|
109
|
+
var domainByHost = /* @__PURE__ */ new Map();
|
|
110
|
+
function detectCookieDomain() {
|
|
111
|
+
if (!hasWindow() || typeof document === "undefined") return null;
|
|
112
|
+
const host = window.location.hostname.toLowerCase();
|
|
113
|
+
if (!host || !host.includes(".") || host.includes(":") || /^[0-9.]+$/.test(host)) return null;
|
|
114
|
+
const cached = domainByHost.get(host);
|
|
115
|
+
if (cached !== void 0) return cached;
|
|
116
|
+
const labels = host.split(".");
|
|
117
|
+
const secure = window.location.protocol === "https:" ? "; Secure" : "";
|
|
118
|
+
let found = null;
|
|
119
|
+
try {
|
|
120
|
+
for (let i = labels.length - 2; i >= 0 && found === null; i -= 1) {
|
|
121
|
+
const candidate = labels.slice(i).join(".");
|
|
122
|
+
const probe = "cfg_probe_" + Math.random().toString(36).slice(2);
|
|
123
|
+
document.cookie = probe + "=1; Domain=" + candidate + "; Path=/; Max-Age=30; SameSite=Lax" + secure;
|
|
124
|
+
if (document.cookie.includes(probe + "=1")) found = candidate;
|
|
125
|
+
document.cookie = probe + "=; Domain=" + candidate + "; Path=/; Max-Age=0; SameSite=Lax" + secure;
|
|
126
|
+
}
|
|
127
|
+
} catch {
|
|
128
|
+
found = null;
|
|
129
|
+
}
|
|
130
|
+
domainByHost.set(host, found);
|
|
131
|
+
return found;
|
|
132
|
+
}
|
|
133
|
+
__name(detectCookieDomain, "detectCookieDomain");
|
|
109
134
|
function nativeStorage(store) {
|
|
110
135
|
if (!hasWindow()) return null;
|
|
111
136
|
try {
|
|
@@ -131,6 +156,12 @@ function createStorage(owner, options = {}) {
|
|
|
131
156
|
const prefix = `${owner}.`;
|
|
132
157
|
const pattern = owner === "cfg" ? /^cfg(\.[a-z0-9_]+)+$/ : new RegExp(`^(cfg|${owner})(\\.[a-z0-9_]+)+$`);
|
|
133
158
|
const cookieMaxAge = options.cookieMaxAgeSeconds ?? 60 * 60 * 24 * 30;
|
|
159
|
+
let cookiePolicy = options.cookieDomain ?? "auto";
|
|
160
|
+
const resolveCookieDomain = /* @__PURE__ */ __name(() => cookiePolicy === false ? null : cookiePolicy === "auto" ? detectCookieDomain() : cookiePolicy, "resolveCookieDomain");
|
|
161
|
+
const expireCookie = /* @__PURE__ */ __name((key, domain) => {
|
|
162
|
+
const secure = window.location.protocol === "https:" ? "; Secure" : "";
|
|
163
|
+
document.cookie = encodeURIComponent(key) + "=; Path=/; Max-Age=0; SameSite=Lax" + (domain ? "; Domain=" + domain : "") + secure;
|
|
164
|
+
}, "expireCookie");
|
|
134
165
|
const specs = Object.values(options.keys ?? {});
|
|
135
166
|
const families = Object.values(options.families ?? {});
|
|
136
167
|
const specByKey = /* @__PURE__ */ new Map();
|
|
@@ -167,12 +198,15 @@ function createStorage(owner, options = {}) {
|
|
|
167
198
|
return memory[store].get(key) ?? null;
|
|
168
199
|
}
|
|
169
200
|
__name(rawGet, "rawGet");
|
|
170
|
-
function rawSet(store, key, value) {
|
|
201
|
+
function rawSet(store, key, value, maxAgeSeconds) {
|
|
171
202
|
if (!hasWindow()) return false;
|
|
172
203
|
try {
|
|
173
204
|
if (store === "cookie") {
|
|
174
205
|
const secure = window.location.protocol === "https:" ? "; Secure" : "";
|
|
175
|
-
|
|
206
|
+
const domain = resolveCookieDomain();
|
|
207
|
+
const domainPart = domain ? `; Domain=${domain}` : "";
|
|
208
|
+
document.cookie = `${encodeURIComponent(key)}=${encodeURIComponent(value)}; Path=/; Max-Age=${Math.max(1, Math.floor(maxAgeSeconds ?? cookieMaxAge))}; SameSite=Lax${domainPart}${secure}`;
|
|
209
|
+
if (domain) expireCookie(key, null);
|
|
176
210
|
if (rawGet("cookie", key) === value && !memory.cookie.has(key)) return true;
|
|
177
211
|
memory.cookie.set(key, value);
|
|
178
212
|
return false;
|
|
@@ -193,8 +227,9 @@ function createStorage(owner, options = {}) {
|
|
|
193
227
|
if (!hasWindow()) return;
|
|
194
228
|
try {
|
|
195
229
|
if (store === "cookie") {
|
|
196
|
-
|
|
197
|
-
|
|
230
|
+
expireCookie(key, null);
|
|
231
|
+
const domain = resolveCookieDomain();
|
|
232
|
+
if (domain) expireCookie(key, domain);
|
|
198
233
|
} else {
|
|
199
234
|
nativeStorage(store)?.removeItem(key);
|
|
200
235
|
}
|
|
@@ -243,10 +278,10 @@ function createStorage(owner, options = {}) {
|
|
|
243
278
|
const target = resolveStore(key, store);
|
|
244
279
|
return rawGet(target, key);
|
|
245
280
|
},
|
|
246
|
-
write(key, value, store) {
|
|
281
|
+
write(key, value, store, writeOptions) {
|
|
247
282
|
assertOwned(key);
|
|
248
283
|
const target = resolveStore(key, store);
|
|
249
|
-
return rawSet(target, key, value);
|
|
284
|
+
return rawSet(target, key, value, writeOptions?.maxAgeSeconds);
|
|
250
285
|
},
|
|
251
286
|
remove(key, store) {
|
|
252
287
|
assertOwned(key);
|
|
@@ -284,6 +319,10 @@ function createStorage(owner, options = {}) {
|
|
|
284
319
|
for (const name of cookieNames()) if (name.startsWith(prefix)) rawRemove("cookie", name);
|
|
285
320
|
}
|
|
286
321
|
},
|
|
322
|
+
setCookieDomain(domain) {
|
|
323
|
+
cookiePolicy = domain;
|
|
324
|
+
},
|
|
325
|
+
cookieDomain: resolveCookieDomain,
|
|
287
326
|
onChange(key, listener, store = "local") {
|
|
288
327
|
assertValid(key);
|
|
289
328
|
if (!hasWindow()) return () => {
|
|
@@ -310,6 +349,11 @@ var REFRESH_KEY = "cfg.auth.refresh_token";
|
|
|
310
349
|
var API_KEY_KEY = "cfg.auth.api_key";
|
|
311
350
|
var storage = true ? cfgStorage : createStorage2("cfg");
|
|
312
351
|
var isBrowser = typeof window !== "undefined";
|
|
352
|
+
function secondsUntilExp(token) {
|
|
353
|
+
const exp = jwtExpMs(token);
|
|
354
|
+
return exp === null ? void 0 : Math.max(1, Math.floor((exp - Date.now()) / 1e3));
|
|
355
|
+
}
|
|
356
|
+
__name(secondsUntilExp, "secondsUntilExp");
|
|
313
357
|
var STORE_OF = {
|
|
314
358
|
localStorage: "local",
|
|
315
359
|
sessionStorage: "session",
|
|
@@ -321,13 +365,31 @@ function backendFor(mode) {
|
|
|
321
365
|
get: /* @__PURE__ */ __name((key) => storage.read(key, store), "get"),
|
|
322
366
|
set(key, value) {
|
|
323
367
|
if (value === null) storage.remove(key, store);
|
|
324
|
-
else storage.write(key, value, store);
|
|
368
|
+
else storage.write(key, value, store, store === "cookie" && key === REFRESH_KEY ? { maxAgeSeconds: secondsUntilExp(value) } : void 0);
|
|
325
369
|
}
|
|
326
370
|
};
|
|
327
371
|
}
|
|
328
372
|
__name(backendFor, "backendFor");
|
|
329
|
-
var _storageMode = "
|
|
373
|
+
var _storageMode = "cookie";
|
|
330
374
|
var _storage = backendFor(_storageMode);
|
|
375
|
+
var _apiKeyStore = backendFor("localStorage");
|
|
376
|
+
function adoptLegacySession() {
|
|
377
|
+
if (!isBrowser || _storageMode !== "cookie") return;
|
|
378
|
+
try {
|
|
379
|
+
if (_storage.get(ACCESS_KEY) !== null || _storage.get(REFRESH_KEY) !== null) return;
|
|
380
|
+
const legacy = backendFor("localStorage");
|
|
381
|
+
const access = legacy.get(ACCESS_KEY);
|
|
382
|
+
const refresh = legacy.get(REFRESH_KEY);
|
|
383
|
+
if (access === null && refresh === null) return;
|
|
384
|
+
if (access !== null) _storage.set(ACCESS_KEY, access);
|
|
385
|
+
if (refresh !== null) _storage.set(REFRESH_KEY, refresh);
|
|
386
|
+
legacy.set(ACCESS_KEY, null);
|
|
387
|
+
legacy.set(REFRESH_KEY, null);
|
|
388
|
+
} catch {
|
|
389
|
+
}
|
|
390
|
+
}
|
|
391
|
+
__name(adoptLegacySession, "adoptLegacySession");
|
|
392
|
+
adoptLegacySession();
|
|
331
393
|
function detectLocale() {
|
|
332
394
|
try {
|
|
333
395
|
if (typeof document === "undefined") return null;
|
|
@@ -472,6 +534,14 @@ function ensureStorageSync() {
|
|
|
472
534
|
}
|
|
473
535
|
});
|
|
474
536
|
window.addEventListener(SESSION_SYNC_EVENT, () => notifySessionChanged());
|
|
537
|
+
window.addEventListener("focus", () => notifySessionChanged());
|
|
538
|
+
document.addEventListener("visibilitychange", () => {
|
|
539
|
+
if (document.visibilityState === "visible") notifySessionChanged();
|
|
540
|
+
});
|
|
541
|
+
try {
|
|
542
|
+
window.cookieStore?.addEventListener("change", () => notifySessionChanged());
|
|
543
|
+
} catch {
|
|
544
|
+
}
|
|
475
545
|
}
|
|
476
546
|
__name(ensureStorageSync, "ensureStorageSync");
|
|
477
547
|
var SESSION_EXPIRED_REGISTRY = `cfg-auth:expired-handlers:${ACCESS_KEY}`;
|
|
@@ -505,6 +575,17 @@ var auth = {
|
|
|
505
575
|
_storage = backendFor(mode);
|
|
506
576
|
notifySessionChanged();
|
|
507
577
|
},
|
|
578
|
+
// ── Shared cookie domain ──────────────────────────────────────────
|
|
579
|
+
/** `'auto'` (default): the registrable domain of the page. A domain forces it; `null` keeps
|
|
580
|
+
* cookies host-only (no sign-in sharing between subdomains). Call before sign-in. */
|
|
581
|
+
setCookieDomain(domain) {
|
|
582
|
+
storage.setCookieDomain(domain === null ? false : domain);
|
|
583
|
+
notifySessionChanged();
|
|
584
|
+
},
|
|
585
|
+
/** The `Domain` the session cookie is written with; `null` = host-only. */
|
|
586
|
+
getCookieDomain() {
|
|
587
|
+
return storage.cookieDomain();
|
|
588
|
+
},
|
|
508
589
|
// ── Bearer token ──────────────────────────────────────────────────
|
|
509
590
|
getToken() {
|
|
510
591
|
return _storage.get(ACCESS_KEY);
|
|
@@ -591,18 +672,18 @@ var auth = {
|
|
|
591
672
|
},
|
|
592
673
|
// ── API key ───────────────────────────────────────────────────────
|
|
593
674
|
getApiKey() {
|
|
594
|
-
return _apiKeyOverride ??
|
|
675
|
+
return _apiKeyOverride ?? _apiKeyStore.get(API_KEY_KEY) ?? defaultApiKey();
|
|
595
676
|
},
|
|
596
677
|
setApiKey(key) {
|
|
597
678
|
_apiKeyOverride = key;
|
|
598
679
|
},
|
|
599
680
|
setApiKeyPersist(key) {
|
|
600
681
|
_apiKeyOverride = key;
|
|
601
|
-
|
|
682
|
+
_apiKeyStore.set(API_KEY_KEY, key);
|
|
602
683
|
},
|
|
603
684
|
clearApiKey() {
|
|
604
685
|
_apiKeyOverride = null;
|
|
605
|
-
|
|
686
|
+
_apiKeyStore.set(API_KEY_KEY, null);
|
|
606
687
|
},
|
|
607
688
|
// ── Locale ────────────────────────────────────────────────────────
|
|
608
689
|
getLocale() {
|