@lvce-editor/file-system-worker 5.20.3 → 5.21.0

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.
@@ -64,10 +64,10 @@ const Object$1 = 1;
64
64
  const Number$1 = 2;
65
65
  const Array$1 = 3;
66
66
  const String$1 = 4;
67
- const Boolean = 5;
67
+ const Boolean$1 = 5;
68
68
  const Function = 6;
69
69
  const Null = 7;
70
- const Unknown = 8;
70
+ const Unknown$1 = 8;
71
71
  const getType = value => {
72
72
  switch (typeof value) {
73
73
  case 'number':
@@ -85,9 +85,9 @@ const getType = value => {
85
85
  }
86
86
  return Object$1;
87
87
  case 'boolean':
88
- return Boolean;
88
+ return Boolean$1;
89
89
  default:
90
- return Unknown;
90
+ return Unknown$1;
91
91
  }
92
92
  };
93
93
  const object = value => {
@@ -601,7 +601,7 @@ const callbacks = Object.create(null);
601
601
  const get$1 = id => {
602
602
  return callbacks[id];
603
603
  };
604
- const remove$6 = id => {
604
+ const remove$7 = id => {
605
605
  delete callbacks[id];
606
606
  };
607
607
  class JsonRpcError extends Error {
@@ -826,7 +826,7 @@ const resolve = (id, response) => {
826
826
  return;
827
827
  }
828
828
  fn(response);
829
- remove$6(id);
829
+ remove$7(id);
830
830
  };
831
831
  const E_COMMAND_NOT_FOUND = 'E_COMMAND_NOT_FOUND';
832
832
  const getErrorType = prettyError => {
@@ -1316,7 +1316,7 @@ const set$5 = (id, rpc) => {
1316
1316
  const get = id => {
1317
1317
  return rpcs[id];
1318
1318
  };
1319
- const remove$5 = id => {
1319
+ const remove$6 = id => {
1320
1320
  delete rpcs[id];
1321
1321
  };
1322
1322
 
@@ -1346,7 +1346,7 @@ const create = rpcId => {
1346
1346
  set$5(rpcId, mockRpc);
1347
1347
  // @ts-ignore
1348
1348
  mockRpc[Symbol.dispose] = () => {
1349
- remove$5(rpcId);
1349
+ remove$6(rpcId);
1350
1350
  };
1351
1351
  // @ts-ignore
1352
1352
  return mockRpc;
@@ -1359,6 +1359,7 @@ const create = rpcId => {
1359
1359
 
1360
1360
  const Directory$1 = 3;
1361
1361
  const File$3 = 7;
1362
+ const Unknown = 12;
1362
1363
 
1363
1364
  const DebugWorker = 55;
1364
1365
  const ExtensionHostWorker = 44;
@@ -1375,17 +1376,17 @@ const {
1375
1376
  invoke: invoke$3,
1376
1377
  set: set$3
1377
1378
  } = create(FileSystemProcess$1);
1378
- const remove$4 = async uri => {
1379
+ const remove$5 = async uri => {
1379
1380
  return invoke$3('FileSystem.remove', uri);
1380
1381
  };
1381
- const readFile$4 = async uri => {
1382
+ const readFile$5 = async uri => {
1382
1383
  return invoke$3('FileSystem.readFile', uri);
1383
1384
  };
1384
1385
  const appendFile$2 = async (uri, text) => {
1385
1386
  // @ts-ignore
1386
1387
  return invoke$3('FileSystem.appendFile', uri, text);
1387
1388
  };
1388
- const readDirWithFileTypes$4 = async uri => {
1389
+ const readDirWithFileTypes$5 = async uri => {
1389
1390
  return invoke$3('FileSystem.readDirWithFileTypes', uri);
1390
1391
  };
1391
1392
  const readJson$4 = async root => {
@@ -1400,11 +1401,11 @@ const stat$4 = async path => {
1400
1401
  // @ts-ignore
1401
1402
  return invoke$3('FileSystem.stat', path);
1402
1403
  };
1403
- const writeFile$4 = async (path, content) => {
1404
+ const writeFile$5 = async (path, content) => {
1404
1405
  // @ts-ignore
1405
1406
  return invoke$3('FileSystem.writeFile', path, content);
1406
1407
  };
1407
- const mkdir$4 = async path => {
1408
+ const mkdir$5 = async path => {
1408
1409
  // @ts-ignore
1409
1410
  return invoke$3('FileSystem.mkdir', path);
1410
1411
  };
@@ -1420,7 +1421,7 @@ const getFolderSize$4 = async uri => {
1420
1421
  // @ts-ignore
1421
1422
  return invoke$3('FileSystem.getFolderSize', uri);
1422
1423
  };
1423
- const exists$4 = async uri => {
1424
+ const exists$5 = async uri => {
1424
1425
  // @ts-ignore
1425
1426
  return invoke$3('FileSystem.exists', uri);
1426
1427
  };
@@ -1429,19 +1430,19 @@ const FileSystemProcess = {
1429
1430
  __proto__: null,
1430
1431
  appendFile: appendFile$2,
1431
1432
  copy: copy$4,
1432
- exists: exists$4,
1433
+ exists: exists$5,
1433
1434
  getFolderSize: getFolderSize$4,
1434
1435
  getRealPath: getRealPath$4,
1435
1436
  invoke: invoke$3,
1436
- mkdir: mkdir$4,
1437
- readDirWithFileTypes: readDirWithFileTypes$4,
1438
- readFile: readFile$4,
1437
+ mkdir: mkdir$5,
1438
+ readDirWithFileTypes: readDirWithFileTypes$5,
1439
+ readFile: readFile$5,
1439
1440
  readJson: readJson$4,
1440
- remove: remove$4,
1441
+ remove: remove$5,
1441
1442
  rename: rename$4,
1442
1443
  set: set$3,
1443
1444
  stat: stat$4,
1444
- writeFile: writeFile$4
1445
+ writeFile: writeFile$5
1445
1446
  };
1446
1447
 
1447
1448
  const createLazyRpc = rpcId => {
@@ -1481,7 +1482,7 @@ const createLazyRpc = rpcId => {
1481
1482
  activeRpc = undefined;
1482
1483
  rpcPromise = undefined;
1483
1484
  if (rpc && get(rpcId) === rpc) {
1484
- remove$5(rpcId);
1485
+ remove$6(rpcId);
1485
1486
  }
1486
1487
  if (notify) {
1487
1488
  for (const listener of resetListeners) {
@@ -1556,19 +1557,19 @@ const getFileHashes$1 = async uris => {
1556
1557
  const {
1557
1558
  appendFile: appendFile$1,
1558
1559
  copy: copy$3,
1559
- exists: exists$3,
1560
+ exists: exists$4,
1560
1561
  getFolderSize: getFolderSize$3,
1561
1562
  getRealPath: getRealPath$3,
1562
1563
  invoke: invoke$1,
1563
- mkdir: mkdir$3,
1564
- readDirWithFileTypes: readDirWithFileTypes$3,
1565
- readFile: readFile$3,
1564
+ mkdir: mkdir$4,
1565
+ readDirWithFileTypes: readDirWithFileTypes$4,
1566
+ readFile: readFile$4,
1566
1567
  readJson: readJson$3,
1567
- remove: remove$3,
1568
+ remove: remove$4,
1568
1569
  rename: rename$3,
1569
1570
  set,
1570
1571
  stat: stat$3,
1571
- writeFile: writeFile$3
1572
+ writeFile: writeFile$4
1572
1573
  } = FileSystemProcess;
1573
1574
 
1574
1575
  const Http = 'http:';
@@ -1689,11 +1690,11 @@ const readFileAsBlob$2 = async uri => {
1689
1690
  if (entry.type !== file) throw new Error(`File is a directory: ${uri}`);
1690
1691
  return entry.content;
1691
1692
  };
1692
- const readFile$2 = async uri => {
1693
+ const readFile$3 = async uri => {
1693
1694
  const blob = await readFileAsBlob$2(uri);
1694
1695
  return blob.text();
1695
1696
  };
1696
- const writeFile$2 = async (uri, content) => {
1697
+ const writeFile$3 = async (uri, content) => {
1697
1698
  const path = getPath(uri);
1698
1699
  ensureParentDirs(path);
1699
1700
  files.set(path, {
@@ -1704,9 +1705,9 @@ const writeFile$2 = async (uri, content) => {
1704
1705
  });
1705
1706
  await triggerMemfsFileWatcher(uri);
1706
1707
  };
1707
- const exists$2 = async uri => !!getEntry(uri);
1708
- const createFile$2 = async uri => writeFile$2(uri, '');
1709
- const mkdir$2 = async uri => {
1708
+ const exists$3 = async uri => !!getEntry(uri);
1709
+ const createFile$2 = async uri => writeFile$3(uri, '');
1710
+ const mkdir$3 = async uri => {
1710
1711
  const path = getPath(uri);
1711
1712
  ensureParentDirs(path);
1712
1713
  files.set(path, {
@@ -1715,14 +1716,14 @@ const mkdir$2 = async uri => {
1715
1716
  });
1716
1717
  await triggerMemfsFileWatcher(uri);
1717
1718
  };
1718
- const remove$2 = async uri => {
1719
+ const remove$3 = async uri => {
1719
1720
  const path = getPath(uri);
1720
1721
  for (const key of files.keys()) {
1721
1722
  if (key === path || key.startsWith(`${path}/`)) files.delete(key);
1722
1723
  }
1723
1724
  await triggerMemfsFileWatcher(uri);
1724
1725
  };
1725
- const readDirWithFileTypes$2 = async uri => {
1726
+ const readDirWithFileTypes$3 = async uri => {
1726
1727
  const path = `${getPath(uri)}/`;
1727
1728
  const entries = new Map();
1728
1729
  for (const [key, value] of files) {
@@ -1756,7 +1757,7 @@ const rename$2 = async (oldUri, newUri) => {
1756
1757
  await triggerMemfsFileWatcher(oldUri);
1757
1758
  await triggerMemfsFileWatcher(newUri);
1758
1759
  };
1759
- const copy$2 = async (oldUri, newUri) => writeFile$2(newUri, await readFile$2(oldUri));
1760
+ const copy$2 = async (oldUri, newUri) => writeFile$3(newUri, await readFile$3(oldUri));
1760
1761
  const stat$2 = async uri => {
1761
1762
  const entry = getEntry(uri);
1762
1763
  return entry ? {
@@ -1768,7 +1769,7 @@ const stat$2 = async uri => {
1768
1769
  size: 0
1769
1770
  };
1770
1771
  };
1771
- const readJson$2 = async uri => JSON.parse(await readFile$2(uri));
1772
+ const readJson$2 = async uri => JSON.parse(await readFile$3(uri));
1772
1773
  const getPathSeparator$1 = async _root => '/';
1773
1774
  const getRealPath$2 = async uri => uri;
1774
1775
  const getFolderSize$2 = async uri => {
@@ -1789,20 +1790,20 @@ const FileSystemMemory = {
1789
1790
  __proto__: null,
1790
1791
  copy: copy$2,
1791
1792
  createFile: createFile$2,
1792
- exists: exists$2,
1793
+ exists: exists$3,
1793
1794
  getFiles,
1794
1795
  getFolderSize: getFolderSize$2,
1795
1796
  getPathSeparator: getPathSeparator$1,
1796
1797
  getRealPath: getRealPath$2,
1797
- mkdir: mkdir$2,
1798
- readDirWithFileTypes: readDirWithFileTypes$2,
1799
- readFile: readFile$2,
1798
+ mkdir: mkdir$3,
1799
+ readDirWithFileTypes: readDirWithFileTypes$3,
1800
+ readFile: readFile$3,
1800
1801
  readFileAsBlob: readFileAsBlob$2,
1801
1802
  readJson: readJson$2,
1802
- remove: remove$2,
1803
+ remove: remove$3,
1803
1804
  rename: rename$2,
1804
1805
  stat: stat$2,
1805
- writeFile: writeFile$2
1806
+ writeFile: writeFile$3
1806
1807
  };
1807
1808
 
1808
1809
  const memoryRoot = id => `memfs:///applications/${encodeURIComponent(id)}`;
@@ -1826,7 +1827,7 @@ const execute = async (id, method, ...args) => {
1826
1827
  // This callback handles only non-memory URIs, never file contents storage.
1827
1828
  return invoke$2('Application.execute', id, `FileSystem.${method}`, ...args);
1828
1829
  };
1829
- const dispose = async id => remove$2(memoryRoot(id));
1830
+ const dispose = async id => remove$3(memoryRoot(id));
1830
1831
 
1831
1832
  const connect = async port => {
1832
1833
  const {
@@ -1838,10 +1839,10 @@ const connect = async port => {
1838
1839
  });
1839
1840
  };
1840
1841
 
1841
- const remove$1 = async dirent => {
1842
+ const remove$2 = async dirent => {
1842
1843
  throw new Error('not implemented');
1843
1844
  };
1844
- const readFile$1 = async uri => {
1845
+ const readFile$2 = async uri => {
1845
1846
  const response = await fetch(uri);
1846
1847
  if (!response.ok) {
1847
1848
  throw new Error(response.statusText);
@@ -1857,11 +1858,11 @@ const readFileAsBlob$1 = async uri => {
1857
1858
  const result = await response.blob();
1858
1859
  return result;
1859
1860
  };
1860
- const exists$1 = async uri => {
1861
+ const exists$2 = async uri => {
1861
1862
  const response = await fetch(uri);
1862
1863
  return response.ok;
1863
1864
  };
1864
- const readDirWithFileTypes$1 = async uri => {
1865
+ const readDirWithFileTypes$2 = async uri => {
1865
1866
  throw new Error('not implemented');
1866
1867
  };
1867
1868
  const readJson$1 = async uri => {
@@ -1881,10 +1882,10 @@ const stat$1 = async dirent => {
1881
1882
  const createFile$1 = async uri => {
1882
1883
  throw new Error('not implemented');
1883
1884
  };
1884
- const writeFile$1 = async (uri, content) => {
1885
+ const writeFile$2 = async (uri, content) => {
1885
1886
  throw new Error('not implemented');
1886
1887
  };
1887
- const mkdir$1 = async uri => {
1888
+ const mkdir$2 = async uri => {
1888
1889
  throw new Error('not implemented');
1889
1890
  };
1890
1891
  const rename$1 = async (oldUri, newUri) => {
@@ -1901,18 +1902,464 @@ const FileSystemFetch = {
1901
1902
  __proto__: null,
1902
1903
  copy: copy$1,
1903
1904
  createFile: createFile$1,
1904
- exists: exists$1,
1905
+ exists: exists$2,
1905
1906
  getFolderSize: getFolderSize$1,
1906
1907
  getRealPath: getRealPath$1,
1907
- mkdir: mkdir$1,
1908
- readDirWithFileTypes: readDirWithFileTypes$1,
1909
- readFile: readFile$1,
1908
+ mkdir: mkdir$2,
1909
+ readDirWithFileTypes: readDirWithFileTypes$2,
1910
+ readFile: readFile$2,
1910
1911
  readFileAsBlob: readFileAsBlob$1,
1911
1912
  readJson: readJson$1,
1912
- remove: remove$1,
1913
+ remove: remove$2,
1913
1914
  rename: rename$1,
1914
1915
  stat: stat$1,
1915
- writeFile: writeFile$1
1916
+ writeFile: writeFile$2
1917
+ };
1918
+
1919
+ const hasName = (error, name) => {
1920
+ return typeof error === 'object' && error !== null && 'name' in error && error.name === name;
1921
+ };
1922
+ const isNotAllowedError = error => hasName(error, 'NotAllowedError');
1923
+ const isNotFoundError = error => hasName(error, 'NotFoundError');
1924
+
1925
+ const Granted = 'granted';
1926
+ const Prompt = 'prompt';
1927
+ const Denied = 'denied';
1928
+
1929
+ const Directory = 'directory';
1930
+ const File$1 = 'file';
1931
+
1932
+ const getDirentType = fileHandleKind => {
1933
+ switch (fileHandleKind) {
1934
+ case Directory:
1935
+ return Directory$1;
1936
+ case File$1:
1937
+ return File$3;
1938
+ default:
1939
+ return Unknown;
1940
+ }
1941
+ };
1942
+
1943
+ class FileNotFoundError extends Error {
1944
+ code = 'ENOENT';
1945
+ constructor(path) {
1946
+ super(`File not found '${path}'`);
1947
+ this.name = 'FileNotFoundError';
1948
+ }
1949
+ }
1950
+
1951
+ /**
1952
+ * Do not use directly, use FileSystemHtml.getChildHandles
1953
+ * instead which prompts for the required permission to
1954
+ * retrieve the child handles
1955
+ */
1956
+ const getChildHandles$1 = async handle => {
1957
+ object(handle);
1958
+ // @ts-ignore - values() exists on FileSystemDirectoryHandle but TypeScript types may not include it
1959
+ const handles = await Array.fromAsync(handle.values());
1960
+ return handles;
1961
+ };
1962
+ const getFileHandle$1 = (handle, name, options) => {
1963
+ return handle.getFileHandle(name, options);
1964
+ };
1965
+ const getDirectoryHandle$1 = (handle, name) => {
1966
+ return handle.getDirectoryHandle(name);
1967
+ };
1968
+
1969
+ const getBinaryString$1 = async file => {
1970
+ const bytes = new Uint8Array(await file.arrayBuffer());
1971
+ const chunks = [];
1972
+ const chunkSize = 32_768;
1973
+ for (let i = 0; i < bytes.length; i += chunkSize) {
1974
+ chunks.push(String.fromCodePoint(...bytes.subarray(i, i + chunkSize)));
1975
+ }
1976
+ return chunks.join('');
1977
+ };
1978
+
1979
+ const getFile = async handle => {
1980
+ if ('file' in handle) return handle.file;
1981
+ return handle.getFile();
1982
+ };
1983
+ const getBinaryString = async handle => {
1984
+ const file = await getFile(handle);
1985
+ const text = await getBinaryString$1(file);
1986
+ return text;
1987
+ };
1988
+ const write = async (handle, content) => {
1989
+ if ('readonly' in handle && handle.readonly) {
1990
+ throw new Error(`File ${handle.name} is read-only`);
1991
+ }
1992
+ const writable = await handle.createWritable();
1993
+ await writable.write(content);
1994
+ await writable.close();
1995
+ };
1996
+
1997
+ const {
1998
+ invoke} = createLazyRpc(RendererProcess);
1999
+
2000
+ const requestPermission = async (handle, options) => {
2001
+ // query permission, but from renderer process
2002
+ // because handle.requestPermission is not implemented
2003
+ // in a worker, see https://github.com/WICG/file-system-access/issues/289
2004
+ const permissionTypeNow = await invoke('FileSystemHandle.requestPermission', handle, options);
2005
+ return permissionTypeNow;
2006
+ };
2007
+ const queryPermission = async (handle, options) => {
2008
+ // @ts-ignore - queryPermission exists on FileSystemHandle but TypeScript types may not include it
2009
+ return handle.queryPermission(options);
2010
+ };
2011
+
2012
+ const join = (pathSeparator, ...parts) => {
2013
+ return parts.join(pathSeparator);
2014
+ };
2015
+ const dirname = (pathSeparator, path) => {
2016
+ const index = path.lastIndexOf(pathSeparator);
2017
+ return index === -1 ? path : path.slice(0, index);
2018
+ };
2019
+ const getBaseName = (pathSeparator, path) => {
2020
+ return path.slice(path.lastIndexOf(pathSeparator) + 1);
2021
+ };
2022
+
2023
+ // Native IDB events expose a generic result that may itself be mutable.
2024
+ // eslint-disable-next-line @typescript-eslint/prefer-readonly-parameter-types
2025
+ const requestToPromise = request => {
2026
+ return new Promise((resolve, reject) => {
2027
+ request.addEventListener('success', () => resolve(request.result), {
2028
+ once: true
2029
+ });
2030
+ request.addEventListener('error', () => reject(request.error || new Error('IndexedDB request failed')), {
2031
+ once: true
2032
+ });
2033
+ });
2034
+ };
2035
+ const state$1 = {};
2036
+ const getDatabase = () => {
2037
+ state$1.databasePromise ||= (() => {
2038
+ // Keep the renderer's database and store names so existing workspaces restore.
2039
+ const request = indexedDB.open('handle', 1);
2040
+ request.onupgradeneeded = () => {
2041
+ const database = request.result;
2042
+ if (!database.objectStoreNames.contains('file-handles-store')) {
2043
+ database.createObjectStore('file-handles-store');
2044
+ }
2045
+ };
2046
+ return requestToPromise(request);
2047
+ })();
2048
+ return state$1.databasePromise;
2049
+ };
2050
+ const addHandle$1 = async (uri, handle) => {
2051
+ const database = await getDatabase();
2052
+ await requestToPromise(database.transaction('file-handles-store', 'readwrite').objectStore('file-handles-store').put(handle, uri));
2053
+ };
2054
+ const getHandle$1 = async uri => {
2055
+ const database = await getDatabase();
2056
+ return requestToPromise(database.transaction('file-handles-store').objectStore('file-handles-store').get(uri));
2057
+ };
2058
+
2059
+ const handles = Object.create(null);
2060
+ const getLegacyHtmlKeys = uri => {
2061
+ if (!uri.startsWith('html://')) {
2062
+ return [];
2063
+ }
2064
+ const strippedUri = uri.slice('html://'.length);
2065
+ const legacyKeys = [];
2066
+ if (strippedUri) {
2067
+ legacyKeys.push(strippedUri);
2068
+ }
2069
+ if (strippedUri.startsWith('/')) {
2070
+ legacyKeys.push(strippedUri.slice(1));
2071
+ }
2072
+ return legacyKeys.filter((value, index, array) => value && array.indexOf(value) === index);
2073
+ };
2074
+ const addHandle = async (uri, handle) => {
2075
+ try {
2076
+ handles[uri] = handle;
2077
+ await addHandle$1(uri, handle);
2078
+ } catch (error) {
2079
+ throw new VError(error, 'Failed to add handle');
2080
+ }
2081
+ };
2082
+ const addHandles = async (parentUri, childHandles) => {
2083
+ const promises = [];
2084
+ for (const childHandle of childHandles) {
2085
+ const childUri = parentUri + '/' + childHandle.name;
2086
+ if (childUri in handles) {
2087
+ continue;
2088
+ }
2089
+ handles[childUri] = childHandle;
2090
+ promises.push(addHandle(childUri, childHandle));
2091
+ }
2092
+ await Promise.all(promises);
2093
+ };
2094
+ const removeHandle = uri => {
2095
+ delete handles[uri];
2096
+ const prefix = `${uri}/`;
2097
+ for (const key in handles) {
2098
+ if (key.startsWith(prefix)) {
2099
+ delete handles[key];
2100
+ }
2101
+ }
2102
+ };
2103
+ const getHandle = async uri => {
2104
+ try {
2105
+ if (uri in handles) {
2106
+ return handles[uri];
2107
+ }
2108
+ let handle = await getHandle$1(uri);
2109
+ if (!handle) {
2110
+ const legacyKeys = getLegacyHtmlKeys(uri);
2111
+ for (const legacyKey of legacyKeys) {
2112
+ handle = await getHandle$1(legacyKey);
2113
+ if (handle) {
2114
+ await addHandle(uri, handle);
2115
+ handles[legacyKey] = handle;
2116
+ break;
2117
+ }
2118
+ }
2119
+ }
2120
+ if (handle) {
2121
+ handles[uri] = handle;
2122
+ }
2123
+ return handle;
2124
+ } catch (error) {
2125
+ throw new VError(error, 'Failed to get handle');
2126
+ }
2127
+ };
2128
+
2129
+ const pathSeparator$2 = '/';
2130
+ const getDirectoryHandleWithDependencies = async (uri, dependencies) => {
2131
+ const handle = await dependencies.getHandle(uri);
2132
+ if (handle) {
2133
+ return handle;
2134
+ }
2135
+ const dirname$1 = dirname(pathSeparator$2, uri);
2136
+ if (uri === dirname$1) {
2137
+ return undefined;
2138
+ }
2139
+ const parentHandle = await getDirectoryHandleWithDependencies(dirname$1, dependencies);
2140
+ if (!parentHandle) {
2141
+ return undefined;
2142
+ }
2143
+ const baseName = getBaseName(pathSeparator$2, uri);
2144
+ try {
2145
+ const directoryHandle = await dependencies.getDirectoryHandle(parentHandle, baseName);
2146
+ await dependencies.addHandle(uri, directoryHandle);
2147
+ return directoryHandle;
2148
+ } catch (error) {
2149
+ if (isNotFoundError(error)) return undefined;
2150
+ throw error;
2151
+ }
2152
+ };
2153
+ const getDirectoryHandle = async uri => {
2154
+ return getDirectoryHandleWithDependencies(uri, {
2155
+ addHandle: addHandle,
2156
+ getDirectoryHandle: getDirectoryHandle$1,
2157
+ getHandle: async path => {
2158
+ const handle = await getHandle(path);
2159
+ return handle;
2160
+ }
2161
+ });
2162
+ };
2163
+
2164
+ const pathSeparator$1 = '/';
2165
+ const getFileHandle = async (uri, options) => {
2166
+ const handle = await getHandle(uri);
2167
+ if (handle) {
2168
+ return handle;
2169
+ }
2170
+ const dirname$1 = dirname(pathSeparator$1, uri);
2171
+ const parentHandle = await getDirectoryHandle(dirname$1);
2172
+ if (!parentHandle) {
2173
+ return undefined;
2174
+ }
2175
+ const baseName = getBaseName(pathSeparator$1, uri);
2176
+ const fileHandle = await getFileHandle$1(parentHandle, baseName, options);
2177
+ return fileHandle;
2178
+ };
2179
+
2180
+ const pathSeparator = '/';
2181
+ const exists$1 = async uri => {
2182
+ const handle = await getHandle(uri);
2183
+ return Boolean(handle);
2184
+ };
2185
+ const getDirent = handle => {
2186
+ const {
2187
+ kind,
2188
+ name
2189
+ } = handle;
2190
+ const type = getDirentType(kind);
2191
+ return {
2192
+ name,
2193
+ type
2194
+ };
2195
+ };
2196
+ const getDirents = handles => {
2197
+ const dirents = handles.map(getDirent);
2198
+ return dirents;
2199
+ };
2200
+ const getChildHandlesFallbackPrompt = async handle => {
2201
+ // TODO cannot prompt without user activation, else error occurs
2202
+ // maybe need to show
2203
+ const permissionTypeNow = await requestPermission(handle, {
2204
+ mode: 'readwrite'
2205
+ });
2206
+ switch (permissionTypeNow) {
2207
+ case Denied:
2208
+ case Prompt:
2209
+ return [];
2210
+ case Granted:
2211
+ return getChildHandles$1(handle);
2212
+ default:
2213
+ return [];
2214
+ }
2215
+ };
2216
+ const getChildHandlesFallback = async handle => {
2217
+ const permissionType = await queryPermission(handle, {
2218
+ mode: 'readwrite'
2219
+ });
2220
+ switch (permissionType) {
2221
+ case Denied:
2222
+ return [];
2223
+ case Granted:
2224
+ throw new VError('invalid state');
2225
+ case Prompt:
2226
+ return await getChildHandlesFallbackPrompt(handle);
2227
+ default:
2228
+ return [];
2229
+ }
2230
+ };
2231
+ const getChildHandles = async handle => {
2232
+ try {
2233
+ return await getChildHandles$1(handle);
2234
+ } catch (error) {
2235
+ if (isNotAllowedError(error)) {
2236
+ return getChildHandlesFallback(handle);
2237
+ }
2238
+ throw new VError(error, 'failed to get child handles');
2239
+ }
2240
+ };
2241
+ const readDirWithFileTypes$1 = async uri => {
2242
+ try {
2243
+ const handle = await getHandle(uri);
2244
+ if (!handle) {
2245
+ throw new Error(`File system handle not found for ${uri}`);
2246
+ }
2247
+ const childHandles = await getChildHandles(handle);
2248
+ await addHandles(uri, childHandles);
2249
+ const dirents = getDirents(childHandles);
2250
+ return dirents;
2251
+ } catch (error) {
2252
+ throw new VError(error, 'failed to read directory');
2253
+ }
2254
+ };
2255
+ const readFile$1 = async uri => {
2256
+ try {
2257
+ const handle = await getFileHandle(uri);
2258
+ if (!handle) {
2259
+ throw new VError(`File not found ${uri}`);
2260
+ }
2261
+ const file = await getFile(handle);
2262
+ const text = await file.text();
2263
+ return text;
2264
+ } catch (error) {
2265
+ if (isNotFoundError(error)) {
2266
+ throw new FileNotFoundError(uri);
2267
+ }
2268
+ throw new VError(error, 'Failed to read file');
2269
+ }
2270
+ };
2271
+ const writeFile$1 = async (uri, content) => {
2272
+ try {
2273
+ const handle = await getFileHandle(uri, {
2274
+ create: true
2275
+ });
2276
+ if (!handle) {
2277
+ throw new VError(`File not found ${uri}`);
2278
+ }
2279
+ await write(handle, content);
2280
+ } catch (error) {
2281
+ throw new VError(error, 'Failed to save file');
2282
+ }
2283
+ };
2284
+ const writeBlob$1 = async (uri, blob) => {
2285
+ try {
2286
+ const handle = await getFileHandle(uri, {
2287
+ create: true
2288
+ });
2289
+ if (!handle) {
2290
+ throw new VError(`File not found ${uri}`);
2291
+ }
2292
+ await write(handle, blob);
2293
+ } catch (error) {
2294
+ throw new VError(error, 'Failed to save file');
2295
+ }
2296
+ };
2297
+ const remove$1 = async uri => {
2298
+ try {
2299
+ const dirname$1 = dirname(pathSeparator, uri);
2300
+ const parentHandle = await getDirectoryHandle(dirname$1);
2301
+ if (!parentHandle) {
2302
+ throw new FileNotFoundError(uri);
2303
+ }
2304
+ const existingHandle = await getHandle(uri);
2305
+ const baseName = getBaseName(pathSeparator, uri);
2306
+ if (existingHandle?.kind === 'directory') {
2307
+ await parentHandle.removeEntry(baseName, {
2308
+ recursive: true
2309
+ });
2310
+ } else {
2311
+ await parentHandle.removeEntry(baseName);
2312
+ }
2313
+ removeHandle(uri);
2314
+ } catch (error) {
2315
+ if (error instanceof FileNotFoundError || isNotFoundError(error)) {
2316
+ throw new FileNotFoundError(uri);
2317
+ }
2318
+ throw new VError(error, 'Failed to remove');
2319
+ }
2320
+ };
2321
+ const ensureDirectoryHandle = async uri => {
2322
+ const existingHandle = await getHandle(uri);
2323
+ if (existingHandle) {
2324
+ if (existingHandle.kind !== 'directory') {
2325
+ throw new VError(`Expected directory at ${uri}`);
2326
+ }
2327
+ return existingHandle;
2328
+ }
2329
+ const dirname$1 = dirname(pathSeparator, uri);
2330
+ if (uri === dirname$1) {
2331
+ throw new VError(`Directory handle not found for ${uri}`);
2332
+ }
2333
+ let parentHandle = await getDirectoryHandle(dirname$1);
2334
+ if (!parentHandle) {
2335
+ parentHandle = await ensureDirectoryHandle(dirname$1);
2336
+ }
2337
+ const baseName = getBaseName(pathSeparator, uri);
2338
+ const directoryHandle = await parentHandle.getDirectoryHandle(baseName, {
2339
+ create: true
2340
+ });
2341
+ await addHandle(uri, directoryHandle);
2342
+ return directoryHandle;
2343
+ };
2344
+ const mkdir$1 = async uri => {
2345
+ try {
2346
+ await ensureDirectoryHandle(uri);
2347
+ } catch (error) {
2348
+ throw new VError(error, 'Failed to create directory');
2349
+ }
2350
+ };
2351
+ const isReadonly$1 = async uri => {
2352
+ const handle = await getHandle(uri);
2353
+ return Boolean(handle && 'readonly' in handle && handle.readonly);
2354
+ };
2355
+ const getBlob = async uri => {
2356
+ const handle = await getFileHandle(uri);
2357
+ if (!handle) {
2358
+ throw new Error(`file not found`);
2359
+ }
2360
+ const file = await getFile(handle);
2361
+ // TODO convert handle to blob mime type?
2362
+ return file;
1916
2363
  };
1917
2364
 
1918
2365
  const isFetch = uri => {
@@ -1938,29 +2385,31 @@ const isProviderUri = uri => {
1938
2385
  };
1939
2386
 
1940
2387
  const remove = async dirent => {
2388
+ if (isHtml(dirent)) return remove$1(dirent);
1941
2389
  if (isMemory(dirent)) {
1942
- return remove$2(dirent);
2390
+ return remove$3(dirent);
1943
2391
  }
1944
2392
  if (isProviderUri(dirent)) {
1945
2393
  return invoke$2('FileSystem.remove', dirent);
1946
2394
  }
1947
- return remove$3(dirent);
2395
+ return remove$4(dirent);
1948
2396
  };
1949
2397
  const readFile = async uri => {
2398
+ if (isHtml(uri)) return readFile$1(uri);
1950
2399
  if (uri.startsWith('untitled:')) return '';
1951
- if (isFetch(uri) || isHtml(uri)) {
2400
+ if (isFetch(uri)) {
1952
2401
  return invoke$2('FileSystem.readFile', uri);
1953
2402
  }
1954
2403
  if (isHttp(uri)) {
1955
- return readFile$1(uri);
2404
+ return readFile$2(uri);
1956
2405
  }
1957
2406
  if (isMemory(uri)) {
1958
- return readFile$2(uri);
2407
+ return readFile$3(uri);
1959
2408
  }
1960
2409
  if (isProviderUri(uri)) {
1961
2410
  return invoke$2('FileSystem.readFile', uri);
1962
2411
  }
1963
- return readFile$3(uri);
2412
+ return readFile$4(uri);
1964
2413
  };
1965
2414
  const getFileHash = async uri => {
1966
2415
  return getFileHash$1(uri);
@@ -1972,21 +2421,24 @@ const appendFile = async (uri, text) => {
1972
2421
  return appendFile$1(uri, text);
1973
2422
  };
1974
2423
  const readDirWithFileTypes = async uri => {
1975
- if (isFetch(uri) || isHtml(uri)) {
2424
+ if (isHtml(uri)) return readDirWithFileTypes$1(uri);
2425
+ if (isFetch(uri)) {
1976
2426
  return invoke$2('FileSystem.readDirWithFileTypes', uri);
1977
2427
  }
1978
2428
  if (isMemory(uri)) {
1979
- return readDirWithFileTypes$2(uri);
2429
+ return readDirWithFileTypes$3(uri);
1980
2430
  }
1981
2431
  if (isProviderUri(uri)) {
1982
2432
  return invoke$2('FileSystem.readDirWithFileTypes', uri);
1983
2433
  }
1984
- return readDirWithFileTypes$3(uri);
2434
+ return readDirWithFileTypes$4(uri);
1985
2435
  };
1986
2436
  const isReadonly = async uri => {
2437
+ if (isHtml(uri)) return isReadonly$1(uri);
1987
2438
  return invoke$1('FileSystem.isReadonly', uri);
1988
2439
  };
1989
2440
  const readJson = async uri => {
2441
+ if (isHtml(uri)) return JSON.parse(await readFile$1(uri));
1990
2442
  if (isHttp(uri)) {
1991
2443
  return readJson$1(uri);
1992
2444
  }
@@ -2006,6 +2458,7 @@ const getFileSize = async uri => {
2006
2458
  return invoke$1('FileSystem.getFileSize', uri);
2007
2459
  };
2008
2460
  const readFileAsBlob = async uri => {
2461
+ if (isHtml(uri)) return getBlob(uri);
2009
2462
  if (isHttp(uri)) {
2010
2463
  return readFileAsBlob$1(uri);
2011
2464
  }
@@ -2032,31 +2485,34 @@ const stat = async dirent => {
2032
2485
  return stat$3(dirent);
2033
2486
  };
2034
2487
  const exists = async uri => {
2035
- if (isFetch(uri) || isHtml(uri) || isProviderUri(uri)) {
2488
+ if (isHtml(uri)) return exists$1(uri);
2489
+ if (isMemory(uri)) {
2490
+ return exists$3(uri);
2491
+ }
2492
+ if (isFetch(uri) || isProviderUri(uri)) {
2036
2493
  return invoke$2('FileSystem.exists', uri);
2037
2494
  }
2038
2495
  if (isHttp(uri)) {
2039
- return exists$1(uri);
2040
- }
2041
- if (isMemory(uri)) {
2042
2496
  return exists$2(uri);
2043
2497
  }
2044
- return exists$3(uri);
2498
+ return exists$4(uri);
2045
2499
  };
2046
2500
  const createFile = async uri => {
2047
2501
  if (isMemory(uri)) {
2048
2502
  return createFile$2(uri);
2049
2503
  }
2050
- return writeFile$3(uri, '');
2504
+ if (isHtml(uri)) return writeFile$1(uri, '');
2505
+ return writeFile$4(uri, '');
2051
2506
  };
2052
2507
  const writeFile = async (uri, content) => {
2508
+ if (isHtml(uri)) return writeFile$1(uri, content);
2053
2509
  if (isMemory(uri)) {
2054
- return writeFile$2(uri, content);
2510
+ return writeFile$3(uri, content);
2055
2511
  }
2056
2512
  if (isProviderUri(uri)) {
2057
2513
  return invoke$2('FileSystem.writeFile', uri, content);
2058
2514
  }
2059
- return writeFile$3(uri, content);
2515
+ return writeFile$4(uri, content);
2060
2516
  };
2061
2517
  const getBytes = async blob => {
2062
2518
  if (blob.bytes) {
@@ -2067,16 +2523,18 @@ const getBytes = async blob => {
2067
2523
  return bytes;
2068
2524
  };
2069
2525
  const writeBlob = async (uri, blob) => {
2526
+ if (isHtml(uri)) return writeBlob$1(uri, blob);
2070
2527
  const bytes = await getBytes(blob);
2071
2528
  // @ts-ignore
2072
2529
  await invoke$1('FileSystem.writeBuffer', uri, bytes);
2073
2530
  };
2074
2531
  const mkdir = async uri => {
2532
+ if (isHtml(uri)) return mkdir$1(uri);
2075
2533
  if (isMemory(uri)) {
2076
- await mkdir$2(uri);
2534
+ await mkdir$3(uri);
2077
2535
  return;
2078
2536
  }
2079
- return mkdir$3(uri);
2537
+ return mkdir$4(uri);
2080
2538
  };
2081
2539
  const rename = async (oldUri, newUri) => {
2082
2540
  if (isMemory(oldUri) || isMemory(newUri)) {
@@ -2365,6 +2823,87 @@ const glob = async (root, pattern) => {
2365
2823
  return globWithFileSystem(FileSystemDisk, root, pattern);
2366
2824
  };
2367
2825
 
2826
+ const FILE_RESULT = 1;
2827
+ const MATCH_RESULT = 2;
2828
+ const USE_REGULAR_EXPRESSION = 1 << 1;
2829
+ const MATCH_WHOLE_WORD = 1 << 3;
2830
+ const MATCH_CASE = 1 << 4;
2831
+ const getLineMatch = (line, lineNumber, query, flags) => {
2832
+ if (flags & USE_REGULAR_EXPRESSION) {
2833
+ const regex = new RegExp(query, flags & MATCH_CASE ? '' : 'i');
2834
+ const match = line.match(regex);
2835
+ return match && typeof match.index === 'number' ? [{
2836
+ end: match.index + match[0].length,
2837
+ lineNumber,
2838
+ start: match.index,
2839
+ text: line,
2840
+ type: MATCH_RESULT
2841
+ }] : [];
2842
+ }
2843
+ const source = flags & MATCH_CASE ? line : line.toLowerCase();
2844
+ const needle = flags & MATCH_CASE ? query : query.toLowerCase();
2845
+ const index = source.indexOf(needle);
2846
+ if (index === -1) {
2847
+ return [];
2848
+ }
2849
+ if (flags & MATCH_WHOLE_WORD) {
2850
+ const before = line[index - 1];
2851
+ const after = line[index + query.length];
2852
+ if (before && /[\p{L}\p{N}_]/u.test(before) || after && /[\p{L}\p{N}_]/u.test(after)) {
2853
+ return [];
2854
+ }
2855
+ }
2856
+ return [{
2857
+ end: index + query.length,
2858
+ lineNumber,
2859
+ start: index,
2860
+ text: line,
2861
+ type: MATCH_RESULT
2862
+ }];
2863
+ };
2864
+ const searchText = (file, content, query, flags = 0) => {
2865
+ const matches = content.split(/\r?\n/).flatMap((line, index) => getLineMatch(line, index, query, flags));
2866
+ return matches.length === 0 ? [] : [{
2867
+ end: 0,
2868
+ lineNumber: 0,
2869
+ start: 0,
2870
+ text: file,
2871
+ type: FILE_RESULT
2872
+ }, ...matches];
2873
+ };
2874
+ const searchHtmlDirectory = async (uri, relativePath, query, flags) => {
2875
+ const entries = await readDirWithFileTypes$1(uri);
2876
+ const results = [];
2877
+ for (const entry of entries) {
2878
+ const childUri = `${uri}/${entry.name}`;
2879
+ const childRelativePath = relativePath ? `${relativePath}/${entry.name}` : entry.name;
2880
+ if (entry.type === Directory$1) {
2881
+ results.push(...(await searchHtmlDirectory(childUri, childRelativePath, query, flags)));
2882
+ } else {
2883
+ const content = await readFile$1(childUri);
2884
+ results.push(...searchText(childRelativePath, content, query, flags));
2885
+ }
2886
+ }
2887
+ return results;
2888
+ };
2889
+ const textSearch = async (root, query, options = {}) => {
2890
+ return searchHtmlDirectory(root, '', query, options.flags || 0);
2891
+ };
2892
+ const searchDirectory = async (uri, prefix = '') => {
2893
+ const entries = await readDirWithFileTypes$1(uri);
2894
+ const results = [];
2895
+ for (const entry of entries) {
2896
+ const relativePath = prefix ? `${prefix}/${entry.name}` : entry.name;
2897
+ if (entry.type === Directory$1) {
2898
+ results.push(...(await searchDirectory(`${uri}/${entry.name}`, relativePath)));
2899
+ } else {
2900
+ results.push(relativePath);
2901
+ }
2902
+ }
2903
+ return results;
2904
+ };
2905
+ const fileSearch = uri => searchDirectory(uri);
2906
+
2368
2907
  const handleMessagePort = async (port, rpcId) => {
2369
2908
  const rpc = await create$6({
2370
2909
  commandMap: {},
@@ -2468,54 +3007,13 @@ const initialize = async platform => {
2468
3007
  await initializeFileSystemProcess(platform);
2469
3008
  };
2470
3009
 
2471
- const Directory = 'directory';
2472
- const File$1 = 'file';
2473
-
2474
- const {
2475
- invoke} = createLazyRpc(RendererProcess);
2476
-
2477
- /**
2478
- * Do not use directly, use FileSystemHtml.getChildHandles
2479
- * instead which prompts for the required permission to
2480
- * retrieve the child handles
2481
- */
2482
- const getChildHandles = async handle => {
2483
- object(handle);
2484
- // @ts-ignore - values() exists on FileSystemDirectoryHandle but TypeScript types may not include it
2485
- const handles = await Array.fromAsync(handle.values());
2486
- return handles;
2487
- };
2488
-
2489
3010
  const uploadDirectory = async (fileSystemHandle, pathSeparator, root, uploadHandles) => {
2490
3011
  const folderPath = root + pathSeparator + fileSystemHandle.name;
2491
3012
  await mkdir(folderPath);
2492
- const childHandles = await getChildHandles(fileSystemHandle);
3013
+ const childHandles = await getChildHandles$1(fileSystemHandle);
2493
3014
  await uploadHandles(childHandles, pathSeparator, folderPath);
2494
3015
  };
2495
3016
 
2496
- const getBinaryString$1 = async file => {
2497
- const bytes = new Uint8Array(await file.arrayBuffer());
2498
- const chunks = [];
2499
- const chunkSize = 32_768;
2500
- for (let i = 0; i < bytes.length; i += chunkSize) {
2501
- chunks.push(String.fromCodePoint(...bytes.subarray(i, i + chunkSize)));
2502
- }
2503
- return chunks.join('');
2504
- };
2505
-
2506
- const getFile = handle => {
2507
- return handle.getFile();
2508
- };
2509
- const getBinaryString = async handle => {
2510
- const file = await getFile(handle);
2511
- const text = await getBinaryString$1(file);
2512
- return text;
2513
- };
2514
-
2515
- const join = (pathSeparator, ...parts) => {
2516
- return parts.join(pathSeparator);
2517
- };
2518
-
2519
3017
  const uploadFile = async (fileSystemHandle, pathSeparator, root) => {
2520
3018
  const content = await getBinaryString(fileSystemHandle);
2521
3019
  const to = join(pathSeparator, root, fileSystemHandle.name);
@@ -2549,7 +3047,7 @@ const uploadFileSystemHandles = async (root, pathSeparator, fileSystemHandles) =
2549
3047
  name
2550
3048
  } = file;
2551
3049
  if (kind === Directory) {
2552
- await invoke('PersistentFileHandle.addHandle', `/${name}`, file);
3050
+ await addHandle(`html:///${name}`, file);
2553
3051
  await invoke('Workspace.setPath', `html:///${name}`);
2554
3052
  return true;
2555
3053
  }
@@ -2589,8 +3087,13 @@ const commandMap = {
2589
3087
  'FileSystem.watchFile': watchFile,
2590
3088
  'FileSystem.writeBlob': writeBlob,
2591
3089
  'FileSystem.writeFile': writeFile,
3090
+ 'FileSystemHtml.fileSearch': fileSearch,
3091
+ 'FileSystemHtml.textSearch': textSearch,
2592
3092
  'FileSystemMemory.getFiles': getFiles,
2593
- 'Initialize.initialize': initialize
3093
+ 'Initialize.initialize': initialize,
3094
+ 'PersistentFileHandle.addHandle': addHandle,
3095
+ 'PersistentFileHandle.getHandle': getHandle,
3096
+ 'PersistentFileHandle.removeHandle': removeHandle
2594
3097
  };
2595
3098
 
2596
3099
  const CommandMap = {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@lvce-editor/file-system-worker",
3
- "version": "5.20.3",
3
+ "version": "5.21.0",
4
4
  "description": "File System Worker",
5
5
  "keywords": [
6
6
  "Lvce Editor"