opfs-worker 0.2.0 → 0.2.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/index.cjs CHANGED
@@ -1,19 +1,19 @@
1
- "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const i=require("comlink"),a=`/**
1
+ "use strict";Object.defineProperty(exports,Symbol.toStringTag,{value:"Module"});const a=require("comlink"),n=require("./helpers-hEpet7x7.cjs"),o=`/**
2
2
  * @license
3
3
  * Copyright 2019 Google LLC
4
4
  * SPDX-License-Identifier: Apache-2.0
5
5
  */
6
- const k = Symbol("Comlink.proxy"), U = Symbol("Comlink.endpoint"), z = Symbol("Comlink.releaseProxy"), T = Symbol("Comlink.finalizer"), E = Symbol("Comlink.thrown"), C = (e) => typeof e == "object" && e !== null || typeof e == "function", _ = {
7
- canHandle: (e) => C(e) && e[k],
6
+ const H = Symbol("Comlink.proxy"), R = Symbol("Comlink.endpoint"), B = Symbol("Comlink.releaseProxy"), T = Symbol("Comlink.finalizer"), p = Symbol("Comlink.thrown"), $ = (e) => typeof e == "object" && e !== null || typeof e == "function", W = {
7
+ canHandle: (e) => $(e) && e[H],
8
8
  serialize(e) {
9
9
  const { port1: t, port2: r } = new MessageChannel();
10
- return x(e, t), [r, [r]];
10
+ return O(e, t), [r, [r]];
11
11
  },
12
12
  deserialize(e) {
13
- return e.start(), j(e);
13
+ return e.start(), Y(e);
14
14
  }
15
- }, R = {
16
- canHandle: (e) => C(e) && E in e,
15
+ }, j = {
16
+ canHandle: (e) => $(e) && p in e,
17
17
  serialize({ value: e }) {
18
18
  let t;
19
19
  return e instanceof Error ? t = {
@@ -28,187 +28,187 @@ const k = Symbol("Comlink.proxy"), U = Symbol("Comlink.endpoint"), z = Symbol("C
28
28
  deserialize(e) {
29
29
  throw e.isError ? Object.assign(new Error(e.value.message), e.value) : e.value;
30
30
  }
31
- }, M = /* @__PURE__ */ new Map([
32
- ["proxy", _],
33
- ["throw", R]
31
+ }, U = /* @__PURE__ */ new Map([
32
+ ["proxy", W],
33
+ ["throw", j]
34
34
  ]);
35
- function W(e, t) {
35
+ function V(e, t) {
36
36
  for (const r of e)
37
37
  if (t === r || r === "*" || r instanceof RegExp && r.test(t))
38
38
  return !0;
39
39
  return !1;
40
40
  }
41
- function x(e, t = globalThis, r = ["*"]) {
41
+ function O(e, t = globalThis, r = ["*"]) {
42
42
  t.addEventListener("message", function a(n) {
43
43
  if (!n || !n.data)
44
44
  return;
45
- if (!W(r, n.origin)) {
45
+ if (!V(r, n.origin)) {
46
46
  console.warn(\`Invalid origin '\${n.origin}' for comlink proxy\`);
47
47
  return;
48
48
  }
49
- const { id: s, type: i, path: o } = Object.assign({ path: [] }, n.data), c = (n.data.argumentList || []).map(d);
50
- let f;
49
+ const { id: s, type: o, path: i } = Object.assign({ path: [] }, n.data), l = (n.data.argumentList || []).map(d);
50
+ let u;
51
51
  try {
52
- const u = o.slice(0, -1).reduce((h, g) => h[g], e), w = o.reduce((h, g) => h[g], e);
53
- switch (i) {
52
+ const f = i.slice(0, -1).reduce((h, g) => h[g], e), w = i.reduce((h, g) => h[g], e);
53
+ switch (o) {
54
54
  case "GET":
55
- f = w;
55
+ u = w;
56
56
  break;
57
57
  case "SET":
58
- u[o.slice(-1)[0]] = d(n.data.value), f = !0;
58
+ f[i.slice(-1)[0]] = d(n.data.value), u = !0;
59
59
  break;
60
60
  case "APPLY":
61
- f = w.apply(u, c);
61
+ u = w.apply(f, l);
62
62
  break;
63
63
  case "CONSTRUCT":
64
64
  {
65
- const h = new w(...c);
66
- f = q(h);
65
+ const h = new w(...l);
66
+ u = Q(h);
67
67
  }
68
68
  break;
69
69
  case "ENDPOINT":
70
70
  {
71
71
  const { port1: h, port2: g } = new MessageChannel();
72
- x(e, g), f = X(h, [h]);
72
+ O(e, g), u = J(h, [h]);
73
73
  }
74
74
  break;
75
75
  case "RELEASE":
76
- f = void 0;
76
+ u = void 0;
77
77
  break;
78
78
  default:
79
79
  return;
80
80
  }
81
- } catch (u) {
82
- f = { value: u, [E]: 0 };
81
+ } catch (f) {
82
+ u = { value: f, [p]: 0 };
83
83
  }
84
- Promise.resolve(f).catch((u) => ({ value: u, [E]: 0 })).then((u) => {
85
- const [w, h] = A(u);
86
- t.postMessage(Object.assign(Object.assign({}, w), { id: s }), h), i === "RELEASE" && (t.removeEventListener("message", a), v(t), T in e && typeof e[T] == "function" && e[T]());
87
- }).catch((u) => {
84
+ Promise.resolve(u).catch((f) => ({ value: f, [p]: 0 })).then((f) => {
85
+ const [w, h] = A(f);
86
+ t.postMessage(Object.assign(Object.assign({}, w), { id: s }), h), o === "RELEASE" && (t.removeEventListener("message", a), L(t), T in e && typeof e[T] == "function" && e[T]());
87
+ }).catch((f) => {
88
88
  const [w, h] = A({
89
89
  value: new TypeError("Unserializable return value"),
90
- [E]: 0
90
+ [p]: 0
91
91
  });
92
92
  t.postMessage(Object.assign(Object.assign({}, w), { id: s }), h);
93
93
  });
94
94
  }), t.start && t.start();
95
95
  }
96
- function B(e) {
96
+ function G(e) {
97
97
  return e.constructor.name === "MessagePort";
98
98
  }
99
- function v(e) {
100
- B(e) && e.close();
99
+ function L(e) {
100
+ G(e) && e.close();
101
101
  }
102
- function j(e, t) {
102
+ function Y(e, t) {
103
103
  const r = /* @__PURE__ */ new Map();
104
104
  return e.addEventListener("message", function(n) {
105
105
  const { data: s } = n;
106
106
  if (!s || !s.id)
107
107
  return;
108
- const i = r.get(s.id);
109
- if (i)
108
+ const o = r.get(s.id);
109
+ if (o)
110
110
  try {
111
- i(s);
111
+ o(s);
112
112
  } finally {
113
113
  r.delete(s.id);
114
114
  }
115
- }), I(e, r, [], t);
115
+ }), x(e, r, [], t);
116
116
  }
117
- function p(e) {
117
+ function E(e) {
118
118
  if (e)
119
119
  throw new Error("Proxy has been released and is not useable");
120
120
  }
121
- function $(e) {
122
- return m(e, /* @__PURE__ */ new Map(), {
121
+ function z(e) {
122
+ return y(e, /* @__PURE__ */ new Map(), {
123
123
  type: "RELEASE"
124
124
  }).then(() => {
125
- v(e);
125
+ L(e);
126
126
  });
127
127
  }
128
128
  const F = /* @__PURE__ */ new WeakMap(), S = "FinalizationRegistry" in globalThis && new FinalizationRegistry((e) => {
129
129
  const t = (F.get(e) || 0) - 1;
130
- F.set(e, t), t === 0 && $(e);
130
+ F.set(e, t), t === 0 && z(e);
131
131
  });
132
- function V(e, t) {
132
+ function X(e, t) {
133
133
  const r = (F.get(t) || 0) + 1;
134
134
  F.set(t, r), S && S.register(e, t, e);
135
135
  }
136
- function G(e) {
136
+ function q(e) {
137
137
  S && S.unregister(e);
138
138
  }
139
- function I(e, t, r = [], a = function() {
139
+ function x(e, t, r = [], a = function() {
140
140
  }) {
141
141
  let n = !1;
142
142
  const s = new Proxy(a, {
143
- get(i, o) {
144
- if (p(n), o === z)
143
+ get(o, i) {
144
+ if (E(n), i === B)
145
145
  return () => {
146
- G(s), $(e), t.clear(), n = !0;
146
+ q(s), z(e), t.clear(), n = !0;
147
147
  };
148
- if (o === "then") {
148
+ if (i === "then") {
149
149
  if (r.length === 0)
150
150
  return { then: () => s };
151
- const c = m(e, t, {
151
+ const l = y(e, t, {
152
152
  type: "GET",
153
- path: r.map((f) => f.toString())
153
+ path: r.map((u) => u.toString())
154
154
  }).then(d);
155
- return c.then.bind(c);
155
+ return l.then.bind(l);
156
156
  }
157
- return I(e, t, [...r, o]);
157
+ return x(e, t, [...r, i]);
158
158
  },
159
- set(i, o, c) {
160
- p(n);
161
- const [f, u] = A(c);
162
- return m(e, t, {
159
+ set(o, i, l) {
160
+ E(n);
161
+ const [u, f] = A(l);
162
+ return y(e, t, {
163
163
  type: "SET",
164
- path: [...r, o].map((w) => w.toString()),
165
- value: f
166
- }, u).then(d);
164
+ path: [...r, i].map((w) => w.toString()),
165
+ value: u
166
+ }, f).then(d);
167
167
  },
168
- apply(i, o, c) {
169
- p(n);
170
- const f = r[r.length - 1];
171
- if (f === U)
172
- return m(e, t, {
168
+ apply(o, i, l) {
169
+ E(n);
170
+ const u = r[r.length - 1];
171
+ if (u === R)
172
+ return y(e, t, {
173
173
  type: "ENDPOINT"
174
174
  }).then(d);
175
- if (f === "bind")
176
- return I(e, t, r.slice(0, -1));
177
- const [u, w] = O(c);
178
- return m(e, t, {
175
+ if (u === "bind")
176
+ return x(e, t, r.slice(0, -1));
177
+ const [f, w] = v(l);
178
+ return y(e, t, {
179
179
  type: "APPLY",
180
180
  path: r.map((h) => h.toString()),
181
- argumentList: u
181
+ argumentList: f
182
182
  }, w).then(d);
183
183
  },
184
- construct(i, o) {
185
- p(n);
186
- const [c, f] = O(o);
187
- return m(e, t, {
184
+ construct(o, i) {
185
+ E(n);
186
+ const [l, u] = v(i);
187
+ return y(e, t, {
188
188
  type: "CONSTRUCT",
189
- path: r.map((u) => u.toString()),
190
- argumentList: c
191
- }, f).then(d);
189
+ path: r.map((f) => f.toString()),
190
+ argumentList: l
191
+ }, u).then(d);
192
192
  }
193
193
  });
194
- return V(s, e), s;
194
+ return X(s, e), s;
195
195
  }
196
- function Y(e) {
196
+ function K(e) {
197
197
  return Array.prototype.concat.apply([], e);
198
198
  }
199
- function O(e) {
199
+ function v(e) {
200
200
  const t = e.map(A);
201
- return [t.map((r) => r[0]), Y(t.map((r) => r[1]))];
201
+ return [t.map((r) => r[0]), K(t.map((r) => r[1]))];
202
202
  }
203
- const L = /* @__PURE__ */ new WeakMap();
204
- function X(e, t) {
205
- return L.set(e, t), e;
203
+ const _ = /* @__PURE__ */ new WeakMap();
204
+ function J(e, t) {
205
+ return _.set(e, t), e;
206
206
  }
207
- function q(e) {
208
- return Object.assign(e, { [k]: !0 });
207
+ function Q(e) {
208
+ return Object.assign(e, { [H]: !0 });
209
209
  }
210
210
  function A(e) {
211
- for (const [t, r] of M)
211
+ for (const [t, r] of U)
212
212
  if (r.canHandle(e)) {
213
213
  const [a, n] = r.serialize(e);
214
214
  return [
@@ -225,52 +225,52 @@ function A(e) {
225
225
  type: "RAW",
226
226
  value: e
227
227
  },
228
- L.get(e) || []
228
+ _.get(e) || []
229
229
  ];
230
230
  }
231
231
  function d(e) {
232
232
  switch (e.type) {
233
233
  case "HANDLER":
234
- return M.get(e.name).deserialize(e.value);
234
+ return U.get(e.name).deserialize(e.value);
235
235
  case "RAW":
236
236
  return e.value;
237
237
  }
238
238
  }
239
- function m(e, t, r, a) {
239
+ function y(e, t, r, a) {
240
240
  return new Promise((n) => {
241
- const s = K();
241
+ const s = Z();
242
242
  t.set(s, n), e.start && e.start(), e.postMessage(Object.assign({ id: s }, r), a);
243
243
  });
244
244
  }
245
- function K() {
245
+ function Z() {
246
246
  return new Array(4).fill(0).map(() => Math.floor(Math.random() * Number.MAX_SAFE_INTEGER).toString(16)).join("-");
247
247
  }
248
- class l extends Error {
248
+ class c extends Error {
249
249
  constructor(t, r, a) {
250
250
  super(t), this.code = r, this.path = a, this.name = "OPFSError";
251
251
  }
252
252
  }
253
- class J extends l {
253
+ class ee extends c {
254
254
  constructor() {
255
255
  super("OPFS is not supported in this browser", "OPFS_NOT_SUPPORTED");
256
256
  }
257
257
  }
258
- class D extends l {
258
+ class D extends c {
259
259
  constructor() {
260
260
  super("OPFS is not mounted", "OPFS_NOT_MOUNTED");
261
261
  }
262
262
  }
263
- class P extends l {
263
+ class k extends c {
264
264
  constructor(t, r) {
265
265
  super(t, "INVALID_PATH", r);
266
266
  }
267
267
  }
268
- class b extends l {
268
+ class b extends c {
269
269
  constructor(t) {
270
270
  super(\`File not found: \${t}\`, "FILE_NOT_FOUND", t);
271
271
  }
272
272
  }
273
- function Q(e, t = "utf-8") {
273
+ function te(e, t = "utf-8") {
274
274
  switch (t) {
275
275
  case "utf8":
276
276
  case "utf-8":
@@ -278,24 +278,24 @@ function Q(e, t = "utf-8") {
278
278
  case "utf16le":
279
279
  case "ucs2":
280
280
  case "ucs-2":
281
- return ee(e);
282
- case "ascii":
283
281
  return ne(e);
282
+ case "ascii":
283
+ return ie(e);
284
284
  case "latin1":
285
- return re(e);
285
+ return se(e);
286
286
  case "binary":
287
287
  return Uint8Array.from(e, (r) => r.charCodeAt(0));
288
288
  case "base64":
289
289
  return Uint8Array.from(atob(e), (r) => r.charCodeAt(0));
290
290
  case "hex":
291
291
  if (!/^[\\da-f]+$/i.test(e) || e.length % 2 !== 0)
292
- throw new l("Invalid hex string", "INVALID_HEX_FORMAT");
292
+ throw new c("Invalid hex string", "INVALID_HEX_FORMAT");
293
293
  return Uint8Array.from(e.match(/.{1,2}/g).map((r) => parseInt(r, 16)));
294
294
  default:
295
295
  return console.warn("Encoding not supported, falling back to UTF-8"), new TextEncoder().encode(e);
296
296
  }
297
297
  }
298
- function Z(e, t = "utf-8") {
298
+ function re(e, t = "utf-8") {
299
299
  switch (t) {
300
300
  case "utf8":
301
301
  case "utf-8":
@@ -303,7 +303,7 @@ function Z(e, t = "utf-8") {
303
303
  case "utf16le":
304
304
  case "ucs2":
305
305
  case "ucs-2":
306
- return te(e);
306
+ return ae(e);
307
307
  case "latin1":
308
308
  return String.fromCharCode(...e);
309
309
  case "binary":
@@ -318,7 +318,7 @@ function Z(e, t = "utf-8") {
318
318
  return console.warn("Unsupported encoding, falling back to UTF-8"), new TextDecoder().decode(e);
319
319
  }
320
320
  }
321
- function ee(e) {
321
+ function ne(e) {
322
322
  const t = new Uint8Array(e.length * 2);
323
323
  for (let r = 0; r < e.length; r++) {
324
324
  const a = e.charCodeAt(r);
@@ -326,37 +326,60 @@ function ee(e) {
326
326
  }
327
327
  return t;
328
328
  }
329
- function te(e) {
329
+ function ae(e) {
330
330
  e.length % 2 !== 0 && (console.warn("Invalid UTF-16LE buffer length, truncating last byte"), e = e.slice(0, e.length - 1));
331
331
  const t = new Uint16Array(e.buffer, e.byteOffset, e.byteLength / 2);
332
332
  return String.fromCharCode(...t);
333
333
  }
334
- function re(e) {
334
+ function se(e) {
335
335
  const t = new Uint8Array(e.length);
336
336
  for (let r = 0; r < e.length; r++)
337
337
  t[r] = e.charCodeAt(r) & 255;
338
338
  return t;
339
339
  }
340
- function ne(e) {
340
+ function ie(e) {
341
341
  const t = new Uint8Array(e.length);
342
342
  for (let r = 0; r < e.length; r++)
343
343
  t[r] = e.charCodeAt(r) & 127;
344
344
  return t;
345
345
  }
346
- function ae() {
346
+ function oe() {
347
347
  if (!("storage" in navigator) || !("getDirectory" in navigator.storage))
348
- throw new J();
348
+ throw new ee();
349
349
  }
350
- function y(e) {
350
+ function m(e) {
351
351
  return Array.isArray(e) ? e : e.split("/").filter(Boolean);
352
352
  }
353
353
  function N(e) {
354
354
  return typeof e == "string" ? e ?? "/" : \`/\${e.join("/")}\`;
355
355
  }
356
- function se(e, t = "utf-8") {
357
- return typeof e == "string" ? Q(e, t) : e instanceof Uint8Array ? e : new Uint8Array(e);
356
+ function P(e) {
357
+ const t = m(e);
358
+ return t[t.length - 1] || "";
359
+ }
360
+ function M(e) {
361
+ const t = m(e);
362
+ return t.pop(), N(t);
363
+ }
364
+ function I(e) {
365
+ return !e || e === "/" ? "/" : e.startsWith("/") ? e : \`/\${e}\`;
366
+ }
367
+ function ce(e) {
368
+ const t = m(e), r = [];
369
+ for (const a of t)
370
+ if (!(a === "." || a === ""))
371
+ if (a === "..") {
372
+ if (r.length === 0)
373
+ continue;
374
+ r.pop();
375
+ } else
376
+ r.push(a);
377
+ return N(r);
378
+ }
379
+ function le(e, t = "utf-8") {
380
+ return typeof e == "string" ? te(e, t) : e instanceof Uint8Array ? e : new Uint8Array(e);
358
381
  }
359
- async function ie(e) {
382
+ async function ue(e) {
360
383
  const t = await e.createSyncAccessHandle();
361
384
  try {
362
385
  const r = t.getSize(), a = new Uint8Array(r);
@@ -365,16 +388,16 @@ async function ie(e) {
365
388
  t.close();
366
389
  }
367
390
  }
368
- async function H(e, t, r, a = {}) {
391
+ async function C(e, t, r, a = {}) {
369
392
  let n = null;
370
393
  try {
371
394
  n = await e.createSyncAccessHandle();
372
- const s = se(t, r), i = a.append ? n.getSize() : 0;
373
- n.write(s, { at: i }), a.truncate && !a.append && n.truncate(s.byteLength), n.flush();
395
+ const s = le(t, r), o = a.append ? n.getSize() : 0;
396
+ n.write(s, { at: o }), a.truncate && !a.append && n.truncate(s.byteLength), n.flush();
374
397
  } catch (s) {
375
398
  console.error(s);
376
- const i = a.append ? "append" : "write";
377
- throw new l(\`Failed to \${i} file\`, \`\${i.toUpperCase()}_FAILED\`);
399
+ const o = a.append ? "append" : "write";
400
+ throw new c(\`Failed to \${o} file\`, \`\${o.toUpperCase()}_FAILED\`);
378
401
  } finally {
379
402
  if (n)
380
403
  try {
@@ -383,7 +406,7 @@ async function H(e, t, r, a = {}) {
383
406
  }
384
407
  }
385
408
  }
386
- async function oe(e, t = "SHA-1") {
409
+ async function fe(e, t = "SHA-1") {
387
410
  try {
388
411
  const r = new Uint8Array(e), a = await crypto.subtle.digest(t, r);
389
412
  return Array.from(new Uint8Array(a)).map((s) => s.toString(16).padStart(2, "0")).join("");
@@ -391,7 +414,11 @@ async function oe(e, t = "SHA-1") {
391
414
  throw console.warn(\`Failed to calculate \${t} hash:\`, r), r;
392
415
  }
393
416
  }
394
- class ce {
417
+ async function he(e) {
418
+ const t = await e.arrayBuffer();
419
+ return new Uint8Array(t);
420
+ }
421
+ class we {
395
422
  /** Root directory handle for the file system */
396
423
  root = null;
397
424
  /** Watch event callback */
@@ -404,19 +431,23 @@ class ce {
404
431
  watchInterval = 1e3;
405
432
  /** Flag to avoid concurrent scans */
406
433
  scanning = !1;
434
+ /** Promise to prevent concurrent mount operations */
435
+ mountingPromise = null;
407
436
  /**
408
437
  * Creates a new OPFSFileSystem instance
409
438
  *
439
+ * @param watchCallback - Optional callback for file change events
440
+ * @param watchOptions - Optional configuration for watching
410
441
  * @throws {OPFSError} If OPFS is not supported in the current browser
411
442
  */
412
- constructor() {
413
- ae();
443
+ constructor(t, r) {
444
+ oe(), t && (this.watchCallback = t, r?.watchInterval && (this.watchInterval = r.watchInterval)), this.mount("/");
414
445
  }
415
446
  /**
416
447
  * Initialize the file system within a given directory
417
448
  *
418
449
  * This method sets up the root directory for all subsequent operations.
419
- * It must be called before any other file system operations.
450
+ * If no root is specified, it will use the OPFS root directory.
420
451
  *
421
452
  * @param root - The root path for the file system (default: '/')
422
453
  * @returns Promise that resolves to true if initialization was successful
@@ -425,15 +456,52 @@ class ce {
425
456
  * @example
426
457
  * \`\`\`typescript
427
458
  * const fs = new OPFSFileSystem();
428
- * const success = await fs.init('/my-app');
459
+ *
460
+ * // Use OPFS root (default)
461
+ * await fs.mount();
462
+ *
463
+ * // Use custom directory
464
+ * await fs.mount('/my-app');
429
465
  * \`\`\`
430
466
  */
431
- async mount(t = "/", r, a) {
432
- try {
433
- const n = await navigator.storage.getDirectory();
434
- return this.root = await this.getDirectoryHandle(t, !0, n), r && (this.watchCallback = r, a?.watchInterval && (this.watchInterval = a.watchInterval)), !0;
435
- } catch (n) {
436
- throw console.error(n), new l("Failed to initialize OPFS", "INIT_FAILED");
467
+ async mount(t = "/") {
468
+ return this.mountingPromise && await this.mountingPromise, this.mountingPromise = new Promise(async (r, a) => {
469
+ this.root = null;
470
+ try {
471
+ const n = await navigator.storage.getDirectory();
472
+ t === "/" ? this.root = n : this.root = await this.getDirectoryHandle(t, !0, n), r(!0);
473
+ } catch (n) {
474
+ console.error(n), a(new c("Failed to initialize OPFS", "INIT_FAILED"));
475
+ } finally {
476
+ this.mountingPromise = null;
477
+ }
478
+ }), this.mountingPromise;
479
+ }
480
+ /**
481
+ * Set the watch callback for file change events
482
+ *
483
+ * @param callback - The callback function to invoke when files change
484
+ * @param options - Optional configuration for watching
485
+ */
486
+ setWatchCallback(t, r) {
487
+ this.watchCallback = t, r?.watchInterval && (this.watchInterval = r.watchInterval);
488
+ }
489
+ /**
490
+ * Automatically mount the OPFS root if not already mounted
491
+ *
492
+ * This method is called internally when file operations are performed
493
+ * without explicitly mounting first.
494
+ *
495
+ * @returns Promise that resolves when auto-mount is complete
496
+ * @throws {OPFSError} If auto-mount fails
497
+ */
498
+ async ensureMounted() {
499
+ if (!this.root) {
500
+ if (this.mountingPromise) {
501
+ await this.mountingPromise;
502
+ return;
503
+ }
504
+ throw new c("OPFS not mounted", "NOT_MOUNTED");
437
505
  }
438
506
  }
439
507
  /**
@@ -457,10 +525,10 @@ class ce {
457
525
  async getDirectoryHandle(t, r = !1, a = this.root) {
458
526
  if (!a)
459
527
  throw new D();
460
- const n = Array.isArray(t) ? t : y(t);
528
+ const n = Array.isArray(t) ? t : m(t);
461
529
  let s = a;
462
- for (const i of n)
463
- s = await s.getDirectoryHandle(i, { create: r });
530
+ for (const o of n)
531
+ s = await s.getDirectoryHandle(o, { create: r });
464
532
  return s;
465
533
  }
466
534
  /**
@@ -485,9 +553,9 @@ class ce {
485
553
  async getFileHandle(t, r = !1, a = this.root) {
486
554
  if (!a)
487
555
  throw new D();
488
- const n = y(t);
556
+ const n = m(t);
489
557
  if (n.length === 0)
490
- throw new P("Path must not be empty", Array.isArray(t) ? t.join("/") : t);
558
+ throw new k("Path must not be empty", Array.isArray(t) ? t.join("/") : t);
491
559
  const s = n.pop();
492
560
  return (await this.getDirectoryHandle(n, r, a)).getFileHandle(s, { create: r });
493
561
  }
@@ -531,13 +599,13 @@ class ce {
531
599
  async index(t) {
532
600
  const r = /* @__PURE__ */ new Map(), a = async (n) => {
533
601
  const s = await this.readdir(n, { withFileTypes: !0 });
534
- for (const i of s) {
535
- const o = \`\${n === "/" ? "" : n}/\${i.name}\`;
602
+ for (const o of s) {
603
+ const i = \`\${n === "/" ? "" : n}/\${o.name}\`;
536
604
  try {
537
- const c = await this.stat(o, t);
538
- r.set(o, c), c.isDirectory && await a(o);
539
- } catch (c) {
540
- console.warn(\`Skipping broken entry: \${o}\`, c);
605
+ const l = await this.stat(i, t);
606
+ r.set(i, l), l.isDirectory && await a(i);
607
+ } catch (l) {
608
+ console.warn(\`Skipping broken entry: \${i}\`, l);
541
609
  }
542
610
  }
543
611
  };
@@ -551,9 +619,10 @@ class ce {
551
619
  }), await a("/"), r;
552
620
  }
553
621
  async readFile(t, r = "utf-8") {
622
+ await this.ensureMounted();
554
623
  try {
555
- const a = await this.getFileHandle(t, !1), n = await ie(a);
556
- return r === "binary" ? n : Z(n, r);
624
+ const a = await this.getFileHandle(t, !1), n = await ue(a);
625
+ return r === "binary" ? n : re(n, r);
557
626
  } catch (a) {
558
627
  throw console.error(a), new b(t);
559
628
  }
@@ -584,8 +653,9 @@ class ce {
584
653
  * \`\`\`
585
654
  */
586
655
  async writeFile(t, r, a) {
656
+ await this.ensureMounted();
587
657
  const n = await this.getFileHandle(t, !0);
588
- await H(n, r, a, { truncate: !0 });
658
+ await C(n, r, a, { truncate: !0 });
589
659
  }
590
660
  /**
591
661
  * Append data to a file
@@ -610,8 +680,9 @@ class ce {
610
680
  * \`\`\`
611
681
  */
612
682
  async appendFile(t, r, a) {
683
+ await this.ensureMounted();
613
684
  const n = await this.getFileHandle(t, !0);
614
- await H(n, r, a, { append: !0 });
685
+ await C(n, r, a, { append: !0 });
615
686
  }
616
687
  /**
617
688
  * Create a directory
@@ -635,19 +706,19 @@ class ce {
635
706
  * \`\`\`
636
707
  */
637
708
  async mkdir(t, r) {
638
- if (!this.root)
709
+ if (await this.ensureMounted(), !this.root)
639
710
  throw new D();
640
- const a = r?.recursive ?? !1, n = y(t);
711
+ const a = r?.recursive ?? !1, n = m(t);
641
712
  let s = this.root;
642
- for (let i = 0; i < n.length; i++) {
643
- const o = n[i];
713
+ for (let o = 0; o < n.length; o++) {
714
+ const i = n[o];
644
715
  try {
645
- s = await s.getDirectoryHandle(o, { create: a || i === n.length - 1 });
646
- } catch (c) {
647
- throw c.name === "NotFoundError" ? new l(
648
- \`Parent directory does not exist: \${N(n.slice(0, i + 1))}\`,
716
+ s = await s.getDirectoryHandle(i, { create: a || o === n.length - 1 });
717
+ } catch (l) {
718
+ throw l.name === "NotFoundError" ? new c(
719
+ \`Parent directory does not exist: \${N(n.slice(0, o + 1))}\`,
649
720
  "ENOENT"
650
- ) : c.name === "TypeMismatchError" ? new l(\`Path segment is not a directory: \${o}\`, "ENOTDIR") : new l("Failed to create directory", "MKDIR_FAILED");
721
+ ) : l.name === "TypeMismatchError" ? new c(\`Path segment is not a directory: \${i}\`, "ENOTDIR") : new c("Failed to create directory", "MKDIR_FAILED");
651
722
  }
652
723
  }
653
724
  }
@@ -681,60 +752,61 @@ class ce {
681
752
  * \`\`\`
682
753
  */
683
754
  async stat(t, r) {
684
- const a = y(t), n = a.pop(), s = await this.getDirectoryHandle(a, !1), i = r?.includeHash ?? !1, o = r?.hashAlgorithm ?? "SHA-1";
755
+ await this.ensureMounted();
756
+ const a = P(t), n = await this.getDirectoryHandle(M(t), !1), s = r?.includeHash ?? !1, o = r?.hashAlgorithm ?? "SHA-1";
685
757
  try {
686
- const f = await (await s.getFileHandle(n, { create: !1 })).getFile(), u = {
758
+ const l = await (await n.getFileHandle(a, { create: !1 })).getFile(), u = {
687
759
  kind: "file",
688
- size: f.size,
689
- mtime: new Date(f.lastModified).toISOString(),
690
- ctime: new Date(f.lastModified).toISOString(),
760
+ size: l.size,
761
+ mtime: new Date(l.lastModified).toISOString(),
762
+ ctime: new Date(l.lastModified).toISOString(),
691
763
  isFile: !0,
692
764
  isDirectory: !1
693
765
  };
694
- if (i)
766
+ if (s)
695
767
  try {
696
- const w = new Uint8Array(await f.arrayBuffer()), h = await oe(w, o);
697
- u.hash = h;
698
- } catch (w) {
699
- console.warn(\`Failed to calculate hash for \${t}:\`, w);
768
+ const f = new Uint8Array(await l.arrayBuffer()), w = await fe(f, o);
769
+ u.hash = w;
770
+ } catch (f) {
771
+ console.warn(\`Failed to calculate hash for \${t}:\`, f);
700
772
  }
701
773
  return u;
702
- } catch (c) {
703
- if (c.name !== "TypeMismatchError" && c.name !== "NotFoundError")
704
- throw new l("Failed to stat (file)", "STAT_FAILED");
774
+ } catch (i) {
775
+ if (i.name !== "TypeMismatchError" && i.name !== "NotFoundError")
776
+ throw new c("Failed to stat (file)", "STAT_FAILED");
705
777
  }
706
778
  try {
707
- return await s.getDirectoryHandle(n, { create: !1 }), {
779
+ return await n.getDirectoryHandle(a, { create: !1 }), {
708
780
  kind: "directory",
709
781
  size: 0,
710
782
  mtime: (/* @__PURE__ */ new Date(0)).toISOString(),
711
783
  ctime: (/* @__PURE__ */ new Date(0)).toISOString(),
712
784
  isFile: !1,
713
785
  isDirectory: !0
714
- // Directories don't have hashes
715
786
  };
716
- } catch (c) {
717
- throw c.name === "NotFoundError" ? new l(\`No such file or directory: \${t}\`, "ENOENT") : new l("Failed to stat (directory)", "STAT_FAILED");
787
+ } catch (i) {
788
+ throw i.name === "NotFoundError" ? new c(\`No such file or directory: \${t}\`, "ENOENT") : new c("Failed to stat (directory)", "STAT_FAILED");
718
789
  }
719
790
  }
720
791
  async readdir(t, r) {
792
+ await this.ensureMounted();
721
793
  const a = r?.withFileTypes ?? !1, n = await this.getDirectoryHandle(t, !1);
722
794
  if (a) {
723
795
  const s = [];
724
- for await (const [i, o] of n.entries()) {
725
- const c = o.kind === "file";
796
+ for await (const [o, i] of n.entries()) {
797
+ const l = i.kind === "file";
726
798
  s.push({
727
- name: i,
728
- kind: o.kind,
729
- isFile: c,
730
- isDirectory: !c
799
+ name: o,
800
+ kind: i.kind,
801
+ isFile: l,
802
+ isDirectory: !l
731
803
  });
732
804
  }
733
805
  return s;
734
806
  } else {
735
807
  const s = [];
736
- for await (const [i] of n.entries())
737
- s.push(i);
808
+ for await (const [o] of n.entries())
809
+ s.push(o);
738
810
  return s;
739
811
  }
740
812
  }
@@ -753,26 +825,27 @@ class ce {
753
825
  * \`\`\`
754
826
  */
755
827
  async exists(t) {
756
- const r = y(t), a = r.pop();
757
- let n = null;
828
+ await this.ensureMounted();
829
+ const r = P(t);
830
+ let a = null;
758
831
  try {
759
- n = await this.getDirectoryHandle(r, !1);
760
- } catch (s) {
761
- throw (s.name === "NotFoundError" || s.name === "TypeMismatchError") && (n = null), s;
832
+ a = await this.getDirectoryHandle(M(t), !1);
833
+ } catch (n) {
834
+ throw (n.name === "NotFoundError" || n.name === "TypeMismatchError") && (a = null), n;
762
835
  }
763
- if (!n || !a)
836
+ if (!a || !r)
764
837
  return !1;
765
838
  try {
766
- return await n.getFileHandle(a, { create: !1 }), !0;
767
- } catch (s) {
768
- if (s.name !== "NotFoundError" && s.name !== "TypeMismatchError")
769
- throw s;
839
+ return await a.getFileHandle(r, { create: !1 }), !0;
840
+ } catch (n) {
841
+ if (n.name !== "NotFoundError" && n.name !== "TypeMismatchError")
842
+ throw n;
770
843
  }
771
844
  try {
772
- return await n.getDirectoryHandle(a, { create: !1 }), !0;
773
- } catch (s) {
774
- if (s.name !== "NotFoundError" && s.name !== "TypeMismatchError")
775
- throw s;
845
+ return await a.getDirectoryHandle(r, { create: !1 }), !0;
846
+ } catch (n) {
847
+ if (n.name !== "NotFoundError" && n.name !== "TypeMismatchError")
848
+ throw n;
776
849
  }
777
850
  return !1;
778
851
  }
@@ -796,6 +869,7 @@ class ce {
796
869
  * \`\`\`
797
870
  */
798
871
  async clear(t = "/") {
872
+ await this.ensureMounted();
799
873
  try {
800
874
  const r = await this.readdir(t, { withFileTypes: !0 });
801
875
  for (const a of r) {
@@ -803,7 +877,7 @@ class ce {
803
877
  await this.remove(n, { recursive: !0 });
804
878
  }
805
879
  } catch (r) {
806
- throw r instanceof l ? r : new l(\`Failed to clear directory: \${t}\`, "CLEAR_FAILED");
880
+ throw r instanceof c ? r : new c(\`Failed to clear directory: \${t}\`, "CLEAR_FAILED");
807
881
  }
808
882
  }
809
883
  /**
@@ -831,17 +905,18 @@ class ce {
831
905
  * \`\`\`
832
906
  */
833
907
  async remove(t, r) {
834
- const a = r?.recursive ?? !1, n = r?.force ?? !1, s = y(t), i = s.pop();
835
- if (!i)
836
- throw new P("Invalid path", t);
837
- const o = await this.getDirectoryHandle(s, !1);
908
+ await this.ensureMounted();
909
+ const a = r?.recursive ?? !1, n = r?.force ?? !1, s = P(t);
910
+ if (!s)
911
+ throw new k("Invalid path", t);
912
+ const o = await this.getDirectoryHandle(M(t), !1);
838
913
  try {
839
- await o.removeEntry(i, { recursive: a });
840
- } catch (c) {
841
- if (c.name === "NotFoundError") {
914
+ await o.removeEntry(s, { recursive: a });
915
+ } catch (i) {
916
+ if (i.name === "NotFoundError") {
842
917
  if (!n)
843
- throw new l(\`No such file or directory: \${t}\`, "ENOENT");
844
- } else throw c.name === "InvalidModificationError" ? new l(\`Directory not empty: \${t}. Use recursive option to force removal.\`, "ENOTEMPTY") : c.name === "TypeMismatchError" && !a ? new l(\`Cannot remove directory without recursive option: \${t}\`, "EISDIR") : new l(\`Failed to remove path: \${t}\`, "RM_FAILED");
918
+ throw new c(\`No such file or directory: \${t}\`, "ENOENT");
919
+ } else throw i.name === "InvalidModificationError" ? new c(\`Directory not empty: \${t}. Use recursive option to force removal.\`, "ENOTEMPTY") : i.name === "TypeMismatchError" && !a ? new c(\`Cannot remove directory without recursive option: \${t}\`, "EISDIR") : new c(\`Failed to remove path: \${t}\`, "RM_FAILED");
845
920
  }
846
921
  }
847
922
  /**
@@ -863,22 +938,14 @@ class ce {
863
938
  * \`\`\`
864
939
  */
865
940
  async realpath(t) {
941
+ await this.ensureMounted();
866
942
  try {
867
- const r = y(t), a = [];
868
- for (const i of r)
869
- if (!(i === "." || i === ""))
870
- if (i === "..") {
871
- if (a.length === 0)
872
- throw new l("Path escapes root", "EINVAL");
873
- a.length > 0 && a.pop();
874
- } else
875
- a.push(i);
876
- const n = N(a);
877
- if (!await this.exists(n))
878
- throw new b(n);
879
- return n;
943
+ const r = ce(t);
944
+ if (!await this.exists(r))
945
+ throw new b(r);
946
+ return r;
880
947
  } catch (r) {
881
- throw r instanceof l ? r : new l(\`Failed to resolve path: \${t}\`, "REALPATH_FAILED");
948
+ throw r instanceof c ? r : new c(\`Failed to resolve path: \${t}\`, "REALPATH_FAILED");
882
949
  }
883
950
  }
884
951
  /**
@@ -898,12 +965,13 @@ class ce {
898
965
  * \`\`\`
899
966
  */
900
967
  async rename(t, r) {
968
+ await this.ensureMounted();
901
969
  try {
902
970
  if (!await this.exists(t))
903
971
  throw new b(t);
904
972
  await this.copy(t, r, { recursive: !0 }), await this.remove(t, { recursive: !0 });
905
973
  } catch (a) {
906
- throw a instanceof l ? a : new l(\`Failed to rename from \${t} to \${r}\`, "RENAME_FAILED");
974
+ throw a instanceof c ? a : new c(\`Failed to rename from \${t} to \${r}\`, "RENAME_FAILED");
907
975
  }
908
976
  }
909
977
  /**
@@ -922,44 +990,46 @@ class ce {
922
990
  * @example
923
991
  * \`\`\`typescript
924
992
  * // Copy a file
925
- * await fs.cp('/source/file.txt', '/dest/file.txt');
993
+ * await fs.copy('/source/file.txt', '/dest/file.txt');
926
994
  *
927
995
  * // Copy a directory and all its contents
928
- * await fs.cp('/source/dir', '/dest/dir', { recursive: true });
996
+ * await fs.copy('/source/dir', '/dest/dir', { recursive: true });
929
997
  *
930
998
  * // Copy without overwriting existing files
931
- * await fs.cp('/source', '/dest', { recursive: true, force: false });
999
+ * await fs.copy('/source', '/dest', { recursive: true, force: false });
932
1000
  * \`\`\`
933
1001
  */
934
1002
  async copy(t, r, a) {
1003
+ await this.ensureMounted();
935
1004
  try {
936
1005
  const n = a?.recursive ?? !1, s = a?.force ?? !0;
937
1006
  if (!await this.exists(t))
938
- throw new l(\`Source does not exist: \${t}\`, "ENOENT");
1007
+ throw new c(\`Source does not exist: \${t}\`, "ENOENT");
939
1008
  if (await this.exists(r) && !s)
940
- throw new l(\`Destination already exists: \${r}\`, "EEXIST");
1009
+ throw new c(\`Destination already exists: \${r}\`, "EEXIST");
941
1010
  if ((await this.stat(t)).isFile) {
942
- const f = await this.readFile(t, "binary");
943
- await this.writeFile(r, f);
1011
+ const u = await this.readFile(t, "binary");
1012
+ await this.writeFile(r, u);
944
1013
  } else {
945
1014
  if (!n)
946
- throw new l(\`Cannot copy directory without recursive option: \${t}\`, "EISDIR");
1015
+ throw new c(\`Cannot copy directory without recursive option: \${t}\`, "EISDIR");
947
1016
  await this.mkdir(r, { recursive: !0 });
948
- const f = await this.readdir(t, { withFileTypes: !0 });
949
- for (const u of f) {
950
- const w = \`\${t}/\${u.name}\`, h = \`\${r}/\${u.name}\`;
1017
+ const u = await this.readdir(t, { withFileTypes: !0 });
1018
+ for (const f of u) {
1019
+ const w = \`\${t}/\${f.name}\`, h = \`\${r}/\${f.name}\`;
951
1020
  await this.copy(w, h, { recursive: !0, force: s });
952
1021
  }
953
1022
  }
954
1023
  } catch (n) {
955
- throw n instanceof l ? n : new l(\`Failed to copy from \${t} to \${r}\`, "CP_FAILED");
1024
+ throw n instanceof c ? n : new c(\`Failed to copy from \${t} to \${r}\`, "CP_FAILED");
956
1025
  }
957
1026
  }
958
1027
  /**
959
1028
  * Start watching a file or directory for changes
960
1029
  */
961
1030
  async watch(t) {
962
- const r = t.startsWith("/") ? t : \`/\${t}\`, a = await this.buildSnapshot(r);
1031
+ await this.ensureMounted();
1032
+ const r = I(t), a = await this.buildSnapshot(r);
963
1033
  this.watchers.set(r, a), this.watchTimer || (this.watchTimer = setInterval(() => {
964
1034
  this.scanWatches();
965
1035
  }, this.watchInterval));
@@ -968,17 +1038,17 @@ class ce {
968
1038
  * Stop watching a previously watched path
969
1039
  */
970
1040
  unwatch(t) {
971
- const r = t.startsWith("/") ? t : \`/\${t}\`;
1041
+ const r = I(t);
972
1042
  this.watchers.delete(r), this.watchers.size === 0 && this.watchTimer && (clearInterval(this.watchTimer), this.watchTimer = null);
973
1043
  }
974
1044
  async buildSnapshot(t) {
975
1045
  const r = /* @__PURE__ */ new Map(), a = async (n) => {
976
1046
  const s = await this.stat(n);
977
1047
  if (r.set(n, s), s.isDirectory) {
978
- const i = await this.readdir(n, { withFileTypes: !0 });
979
- for (const o of i) {
980
- const c = \`\${n === "/" ? "" : n}/\${o.name}\`;
981
- await a(c);
1048
+ const o = await this.readdir(n, { withFileTypes: !0 });
1049
+ for (const i of o) {
1050
+ const l = \`\${n === "/" ? "" : n}/\${i.name}\`;
1051
+ await a(l);
982
1052
  }
983
1053
  }
984
1054
  };
@@ -997,9 +1067,9 @@ class ce {
997
1067
  a = /* @__PURE__ */ new Map();
998
1068
  }
999
1069
  const n = [];
1000
- for (const [s, i] of a) {
1001
- const o = r.get(s);
1002
- o ? (o.mtime !== i.mtime || o.size !== i.size) && n.push({ path: s, type: "change" }) : n.push({ path: s, type: "create" });
1070
+ for (const [s, o] of a) {
1071
+ const i = r.get(s);
1072
+ i ? (i.mtime !== o.mtime || i.size !== o.size) && n.push({ path: s, type: "change" }) : n.push({ path: s, type: "create" });
1003
1073
  }
1004
1074
  for (const s of r.keys())
1005
1075
  a.has(s) || n.push({ path: s, type: "delete" });
@@ -1043,24 +1113,20 @@ class ce {
1043
1113
  * \`\`\`
1044
1114
  */
1045
1115
  async sync(t, r) {
1116
+ await this.ensureMounted();
1046
1117
  try {
1047
1118
  (r?.cleanBefore ?? !1) && await this.clear("/");
1048
1119
  for (const [n, s] of t) {
1049
- const i = n.startsWith("/") ? n : \`/\${n}\`;
1050
- let o;
1051
- if (s instanceof Blob) {
1052
- const c = await s.arrayBuffer();
1053
- o = new Uint8Array(c);
1054
- } else
1055
- o = s;
1056
- await this.writeFile(i, o);
1120
+ const o = I(n);
1121
+ let i;
1122
+ s instanceof Blob ? i = await he(s) : i = s, await this.writeFile(o, i);
1057
1123
  }
1058
1124
  } catch (a) {
1059
- throw a instanceof l ? a : new l("Failed to sync file system", "SYNC_FAILED");
1125
+ throw a instanceof c ? a : new c("Failed to sync file system", "SYNC_FAILED");
1060
1126
  }
1061
1127
  }
1062
1128
  }
1063
- typeof self < "u" && self.constructor.name === "DedicatedWorkerGlobalScope" && x(new ce());
1064
- //# sourceMappingURL=worker-D5GbafFH.js.map
1065
- `,r=typeof self<"u"&&self.Blob&&new Blob(["URL.revokeObjectURL(import.meta.url);",a],{type:"text/javascript;charset=utf-8"});function s(t){let n;try{if(n=r&&(self.URL||self.webkitURL).createObjectURL(r),!n)throw"";const e=new Worker(n,{type:"module",name:t?.name});return e.addEventListener("error",()=>{(self.URL||self.webkitURL).revokeObjectURL(n)}),e}catch{return new Worker("data:text/javascript;charset=utf-8,"+encodeURIComponent(a),{type:"module",name:t?.name})}}function o(){return i.wrap(new s)}exports.createWorker=o;
1129
+ typeof self < "u" && self.constructor.name === "DedicatedWorkerGlobalScope" && O(new we());
1130
+ //# sourceMappingURL=worker-CMvl9yOu.js.map
1131
+ `,i=typeof self<"u"&&self.Blob&&new Blob(["URL.revokeObjectURL(import.meta.url);",o],{type:"text/javascript;charset=utf-8"});function s(r){let t;try{if(t=i&&(self.URL||self.webkitURL).createObjectURL(i),!t)throw"";const e=new Worker(t,{type:"module",name:r?.name});return e.addEventListener("error",()=>{(self.URL||self.webkitURL).revokeObjectURL(t)}),e}catch{return new Worker("data:text/javascript;charset=utf-8,"+encodeURIComponent(o),{type:"module",name:r?.name})}}function c(r,t){const e=a.wrap(new s);return r&&e.setWatchCallback(a.proxy(r),t),e}exports.DirectoryNotFoundError=n.DirectoryNotFoundError;exports.FileNotFoundError=n.FileNotFoundError;exports.OPFSError=n.OPFSError;exports.OPFSNotMountedError=n.OPFSNotMountedError;exports.OPFSNotSupportedError=n.OPFSNotSupportedError;exports.PathError=n.PathError;exports.PermissionError=n.PermissionError;exports.StorageError=n.StorageError;exports.TimeoutError=n.TimeoutError;exports.basename=n.basename;exports.calculateFileHash=n.calculateFileHash;exports.checkOPFSSupport=n.checkOPFSSupport;exports.convertBlobToUint8Array=n.convertBlobToUint8Array;exports.createBuffer=n.createBuffer;exports.decodeBuffer=n.decodeBuffer;exports.dirname=n.dirname;exports.encodeString=n.encodeString;exports.extname=n.extname;exports.joinPath=n.joinPath;exports.normalizePath=n.normalizePath;exports.readFileData=n.readFileData;exports.resolvePath=n.resolvePath;exports.splitPath=n.splitPath;exports.writeFileData=n.writeFileData;exports.createWorker=c;
1066
1132
  //# sourceMappingURL=index.cjs.map