typescript-virtual-container 1.2.9 → 1.3.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.
Files changed (281) hide show
  1. package/.vscode/settings.json +0 -1
  2. package/README.md +141 -50
  3. package/biome.json +7 -0
  4. package/dist/SSHMimic/exec.d.ts.map +1 -1
  5. package/dist/SSHMimic/executor.d.ts.map +1 -1
  6. package/dist/SSHMimic/executor.js +32 -16
  7. package/dist/SSHMimic/index.d.ts.map +1 -1
  8. package/dist/SSHMimic/index.js +20 -6
  9. package/dist/VirtualFileSystem/binaryPack.d.ts.map +1 -1
  10. package/dist/VirtualFileSystem/binaryPack.js +29 -6
  11. package/dist/VirtualFileSystem/index.d.ts.map +1 -1
  12. package/dist/VirtualFileSystem/index.js +36 -13
  13. package/dist/VirtualPackageManager/index.d.ts.map +1 -1
  14. package/dist/VirtualPackageManager/index.js +192 -43
  15. package/dist/VirtualShell/index.d.ts +10 -4
  16. package/dist/VirtualShell/index.d.ts.map +1 -1
  17. package/dist/VirtualShell/index.js +18 -7
  18. package/dist/VirtualShell/shell.d.ts.map +1 -1
  19. package/dist/VirtualShell/shell.js +3 -1
  20. package/dist/VirtualShell/shellParser.d.ts.map +1 -1
  21. package/dist/VirtualUserManager/index.d.ts.map +1 -1
  22. package/dist/commands/adduser.d.ts +6 -0
  23. package/dist/commands/adduser.d.ts.map +1 -1
  24. package/dist/commands/adduser.js +6 -0
  25. package/dist/commands/alias.d.ts +5 -0
  26. package/dist/commands/alias.d.ts.map +1 -1
  27. package/dist/commands/alias.js +5 -0
  28. package/dist/commands/apt.d.ts +5 -0
  29. package/dist/commands/apt.d.ts.map +1 -1
  30. package/dist/commands/apt.js +32 -9
  31. package/dist/commands/awk.d.ts +11 -0
  32. package/dist/commands/awk.d.ts.map +1 -1
  33. package/dist/commands/awk.js +15 -2
  34. package/dist/commands/base64.d.ts +5 -0
  35. package/dist/commands/base64.d.ts.map +1 -1
  36. package/dist/commands/base64.js +9 -1
  37. package/dist/commands/cat.d.ts +5 -0
  38. package/dist/commands/cat.d.ts.map +1 -1
  39. package/dist/commands/cat.js +10 -2
  40. package/dist/commands/cd.d.ts +5 -0
  41. package/dist/commands/cd.d.ts.map +1 -1
  42. package/dist/commands/cd.js +5 -0
  43. package/dist/commands/chmod.d.ts +5 -0
  44. package/dist/commands/chmod.d.ts.map +1 -1
  45. package/dist/commands/chmod.js +5 -0
  46. package/dist/commands/cp.d.ts +5 -0
  47. package/dist/commands/cp.d.ts.map +1 -1
  48. package/dist/commands/cp.js +5 -0
  49. package/dist/commands/curl.d.ts +5 -0
  50. package/dist/commands/curl.d.ts.map +1 -1
  51. package/dist/commands/curl.js +34 -6
  52. package/dist/commands/cut.d.ts +5 -0
  53. package/dist/commands/cut.d.ts.map +1 -1
  54. package/dist/commands/cut.js +8 -1
  55. package/dist/commands/date.d.ts +5 -0
  56. package/dist/commands/date.d.ts.map +1 -1
  57. package/dist/commands/date.js +7 -1
  58. package/dist/commands/declare.d.ts +3 -0
  59. package/dist/commands/declare.d.ts.map +1 -0
  60. package/dist/commands/declare.js +39 -0
  61. package/dist/commands/diff.d.ts +5 -0
  62. package/dist/commands/diff.d.ts.map +1 -1
  63. package/dist/commands/diff.js +5 -0
  64. package/dist/commands/dpkg.d.ts +5 -0
  65. package/dist/commands/dpkg.d.ts.map +1 -1
  66. package/dist/commands/dpkg.js +24 -7
  67. package/dist/commands/du.d.ts.map +1 -1
  68. package/dist/commands/du.js +8 -2
  69. package/dist/commands/echo.d.ts +5 -0
  70. package/dist/commands/echo.d.ts.map +1 -1
  71. package/dist/commands/echo.js +13 -4
  72. package/dist/commands/env.d.ts +5 -0
  73. package/dist/commands/env.d.ts.map +1 -1
  74. package/dist/commands/env.js +11 -1
  75. package/dist/commands/exit.d.ts +5 -0
  76. package/dist/commands/exit.d.ts.map +1 -1
  77. package/dist/commands/exit.js +12 -2
  78. package/dist/commands/export.d.ts.map +1 -1
  79. package/dist/commands/export.js +3 -1
  80. package/dist/commands/find.d.ts +5 -0
  81. package/dist/commands/find.d.ts.map +1 -1
  82. package/dist/commands/find.js +5 -0
  83. package/dist/commands/free.d.ts +5 -0
  84. package/dist/commands/free.d.ts.map +1 -1
  85. package/dist/commands/free.js +5 -0
  86. package/dist/commands/grep.d.ts +5 -0
  87. package/dist/commands/grep.d.ts.map +1 -1
  88. package/dist/commands/grep.js +12 -2
  89. package/dist/commands/gzip.d.ts +5 -0
  90. package/dist/commands/gzip.d.ts.map +1 -1
  91. package/dist/commands/gzip.js +18 -2
  92. package/dist/commands/head.d.ts +5 -0
  93. package/dist/commands/head.d.ts.map +1 -1
  94. package/dist/commands/head.js +5 -0
  95. package/dist/commands/help.d.ts.map +1 -1
  96. package/dist/commands/help.js +98 -45
  97. package/dist/commands/history.d.ts +5 -0
  98. package/dist/commands/history.d.ts.map +1 -1
  99. package/dist/commands/history.js +5 -0
  100. package/dist/commands/hostname.d.ts +5 -0
  101. package/dist/commands/hostname.d.ts.map +1 -1
  102. package/dist/commands/hostname.js +5 -0
  103. package/dist/commands/id.d.ts.map +1 -1
  104. package/dist/commands/id.js +4 -1
  105. package/dist/commands/index.d.ts +2 -17
  106. package/dist/commands/index.d.ts.map +1 -1
  107. package/dist/commands/index.js +2 -340
  108. package/dist/commands/ls.d.ts.map +1 -1
  109. package/dist/commands/ls.js +3 -1
  110. package/dist/commands/lsb-release.d.ts.map +1 -1
  111. package/dist/commands/lsb-release.js +8 -2
  112. package/dist/commands/nano.js +1 -1
  113. package/dist/commands/neofetch.js +1 -1
  114. package/dist/commands/node.d.ts +9 -0
  115. package/dist/commands/node.d.ts.map +1 -0
  116. package/dist/commands/node.js +316 -0
  117. package/dist/commands/npm.d.ts +19 -0
  118. package/dist/commands/npm.d.ts.map +1 -0
  119. package/dist/commands/npm.js +109 -0
  120. package/dist/commands/ping.d.ts.map +1 -1
  121. package/dist/commands/ping.js +3 -1
  122. package/dist/commands/printf.d.ts +3 -0
  123. package/dist/commands/printf.d.ts.map +1 -0
  124. package/dist/commands/printf.js +113 -0
  125. package/dist/commands/ps.d.ts.map +1 -1
  126. package/dist/commands/ps.js +4 -1
  127. package/dist/commands/python.d.ts +30 -0
  128. package/dist/commands/python.d.ts.map +1 -0
  129. package/dist/commands/python.js +2058 -0
  130. package/dist/commands/read.d.ts +3 -0
  131. package/dist/commands/read.d.ts.map +1 -0
  132. package/dist/commands/read.js +34 -0
  133. package/dist/commands/registry.d.ts +8 -0
  134. package/dist/commands/registry.d.ts.map +1 -0
  135. package/dist/commands/registry.js +229 -0
  136. package/dist/commands/runtime.d.ts +6 -0
  137. package/dist/commands/runtime.d.ts.map +1 -0
  138. package/dist/commands/runtime.js +280 -0
  139. package/dist/commands/sed.d.ts.map +1 -1
  140. package/dist/commands/sed.js +11 -3
  141. package/dist/commands/set.d.ts.map +1 -1
  142. package/dist/commands/set.js +9 -3
  143. package/dist/commands/sh.d.ts.map +1 -1
  144. package/dist/commands/sh.js +57 -36
  145. package/dist/commands/shift.d.ts +5 -0
  146. package/dist/commands/shift.d.ts.map +1 -0
  147. package/dist/commands/shift.js +52 -0
  148. package/dist/commands/sleep.d.ts.map +1 -1
  149. package/dist/commands/sort.d.ts.map +1 -1
  150. package/dist/commands/sort.js +4 -2
  151. package/dist/commands/source.d.ts.map +1 -1
  152. package/dist/commands/source.js +5 -2
  153. package/dist/commands/sudo.js +1 -1
  154. package/dist/commands/tar.d.ts.map +1 -1
  155. package/dist/commands/tar.js +11 -3
  156. package/dist/commands/tee.d.ts.map +1 -1
  157. package/dist/commands/tee.js +8 -6
  158. package/dist/commands/test.d.ts.map +1 -1
  159. package/dist/commands/test.js +46 -24
  160. package/dist/commands/tr.d.ts.map +1 -1
  161. package/dist/commands/tr.js +3 -1
  162. package/dist/commands/true.d.ts +4 -0
  163. package/dist/commands/true.d.ts.map +1 -0
  164. package/dist/commands/true.js +14 -0
  165. package/dist/commands/type.d.ts.map +1 -1
  166. package/dist/commands/type.js +1 -1
  167. package/dist/commands/uname.d.ts.map +1 -1
  168. package/dist/commands/uname.js +4 -1
  169. package/dist/commands/uniq.d.ts.map +1 -1
  170. package/dist/commands/uptime.d.ts.map +1 -1
  171. package/dist/commands/uptime.js +4 -1
  172. package/dist/commands/wget.d.ts.map +1 -1
  173. package/dist/commands/wget.js +32 -7
  174. package/dist/commands/which.d.ts.map +1 -1
  175. package/dist/commands/xargs.d.ts.map +1 -1
  176. package/dist/commands/xargs.js +1 -1
  177. package/dist/index.d.ts +15 -14
  178. package/dist/index.d.ts.map +1 -1
  179. package/dist/index.js +9 -9
  180. package/dist/modules/linuxRootfs.d.ts +18 -1
  181. package/dist/modules/linuxRootfs.d.ts.map +1 -1
  182. package/dist/modules/linuxRootfs.js +160 -17
  183. package/dist/standalone-wo-sftp.d.ts +2 -0
  184. package/dist/standalone-wo-sftp.d.ts.map +1 -0
  185. package/dist/standalone-wo-sftp.js +30 -0
  186. package/dist/utils/expand.d.ts +50 -0
  187. package/dist/utils/expand.d.ts.map +1 -0
  188. package/dist/utils/expand.js +183 -0
  189. package/dist/utils/vfsDiff.d.ts +90 -0
  190. package/dist/utils/vfsDiff.d.ts.map +1 -0
  191. package/dist/utils/vfsDiff.js +177 -0
  192. package/package.json +2 -1
  193. package/src/SSHMimic/exec.ts +10 -1
  194. package/src/SSHMimic/executor.ts +104 -18
  195. package/src/SSHMimic/index.ts +49 -15
  196. package/src/VirtualFileSystem/binaryPack.ts +35 -8
  197. package/src/VirtualFileSystem/index.ts +78 -28
  198. package/src/VirtualPackageManager/index.ts +208 -49
  199. package/src/VirtualShell/index.ts +35 -7
  200. package/src/VirtualShell/shell.ts +23 -3
  201. package/src/VirtualShell/shellParser.ts +134 -36
  202. package/src/VirtualUserManager/index.ts +7 -2
  203. package/src/commands/adduser.ts +6 -0
  204. package/src/commands/alias.ts +5 -1
  205. package/src/commands/apt.ts +47 -17
  206. package/src/commands/awk.ts +20 -6
  207. package/src/commands/base64.ts +13 -2
  208. package/src/commands/cat.ts +13 -5
  209. package/src/commands/cd.ts +5 -0
  210. package/src/commands/chmod.ts +5 -0
  211. package/src/commands/cp.ts +5 -0
  212. package/src/commands/curl.ts +56 -12
  213. package/src/commands/cut.ts +8 -1
  214. package/src/commands/date.ts +7 -1
  215. package/src/commands/declare.ts +44 -0
  216. package/src/commands/diff.ts +17 -3
  217. package/src/commands/dpkg.ts +33 -11
  218. package/src/commands/du.ts +17 -5
  219. package/src/commands/echo.ts +22 -9
  220. package/src/commands/env.ts +11 -1
  221. package/src/commands/exit.ts +12 -2
  222. package/src/commands/export.ts +3 -1
  223. package/src/commands/find.ts +5 -0
  224. package/src/commands/free.ts +9 -2
  225. package/src/commands/grep.ts +12 -2
  226. package/src/commands/gzip.ts +28 -4
  227. package/src/commands/head.ts +5 -0
  228. package/src/commands/help.ts +121 -47
  229. package/src/commands/history.ts +7 -2
  230. package/src/commands/hostname.ts +5 -0
  231. package/src/commands/id.ts +4 -1
  232. package/src/commands/index.ts +9 -360
  233. package/src/commands/ls.ts +5 -3
  234. package/src/commands/lsb-release.ts +8 -2
  235. package/src/commands/nano.ts +1 -1
  236. package/src/commands/neofetch.ts +1 -1
  237. package/src/commands/node.ts +341 -0
  238. package/src/commands/npm.ts +132 -0
  239. package/src/commands/ping.ts +6 -2
  240. package/src/commands/printf.ts +112 -0
  241. package/src/commands/ps.ts +21 -9
  242. package/src/commands/python.ts +2229 -0
  243. package/src/commands/read.ts +41 -0
  244. package/src/commands/registry.ts +244 -0
  245. package/src/commands/runtime.ts +353 -0
  246. package/src/commands/sed.ts +27 -9
  247. package/src/commands/set.ts +9 -3
  248. package/src/commands/sh.ts +159 -55
  249. package/src/commands/shift.ts +53 -0
  250. package/src/commands/sleep.ts +2 -1
  251. package/src/commands/sort.ts +10 -6
  252. package/src/commands/source.ts +15 -3
  253. package/src/commands/sudo.ts +1 -1
  254. package/src/commands/tar.ts +28 -7
  255. package/src/commands/tee.ts +7 -1
  256. package/src/commands/test.ts +61 -26
  257. package/src/commands/tr.ts +3 -1
  258. package/src/commands/true.ts +17 -0
  259. package/src/commands/type.ts +6 -3
  260. package/src/commands/uname.ts +5 -1
  261. package/src/commands/uniq.ts +8 -2
  262. package/src/commands/uptime.ts +4 -1
  263. package/src/commands/wget.ts +51 -12
  264. package/src/commands/which.ts +5 -2
  265. package/src/commands/xargs.ts +11 -2
  266. package/src/index.ts +23 -24
  267. package/src/modules/linuxRootfs.ts +233 -30
  268. package/src/standalone-wo-sftp.ts +38 -0
  269. package/src/utils/expand.ts +238 -0
  270. package/src/utils/vfsDiff.ts +275 -0
  271. package/standalone-wo-sftp.js +507 -0
  272. package/standalone-wo-sftp.js.map +7 -0
  273. package/standalone.js +253 -191
  274. package/standalone.js.map +4 -4
  275. package/tests/bun-test-shim.ts +9 -1
  276. package/tests/command-helpers.test.ts +1 -5
  277. package/tests/new-features.test.ts +415 -5
  278. package/tests/parser-executor.test.ts +27 -27
  279. package/tests/sftp.test.ts +122 -42
  280. package/tests/users.test.ts +23 -5
  281. package/CHANGELOG.md +0 -150
@@ -31,19 +31,25 @@
31
31
  * Binary pack : ~1.00 MB + ~40 bytes/node header → ~27% smaller, no string parsing
32
32
  */
33
33
 
34
- import type { InternalDirectoryNode, InternalFileNode, InternalNode } from "./internalTypes";
34
+ import type {
35
+ InternalDirectoryNode,
36
+ InternalFileNode,
37
+ InternalNode,
38
+ } from "./internalTypes";
35
39
 
36
40
  const MAGIC = Buffer.from([0x56, 0x46, 0x53, 0x21]); // "VFS!"
37
41
  const VERSION = 0x01;
38
42
  const TYPE_FILE = 0x01;
39
- const TYPE_DIR = 0x02;
43
+ const TYPE_DIR = 0x02;
40
44
 
41
45
  // ── Encoder ───────────────────────────────────────────────────────────────────
42
46
 
43
47
  class Encoder {
44
48
  private chunks: Buffer[] = [];
45
49
 
46
- write(buf: Buffer): void { this.chunks.push(buf); }
50
+ write(buf: Buffer): void {
51
+ this.chunks.push(buf);
52
+ }
47
53
 
48
54
  writeUint8(n: number): void {
49
55
  const b = Buffer.allocUnsafe(1);
@@ -80,7 +86,9 @@ class Encoder {
80
86
  this.chunks.push(bytes);
81
87
  }
82
88
 
83
- toBuffer(): Buffer { return Buffer.concat(this.chunks); }
89
+ toBuffer(): Buffer {
90
+ return Buffer.concat(this.chunks);
91
+ }
84
92
  }
85
93
 
86
94
  function encodeNode(enc: Encoder, node: InternalNode): void {
@@ -124,7 +132,9 @@ class Decoder {
124
132
  private pos = 0;
125
133
  constructor(private readonly buf: Buffer) {}
126
134
 
127
- readUint8(): number { return this.buf.readUInt8(this.pos++); }
135
+ readUint8(): number {
136
+ return this.buf.readUInt8(this.pos++);
137
+ }
128
138
 
129
139
  readUint16(): number {
130
140
  const v = this.buf.readUInt16LE(this.pos);
@@ -158,7 +168,9 @@ class Decoder {
158
168
  return b;
159
169
  }
160
170
 
161
- remaining(): number { return this.buf.length - this.pos; }
171
+ remaining(): number {
172
+ return this.buf.length - this.pos;
173
+ }
162
174
  }
163
175
 
164
176
  function decodeNode(dec: Decoder): InternalNode {
@@ -171,7 +183,15 @@ function decodeNode(dec: Decoder): InternalNode {
171
183
  if (type === TYPE_FILE) {
172
184
  const compressed = dec.readUint8() === 0x01;
173
185
  const content = dec.readBytes();
174
- return { type: "file", name, mode, createdAt, updatedAt, compressed, content } satisfies InternalFileNode;
186
+ return {
187
+ type: "file",
188
+ name,
189
+ mode,
190
+ createdAt,
191
+ updatedAt,
192
+ compressed,
193
+ content,
194
+ } satisfies InternalFileNode;
175
195
  }
176
196
 
177
197
  if (type === TYPE_DIR) {
@@ -181,7 +201,14 @@ function decodeNode(dec: Decoder): InternalNode {
181
201
  const child = decodeNode(dec);
182
202
  children.set(child.name, child);
183
203
  }
184
- return { type: "directory", name, mode, createdAt, updatedAt, children } satisfies InternalDirectoryNode;
204
+ return {
205
+ type: "directory",
206
+ name,
207
+ mode,
208
+ createdAt,
209
+ updatedAt,
210
+ children,
211
+ } satisfies InternalDirectoryNode;
185
212
  }
186
213
 
187
214
  throw new Error(`[VFS binary] Unknown node type: 0x${type.toString(16)}`);
@@ -172,7 +172,9 @@ class VirtualFileSystem extends EventEmitter {
172
172
  // Legacy JSON fallback — auto-migrates on next flushMirror()
173
173
  const snapshot: VfsSnapshot = JSON.parse(raw.toString("utf8"));
174
174
  this.root = this.deserializeDir(snapshot.root, "");
175
- console.info("[VirtualFileSystem] Migrating legacy JSON snapshot to binary format.");
175
+ console.info(
176
+ "[VirtualFileSystem] Migrating legacy JSON snapshot to binary format.",
177
+ );
176
178
  }
177
179
  this.emit("snapshot:restore", { path: this.snapshotFile });
178
180
  } catch (err) {
@@ -220,7 +222,11 @@ class VirtualFileSystem extends EventEmitter {
220
222
  public mkdir(targetPath: string, mode: number = 0o755): void {
221
223
  const normalized = normalizePath(targetPath);
222
224
  const existing = (() => {
223
- try { return getNode(this.root, normalized); } catch { return null; }
225
+ try {
226
+ return getNode(this.root, normalized);
227
+ } catch {
228
+ return null;
229
+ }
224
230
  })();
225
231
  if (existing && existing.type !== "directory") {
226
232
  throw new Error(
@@ -311,7 +317,9 @@ class VirtualFileSystem extends EventEmitter {
311
317
  try {
312
318
  getNode(this.root, normalizePath(targetPath));
313
319
  return true;
314
- } catch { return false; }
320
+ } catch {
321
+ return false;
322
+ }
315
323
  }
316
324
 
317
325
  /** Updates mode bits on a node. */
@@ -327,15 +335,24 @@ class VirtualFileSystem extends EventEmitter {
327
335
  if (node.type === "file") {
328
336
  const f = node as InternalFileNode;
329
337
  return {
330
- type: "file", name, path: normalized, mode: f.mode,
331
- createdAt: f.createdAt, updatedAt: f.updatedAt,
332
- compressed: f.compressed, size: f.content.length,
338
+ type: "file",
339
+ name,
340
+ path: normalized,
341
+ mode: f.mode,
342
+ createdAt: f.createdAt,
343
+ updatedAt: f.updatedAt,
344
+ compressed: f.compressed,
345
+ size: f.content.length,
333
346
  };
334
347
  }
335
348
  const d = node as InternalDirectoryNode;
336
349
  return {
337
- type: "directory", name, path: normalized, mode: d.mode,
338
- createdAt: d.createdAt, updatedAt: d.updatedAt,
350
+ type: "directory",
351
+ name,
352
+ path: normalized,
353
+ mode: d.mode,
354
+ createdAt: d.createdAt,
355
+ updatedAt: d.updatedAt,
339
356
  childrenCount: d.children.size,
340
357
  };
341
358
  }
@@ -355,9 +372,7 @@ class VirtualFileSystem extends EventEmitter {
355
372
  const normalized = normalizePath(dirPath);
356
373
  const node = getNode(this.root, normalized);
357
374
  if (node.type !== "directory") {
358
- throw new Error(
359
- `Cannot render tree for '${dirPath}': not a directory.`,
360
- );
375
+ throw new Error(`Cannot render tree for '${dirPath}': not a directory.`);
361
376
  }
362
377
  const label = dirPath === "/" ? "/" : path.posix.basename(normalized);
363
378
  return this.renderTreeLines(node as InternalDirectoryNode, label);
@@ -375,7 +390,8 @@ class VirtualFileSystem extends EventEmitter {
375
390
  lines.push(`${connector}${name}`);
376
391
  if (child.type === "directory") {
377
392
  const sub = this.renderTreeLines(child as InternalDirectoryNode, "")
378
- .split("\n").slice(1)
393
+ .split("\n")
394
+ .slice(1)
379
395
  .map((l) => `${nextPrefix}${l}`);
380
396
  lines.push(...sub);
381
397
  }
@@ -400,7 +416,8 @@ class VirtualFileSystem extends EventEmitter {
400
416
  /** Compresses a file's content with gzip in place. */
401
417
  public compressFile(targetPath: string): void {
402
418
  const node = getNode(this.root, normalizePath(targetPath));
403
- if (node.type !== "file") throw new Error(`Cannot compress '${targetPath}': not a file.`);
419
+ if (node.type !== "file")
420
+ throw new Error(`Cannot compress '${targetPath}': not a file.`);
404
421
  const f = node as InternalFileNode;
405
422
  if (!f.compressed) {
406
423
  f.content = gzipSync(f.content);
@@ -412,7 +429,8 @@ class VirtualFileSystem extends EventEmitter {
412
429
  /** Decompresses a gzip-compressed file in place. */
413
430
  public decompressFile(targetPath: string): void {
414
431
  const node = getNode(this.root, normalizePath(targetPath));
415
- if (node.type !== "file") throw new Error(`Cannot decompress '${targetPath}': not a file.`);
432
+ if (node.type !== "file")
433
+ throw new Error(`Cannot decompress '${targetPath}': not a file.`);
416
434
  const f = node as InternalFileNode;
417
435
  if (f.compressed) {
418
436
  f.content = gunzipSync(f.content);
@@ -431,18 +449,25 @@ class VirtualFileSystem extends EventEmitter {
431
449
  ? normalizePath(targetPath)
432
450
  : targetPath;
433
451
  const { parent, name } = getParentDirectory(
434
- this.root, normalizedLink, true,
452
+ this.root,
453
+ normalizedLink,
454
+ true,
435
455
  (p) => this.mkdirRecursive(p, 0o755),
436
456
  );
437
457
  const symNode: InternalFileNode = {
438
- type: "file", name,
458
+ type: "file",
459
+ name,
439
460
  content: Buffer.from(normalizedTarget, "utf8"),
440
461
  mode: 0o120777,
441
462
  compressed: false,
442
- createdAt: new Date(), updatedAt: new Date(),
463
+ createdAt: new Date(),
464
+ updatedAt: new Date(),
443
465
  };
444
466
  parent.children.set(name, symNode);
445
- this.emit("symlink:create", { link: normalizedLink, target: normalizedTarget });
467
+ this.emit("symlink:create", {
468
+ link: normalizedLink,
469
+ target: normalizedTarget,
470
+ });
446
471
  }
447
472
 
448
473
  /** Returns true when the path is a symbolic link node. */
@@ -450,7 +475,9 @@ class VirtualFileSystem extends EventEmitter {
450
475
  try {
451
476
  const node = getNode(this.root, normalizePath(targetPath));
452
477
  return node.type === "file" && node.mode === 0o120777;
453
- } catch { return false; }
478
+ } catch {
479
+ return false;
480
+ }
454
481
  }
455
482
 
456
483
  /**
@@ -466,10 +493,14 @@ class VirtualFileSystem extends EventEmitter {
466
493
  const target = (node as InternalFileNode).content.toString("utf8");
467
494
  current = target.startsWith("/")
468
495
  ? target
469
- : normalizePath(path.posix.join(path.posix.dirname(current), target));
496
+ : normalizePath(
497
+ path.posix.join(path.posix.dirname(current), target),
498
+ );
470
499
  continue;
471
500
  }
472
- } catch { break; }
501
+ } catch {
502
+ break;
503
+ }
473
504
  return current;
474
505
  }
475
506
  throw new Error(`Too many levels of symbolic links: ${linkPath}`);
@@ -488,7 +519,12 @@ class VirtualFileSystem extends EventEmitter {
488
519
  );
489
520
  }
490
521
  }
491
- const { parent, name } = getParentDirectory(this.root, normalized, false, () => {});
522
+ const { parent, name } = getParentDirectory(
523
+ this.root,
524
+ normalized,
525
+ false,
526
+ () => {},
527
+ );
492
528
  parent.children.delete(name);
493
529
  this.emit("node:remove", { path: normalized });
494
530
  }
@@ -506,10 +542,16 @@ class VirtualFileSystem extends EventEmitter {
506
542
  }
507
543
  this.mkdirRecursive(path.posix.dirname(toNormalized), 0o755);
508
544
  const { parent: destParent, name: destName } = getParentDirectory(
509
- this.root, toNormalized, false, () => {},
545
+ this.root,
546
+ toNormalized,
547
+ false,
548
+ () => {},
510
549
  );
511
550
  const { parent: srcParent, name: srcName } = getParentDirectory(
512
- this.root, fromNormalized, false, () => {},
551
+ this.root,
552
+ fromNormalized,
553
+ false,
554
+ () => {},
513
555
  );
514
556
  srcParent.children.delete(srcName);
515
557
  node.name = destName;
@@ -538,7 +580,9 @@ class VirtualFileSystem extends EventEmitter {
538
580
  );
539
581
  }
540
582
  return {
541
- type: "directory", name: dir.name, mode: dir.mode,
583
+ type: "directory",
584
+ name: dir.name,
585
+ mode: dir.mode,
542
586
  createdAt: dir.createdAt.toISOString(),
543
587
  updatedAt: dir.updatedAt.toISOString(),
544
588
  children,
@@ -547,7 +591,9 @@ class VirtualFileSystem extends EventEmitter {
547
591
 
548
592
  private serializeFile(file: InternalFileNode): VfsSnapshotFileNode {
549
593
  return {
550
- type: "file", name: file.name, mode: file.mode,
594
+ type: "file",
595
+ name: file.name,
596
+ mode: file.mode,
551
597
  createdAt: file.createdAt.toISOString(),
552
598
  updatedAt: file.updatedAt.toISOString(),
553
599
  compressed: file.compressed,
@@ -588,7 +634,9 @@ class VirtualFileSystem extends EventEmitter {
588
634
  name: string,
589
635
  ): InternalDirectoryNode {
590
636
  const dir: InternalDirectoryNode = {
591
- type: "directory", name, mode: snap.mode,
637
+ type: "directory",
638
+ name,
639
+ mode: snap.mode,
592
640
  createdAt: new Date(snap.createdAt),
593
641
  updatedAt: new Date(snap.updatedAt),
594
642
  children: new Map(),
@@ -597,7 +645,9 @@ class VirtualFileSystem extends EventEmitter {
597
645
  if (child.type === "file") {
598
646
  const f = child as VfsSnapshotFileNode;
599
647
  dir.children.set(f.name, {
600
- type: "file", name: f.name, mode: f.mode,
648
+ type: "file",
649
+ name: f.name,
650
+ mode: f.mode,
601
651
  createdAt: new Date(f.createdAt),
602
652
  updatedAt: new Date(f.updatedAt),
603
653
  compressed: f.compressed,