selfstore 1.8.33 → 1.8.35

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 (52) hide show
  1. package/dist/advanced.d.ts +9 -9
  2. package/dist/advanced.js +4 -4
  3. package/dist/backups.d.ts +4 -4
  4. package/dist/backups.js +1 -1
  5. package/dist/{cache-BEv-Har2.d.ts → cache-C1edLncd.d.ts} +3 -3
  6. package/dist/{chunk-A2RRJLIF.js → chunk-3P2W3XQD.js} +36 -23
  7. package/dist/chunk-3P2W3XQD.js.map +1 -0
  8. package/dist/chunk-DJ6YPMBK.js +10 -0
  9. package/dist/chunk-DJ6YPMBK.js.map +1 -0
  10. package/dist/{chunk-7U5XMKVP.js → chunk-E4S77JSN.js} +34 -6
  11. package/dist/chunk-E4S77JSN.js.map +1 -0
  12. package/dist/{chunk-AFBPJ7KA.js → chunk-SHX36MIE.js} +63 -30
  13. package/dist/chunk-SHX36MIE.js.map +1 -0
  14. package/dist/{chunk-JDDWWQEB.js → chunk-TNYL6FNW.js} +6 -6
  15. package/dist/{chunk-JDDWWQEB.js.map → chunk-TNYL6FNW.js.map} +1 -1
  16. package/dist/{chunk-CI5JYSWE.js → chunk-VRWAV3GI.js} +4 -4
  17. package/dist/{chunk-CI5JYSWE.js.map → chunk-VRWAV3GI.js.map} +1 -1
  18. package/dist/{chunk-Q3NO477P.js → chunk-XAONTUEC.js} +3 -3
  19. package/dist/{chunk-Q3NO477P.js.map → chunk-XAONTUEC.js.map} +1 -1
  20. package/dist/{connect-CDazV36v.d.ts → connect-D7Yzdi9N.d.ts} +4 -4
  21. package/dist/{drive-CwlKlowN.d.ts → drive-3K6pBAmG.d.ts} +2 -2
  22. package/dist/flows.d.ts +4 -4
  23. package/dist/flows.js +3 -3
  24. package/dist/groups.d.ts +2 -2
  25. package/dist/index.d.ts +9 -9
  26. package/dist/index.js +23 -13
  27. package/dist/index.js.map +1 -1
  28. package/dist/{local-DytMg5GC.d.ts → local-Cr5cCaQ2.d.ts} +2 -2
  29. package/dist/{local-S3WUZSDX.js → local-D72LJOKX.js} +4 -4
  30. package/dist/{local-S3WUZSDX.js.map → local-D72LJOKX.js.map} +1 -1
  31. package/dist/{manager-CnlIs-hY.d.ts → manager-Bl16FR-e.d.ts} +2 -2
  32. package/dist/{manager-drive-KSZIHMLF.js → manager-drive-TEYNJVUU.js} +3 -3
  33. package/dist/{manager-drive-KSZIHMLF.js.map → manager-drive-TEYNJVUU.js.map} +1 -1
  34. package/dist/proof.d.ts +6 -6
  35. package/dist/proof.js +1 -1
  36. package/dist/{s3-Bexn9kzT.d.ts → s3-C2PrgMpD.d.ts} +2 -2
  37. package/dist/{s3-ORDHS7G3.js → s3-KZPMSI4J.js} +3 -3
  38. package/dist/s3-KZPMSI4J.js.map +1 -0
  39. package/dist/{simple-cLzoTGhN.d.ts → simple-Dp1tbrwo.d.ts} +6 -6
  40. package/dist/{store-DSPbCCtM.d.ts → store-B4Zo0f6G.d.ts} +11 -3
  41. package/dist/sync.js +1 -1
  42. package/dist/{webdav-PXKELPA4.js → webdav-5YKO47EE.js} +3 -3
  43. package/dist/{webdav-PXKELPA4.js.map → webdav-5YKO47EE.js.map} +1 -1
  44. package/dist/widgets.d.ts +5 -5
  45. package/dist/widgets.js +4 -4
  46. package/package.json +1 -1
  47. package/dist/chunk-7U5XMKVP.js.map +0 -1
  48. package/dist/chunk-A2RRJLIF.js.map +0 -1
  49. package/dist/chunk-AFBPJ7KA.js.map +0 -1
  50. package/dist/chunk-SJ3PKQPR.js +0 -10
  51. package/dist/chunk-SJ3PKQPR.js.map +0 -1
  52. package/dist/s3-ORDHS7G3.js.map +0 -1
@@ -1,5 +1,5 @@
1
- import { createNode, createMeta, gcTombstones, stamp, merge, unsyncableCounts, idPathFor, detectConflicts, changes } from './chunk-A2RRJLIF.js';
2
- import { inspect, checkPasswordPolicy, writeBox, BACKUP_MIME, readBoxWithSync, asBytes } from './chunk-7U5XMKVP.js';
1
+ import { createNode, createMeta, gcTombstones, stamp, merge, unsyncableCounts, idPathFor, detectConflicts, changes } from './chunk-3P2W3XQD.js';
2
+ import { inspect, checkPasswordPolicy, writeBox, BACKUP_MIME, readBoxWithSync, asBytes } from './chunk-E4S77JSN.js';
3
3
  import { seal, isEnvelope, unseal, newDeviceKey } from './chunk-QBCU7OOP.js';
4
4
  import { openManifest, GROUP_KEYING } from './chunk-F4ZZEJ5H.js';
5
5
  import { mintSlot, MAX_KEY_SLOTS, mintExternalSlot, openSlot } from './chunk-H2T4S3KM.js';
@@ -253,8 +253,12 @@ function createLocalStore(opts) {
253
253
  subs.forEach((f) => f());
254
254
  };
255
255
  const locked = () => durableKind() && encrypted && !pass && !envelope && !group;
256
- const ownGroupRead = () => group ? { identity: group.identity, authors: [group.identity.sigPub] } : void 0;
257
- const peerGroupRead = () => group ? { identity: group.identity, authors: group.manifest.members.map((m) => m.sig) } : void 0;
256
+ const ownGroupRead = () => group ? { identity: group.identity, authors: [group.identity.sigPub], group: group.manifest.group } : void 0;
257
+ const peerGroupRead = () => group ? {
258
+ identity: group.identity,
259
+ authors: group.manifest.members.map((m) => m.sig),
260
+ group: group.manifest.group
261
+ } : void 0;
258
262
  const groupSeqKey = (id) => `groupSeq:${id}`;
259
263
  async function persistGroupSeq(id, seq) {
260
264
  await kv.set(groupSeqKey(id), seq);
@@ -286,22 +290,25 @@ function createLocalStore(opts) {
286
290
  if (p === null) envelope = null;
287
291
  armIdleLock();
288
292
  }
289
- const toCachedFiles = (snap) => snap.files.map((f) => ({
290
- id: f.id,
291
- name: f.name,
292
- mime: f.mime,
293
- blob: new Blob([f.bytes], { type: f.mime })
294
- }));
293
+ const blobOf = /* @__PURE__ */ new WeakMap();
294
+ const blobFor = (f) => {
295
+ let blob = blobOf.get(f.bytes);
296
+ if (!blob) {
297
+ blob = new Blob([f.bytes], { type: f.mime });
298
+ blobOf.set(f.bytes, blob);
299
+ }
300
+ return blob;
301
+ };
302
+ const toCachedFiles = (snap) => snap.files.map((f) => ({ id: f.id, name: f.name, mime: f.mime, blob: blobFor(f) }));
295
303
  async function cachedToSnapshot(local) {
296
304
  return {
297
305
  collections: local.collections,
298
306
  files: await Promise.all(
299
- local.files.map(async (f) => ({
300
- id: f.id,
301
- name: f.name,
302
- mime: f.mime,
303
- bytes: new Uint8Array(await f.blob.arrayBuffer())
304
- }))
307
+ local.files.map(async (f) => {
308
+ const bytes = new Uint8Array(await f.blob.arrayBuffer());
309
+ blobOf.set(bytes, f.blob);
310
+ return { id: f.id, name: f.name, mime: f.mime, bytes };
311
+ })
305
312
  )
306
313
  };
307
314
  }
@@ -349,7 +356,8 @@ function createLocalStore(opts) {
349
356
  recipients: [
350
357
  .../* @__PURE__ */ new Set([...group.manifest.members.map((m) => m.enc), group.identity.encPub])
351
358
  ],
352
- sign: { pub: group.identity.sigPub, priv: group.identity.sigPriv }
359
+ sign: { pub: group.identity.sigPub, priv: group.identity.sigPriv },
360
+ id: group.manifest.group
353
361
  } : void 0;
354
362
  const bytes = await writeBox(
355
363
  { collections: snap.collections, files: snap.files },
@@ -1894,6 +1902,24 @@ function memoryCache() {
1894
1902
  var COLLECTIONS_KEY = "__collections";
1895
1903
  var DEVICE_KEY = "__deviceKey";
1896
1904
  var CACHE_KDF = "__cacheKdf";
1905
+ async function sealFile(k, meta, bytes) {
1906
+ const sealedMeta = await seal(k, new TextEncoder().encode(JSON.stringify(meta)));
1907
+ return { meta: sealedMeta, ...await seal(k, bytes) };
1908
+ }
1909
+ async function openFileMeta(k, v) {
1910
+ if (!("meta" in v)) return { name: v.name, mime: v.mime };
1911
+ if (!isEnvelope(v.meta)) {
1912
+ throw new SelfstoreError("BAD_FORMAT", "Unrecognized cache record (not a sealed envelope).");
1913
+ }
1914
+ const meta = JSON.parse(new TextDecoder().decode(await unseal(k, v.meta)));
1915
+ if (typeof meta.name !== "string" || typeof meta.mime !== "string") {
1916
+ throw new SelfstoreError(
1917
+ "BAD_FORMAT",
1918
+ "Unrecognized cache record (file name or type missing)."
1919
+ );
1920
+ }
1921
+ return { name: meta.name, mime: meta.mime };
1922
+ }
1897
1923
  function indexedDbCache(name, opts) {
1898
1924
  let _db = null;
1899
1925
  const db = () => _db ??= openDB(name, 1, {
@@ -1930,8 +1956,10 @@ function indexedDbCache(name, opts) {
1930
1956
  if (!isEnvelope(v)) {
1931
1957
  throw new SelfstoreError("BAD_FORMAT", "Unrecognized cache record (not a sealed envelope).");
1932
1958
  }
1933
- const bytes = await unseal(await key(), v);
1934
- return { name: v.name, mime: v.mime, blob: new Blob([bytes], { type: v.mime }) };
1959
+ const k = await key();
1960
+ const { name: name2, mime } = await openFileMeta(k, v);
1961
+ const bytes = await unseal(k, v);
1962
+ return { name: name2, mime, blob: new Blob([bytes], { type: mime }) };
1935
1963
  }
1936
1964
  const kv = {
1937
1965
  async get(key2) {
@@ -1944,6 +1972,8 @@ function indexedDbCache(name, opts) {
1944
1972
  await (await db()).delete("kv", `m:${key2}`);
1945
1973
  }
1946
1974
  };
1975
+ const written = /* @__PURE__ */ new Map();
1976
+ const changed = (f, have) => !have.has(f.id) || written.has(f.id) && written.get(f.id) !== f.blob;
1947
1977
  const base = {
1948
1978
  kv,
1949
1979
  async load() {
@@ -1962,7 +1992,10 @@ function indexedDbCache(name, opts) {
1962
1992
  const files = [];
1963
1993
  for (const fileKey of await d.getAllKeys("files")) {
1964
1994
  const v = await d.get("files", fileKey);
1965
- if (v) files.push({ id: String(fileKey), ...await decodeFile(v) });
1995
+ if (!v) continue;
1996
+ const file = { id: String(fileKey), ...await decodeFile(v) };
1997
+ written.set(file.id, file.blob);
1998
+ files.push(file);
1966
1999
  }
1967
2000
  return { collections, files };
1968
2001
  },
@@ -1977,20 +2010,23 @@ function indexedDbCache(name, opts) {
1977
2010
  const want = new Set(files.map((f) => f.id));
1978
2011
  const k = await key();
1979
2012
  const fresh = await Promise.all(
1980
- files.filter((f) => !have.has(f.id)).map(async (f) => {
1981
- const env = await seal(k, new Uint8Array(await f.blob.arrayBuffer()));
1982
- return { id: f.id, rec: { name: f.name, mime: f.mime, ...env } };
2013
+ files.filter((f) => changed(f, have)).map(async (f) => {
2014
+ const bytes = new Uint8Array(await f.blob.arrayBuffer());
2015
+ return { id: f.id, rec: await sealFile(k, { name: f.name, mime: f.mime }, bytes) };
1983
2016
  })
1984
2017
  );
1985
2018
  const tx = d.transaction("files", "readwrite");
1986
2019
  for (const { id, rec } of fresh) tx.store.put(rec, id);
1987
2020
  for (const id of have) if (!want.has(id)) tx.store.delete(id);
1988
2021
  await tx.done;
2022
+ written.clear();
2023
+ for (const f of files) written.set(f.id, f.blob);
1989
2024
  },
1990
2025
  async clear() {
1991
2026
  const d = await db();
1992
2027
  await d.clear("kv");
1993
2028
  await d.clear("files");
2029
+ written.clear();
1994
2030
  _key = null;
1995
2031
  sealKey = null;
1996
2032
  },
@@ -2031,11 +2067,8 @@ function indexedDbCache(name, opts) {
2031
2067
  for (const fileKey of await d.getAllKeys("files")) {
2032
2068
  const v = await d.get("files", fileKey);
2033
2069
  if (!v) continue;
2034
- const bytes = await unseal(previous, v);
2035
- files.push({
2036
- id: fileKey,
2037
- rec: { name: v.name, mime: v.mime, ...await seal(next, bytes) }
2038
- });
2070
+ const meta = await openFileMeta(previous, v);
2071
+ files.push({ id: fileKey, rec: await sealFile(next, meta, await unseal(previous, v)) });
2039
2072
  }
2040
2073
  const tx = d.transaction(["kv", "files"], "readwrite");
2041
2074
  const store = tx.objectStore("kv");
@@ -2203,5 +2236,5 @@ function gisDriveAuth(opts) {
2203
2236
  }
2204
2237
 
2205
2238
  export { RESERVED_STORE_MODES, createLocalStore, deriveStatus, gisDriveAuth, indexedDbCache, isLockableCache, isReservedStoreMode, memoryCache, preloadGoogleIdentity };
2206
- //# sourceMappingURL=chunk-AFBPJ7KA.js.map
2207
- //# sourceMappingURL=chunk-AFBPJ7KA.js.map
2239
+ //# sourceMappingURL=chunk-SHX36MIE.js.map
2240
+ //# sourceMappingURL=chunk-SHX36MIE.js.map