@unhingged/vizu-core 0.1.0 → 0.1.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.
- package/dist/auto.cjs +62 -4
- package/dist/auto.cjs.map +1 -1
- package/dist/auto.js +62 -4
- package/dist/auto.js.map +1 -1
- package/dist/index.cjs +62 -4
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +29 -0
- package/dist/index.d.ts +29 -0
- package/dist/index.js +62 -4
- package/dist/index.js.map +1 -1
- package/dist/vizu.min.js +11 -11
- package/dist/vizu.min.js.map +1 -1
- package/package.json +1 -1
package/dist/auto.cjs
CHANGED
|
@@ -1714,10 +1714,28 @@ var CloudStorageAdapter = class {
|
|
|
1714
1714
|
this.cachedToken = null;
|
|
1715
1715
|
/** Single-flight: at most one popup at a time. Subsequent requests await this. */
|
|
1716
1716
|
this.pendingAuth = null;
|
|
1717
|
+
/** Whether we've already fired onAuthChanged for the current token. */
|
|
1718
|
+
this.lastNotifiedTokenId = null;
|
|
1717
1719
|
this.workspace = opts.workspace;
|
|
1718
1720
|
this.apiUrl = (opts.apiUrl ?? DEFAULT_API_URL).replace(/\/$/, "");
|
|
1719
1721
|
this.autoSignIn = opts.autoSignIn !== false;
|
|
1722
|
+
this.onAuthChanged = opts.onAuthChanged;
|
|
1720
1723
|
this.cachedToken = this.readStoredToken();
|
|
1724
|
+
if (this.cachedToken && !this.isExpired(this.cachedToken)) {
|
|
1725
|
+
this.fireAuthChanged(this.cachedToken);
|
|
1726
|
+
}
|
|
1727
|
+
}
|
|
1728
|
+
/**
|
|
1729
|
+
* Open the sign-in popup right now (or no-op if a valid token is
|
|
1730
|
+
* cached). Vizu calls this on enable() so the user signs in BEFORE
|
|
1731
|
+
* trying to leave a comment — no surprise modal mid-comment.
|
|
1732
|
+
*
|
|
1733
|
+
* Throws auth_canceled if the user closes the popup. Caller can
|
|
1734
|
+
* decide whether to disable the surface or leave it in a read-only
|
|
1735
|
+
* state.
|
|
1736
|
+
*/
|
|
1737
|
+
async preflightAuth() {
|
|
1738
|
+
await this.resolveToken();
|
|
1721
1739
|
}
|
|
1722
1740
|
/* ─── StorageAdapter v2 ───────────────────────────────────────────── */
|
|
1723
1741
|
async load(_namespace) {
|
|
@@ -1906,6 +1924,7 @@ var CloudStorageAdapter = class {
|
|
|
1906
1924
|
const fresh = this.readStoredToken();
|
|
1907
1925
|
if (fresh) {
|
|
1908
1926
|
this.cachedToken = fresh;
|
|
1927
|
+
this.fireAuthChanged(fresh);
|
|
1909
1928
|
return fresh;
|
|
1910
1929
|
}
|
|
1911
1930
|
if (!this.autoSignIn) {
|
|
@@ -1914,6 +1933,7 @@ var CloudStorageAdapter = class {
|
|
|
1914
1933
|
if (!this.pendingAuth) {
|
|
1915
1934
|
this.pendingAuth = this.openSignInPopup().then((t) => {
|
|
1916
1935
|
this.writeStoredToken(t);
|
|
1936
|
+
this.fireAuthChanged(t);
|
|
1917
1937
|
return t;
|
|
1918
1938
|
}).finally(() => {
|
|
1919
1939
|
this.pendingAuth = null;
|
|
@@ -1921,6 +1941,22 @@ var CloudStorageAdapter = class {
|
|
|
1921
1941
|
}
|
|
1922
1942
|
return this.pendingAuth;
|
|
1923
1943
|
}
|
|
1944
|
+
/**
|
|
1945
|
+
* Notify the host that the authenticated identity changed. De-duped
|
|
1946
|
+
* via the token string so multiple resolveToken() hits with the same
|
|
1947
|
+
* cached token don't re-call setUser on every fetch.
|
|
1948
|
+
*/
|
|
1949
|
+
fireAuthChanged(token) {
|
|
1950
|
+
if (this.lastNotifiedTokenId === token.token) return;
|
|
1951
|
+
this.lastNotifiedTokenId = token.token;
|
|
1952
|
+
try {
|
|
1953
|
+
this.onAuthChanged?.({ userId: token.userId, user: token.user });
|
|
1954
|
+
} catch (err) {
|
|
1955
|
+
if (typeof console !== "undefined") {
|
|
1956
|
+
console.warn("[vizu/cloud] onAuthChanged callback threw", err);
|
|
1957
|
+
}
|
|
1958
|
+
}
|
|
1959
|
+
}
|
|
1924
1960
|
openSignInPopup() {
|
|
1925
1961
|
return new Promise((resolve, reject) => {
|
|
1926
1962
|
if (typeof window === "undefined") {
|
|
@@ -1953,7 +1989,13 @@ var CloudStorageAdapter = class {
|
|
|
1953
1989
|
if (typeof data.token !== "string" || typeof data.expiresAt !== "string" || typeof data.userId !== "string") return;
|
|
1954
1990
|
resolved = true;
|
|
1955
1991
|
cleanup();
|
|
1956
|
-
|
|
1992
|
+
const userPayload = data.user;
|
|
1993
|
+
const user = userPayload && typeof userPayload.name === "string" ? {
|
|
1994
|
+
id: typeof userPayload.id === "string" ? userPayload.id : data.userId,
|
|
1995
|
+
name: userPayload.name,
|
|
1996
|
+
avatarUrl: typeof userPayload.avatarUrl === "string" ? userPayload.avatarUrl : void 0
|
|
1997
|
+
} : null;
|
|
1998
|
+
resolve({ token: data.token, expiresAt: data.expiresAt, userId: data.userId, user });
|
|
1957
1999
|
};
|
|
1958
2000
|
const onPoll = window.setInterval(() => {
|
|
1959
2001
|
if (popup.closed) {
|
|
@@ -4054,7 +4096,7 @@ var DEFAULTS = {
|
|
|
4054
4096
|
namespace: "default",
|
|
4055
4097
|
accent: "#FF6647"
|
|
4056
4098
|
};
|
|
4057
|
-
function resolveStorage(storage, cloud, defaultMode) {
|
|
4099
|
+
function resolveStorage(storage, cloud, defaultMode, onAuthChanged) {
|
|
4058
4100
|
if (cloud) {
|
|
4059
4101
|
if (storage && typeof console !== "undefined") {
|
|
4060
4102
|
console.warn("[vizu] Both `cloud` and `storage` set; `cloud` wins. Drop `storage` to silence this.");
|
|
@@ -4062,7 +4104,8 @@ function resolveStorage(storage, cloud, defaultMode) {
|
|
|
4062
4104
|
return new CloudStorageAdapter({
|
|
4063
4105
|
workspace: cloud.workspace,
|
|
4064
4106
|
apiUrl: cloud.apiUrl,
|
|
4065
|
-
autoSignIn: cloud.autoSignIn
|
|
4107
|
+
autoSignIn: cloud.autoSignIn,
|
|
4108
|
+
onAuthChanged
|
|
4066
4109
|
});
|
|
4067
4110
|
}
|
|
4068
4111
|
if (!storage) return defaultMode === "local" ? new LocalStorageAdapter() : new InMemoryStorageAdapter();
|
|
@@ -4168,7 +4211,14 @@ var Vizu = class {
|
|
|
4168
4211
|
this.opts.namespace = options.namespace ?? DEFAULTS.namespace;
|
|
4169
4212
|
this.opts.accent = options.accent ?? DEFAULTS.accent;
|
|
4170
4213
|
this.parsedShortcut = parseShortcut(this.opts.shortcut);
|
|
4171
|
-
this.storage = resolveStorage(
|
|
4214
|
+
this.storage = resolveStorage(
|
|
4215
|
+
options.storage,
|
|
4216
|
+
options.cloud,
|
|
4217
|
+
_defaultStorage,
|
|
4218
|
+
(info) => {
|
|
4219
|
+
if (info.user) this.setUser(info.user);
|
|
4220
|
+
}
|
|
4221
|
+
);
|
|
4172
4222
|
this.user = options.user ?? null;
|
|
4173
4223
|
if (options.actions) this.actions = [...options.actions];
|
|
4174
4224
|
if (options.onCommentAdded) this.bus.on("comment:added", (p) => options.onCommentAdded(p.comment));
|
|
@@ -4214,6 +4264,14 @@ var Vizu = class {
|
|
|
4214
4264
|
this.enabled = true;
|
|
4215
4265
|
this.bus.emit("enabled", {});
|
|
4216
4266
|
this.deferred(() => this.mount());
|
|
4267
|
+
if (this.storage instanceof CloudStorageAdapter) {
|
|
4268
|
+
void this.storage.preflightAuth().catch((err) => {
|
|
4269
|
+
if (err?.code === "auth_canceled" || err?.code === "popup_blocked") return;
|
|
4270
|
+
if (typeof console !== "undefined") {
|
|
4271
|
+
console.warn("[vizu] preflight auth failed:", err);
|
|
4272
|
+
}
|
|
4273
|
+
});
|
|
4274
|
+
}
|
|
4217
4275
|
}
|
|
4218
4276
|
disable() {
|
|
4219
4277
|
if (!this.enabled) return;
|