typescript-virtual-container 1.3.4 → 1.4.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 (368) hide show
  1. package/.vscode/settings.json +0 -1
  2. package/README.md +674 -1504
  3. package/benchmark-results.txt +21 -21
  4. package/builds/self-standalone.js +282 -332
  5. package/builds/self-standalone.js.map +4 -4
  6. package/builds/standalone-wo-sftp.js +218 -282
  7. package/builds/standalone-wo-sftp.js.map +4 -4
  8. package/builds/standalone.js +271 -335
  9. package/builds/standalone.js.map +4 -4
  10. package/builds/web-full-api.min.js +3 -3
  11. package/builds/web-full-api.min.js.map +4 -4
  12. package/builds/web.min.js +2 -2
  13. package/builds/web.min.js.map +4 -4
  14. package/bun.lock +14 -12
  15. package/dist/SSHClient/index.d.ts.map +1 -1
  16. package/dist/SSHClient/index.js +5 -3
  17. package/dist/SSHMimic/executor.d.ts +1 -3
  18. package/dist/SSHMimic/executor.d.ts.map +1 -1
  19. package/dist/SSHMimic/executor.js +20 -22
  20. package/dist/SSHMimic/index.d.ts.map +1 -1
  21. package/dist/SSHMimic/index.js +5 -3
  22. package/dist/SSHMimic/sftp.d.ts.map +1 -1
  23. package/dist/SSHMimic/sftp.js +26 -21
  24. package/dist/VirtualPackageManager/index.d.ts.map +1 -1
  25. package/dist/VirtualPackageManager/index.js +29 -1
  26. package/dist/VirtualShell/shell.d.ts.map +1 -1
  27. package/dist/VirtualShell/shell.js +25 -3
  28. package/dist/VirtualShell/shellParser.d.ts +1 -8
  29. package/dist/VirtualShell/shellParser.d.ts.map +1 -1
  30. package/dist/VirtualShell/shellParser.js +2 -81
  31. package/dist/VirtualUserManager/index.d.ts +7 -1
  32. package/dist/VirtualUserManager/index.d.ts.map +1 -1
  33. package/dist/VirtualUserManager/index.js +47 -16
  34. package/dist/commands/adduser.d.ts +10 -4
  35. package/dist/commands/adduser.d.ts.map +1 -1
  36. package/dist/commands/adduser.js +75 -12
  37. package/dist/commands/alias.d.ts +5 -0
  38. package/dist/commands/alias.d.ts.map +1 -1
  39. package/dist/commands/alias.js +5 -0
  40. package/dist/commands/apt.d.ts +5 -0
  41. package/dist/commands/apt.d.ts.map +1 -1
  42. package/dist/commands/apt.js +5 -0
  43. package/dist/commands/awk.d.ts +10 -8
  44. package/dist/commands/awk.d.ts.map +1 -1
  45. package/dist/commands/awk.js +156 -28
  46. package/dist/commands/cd.d.ts.map +1 -1
  47. package/dist/commands/cd.js +0 -3
  48. package/dist/commands/clear.d.ts +5 -0
  49. package/dist/commands/clear.d.ts.map +1 -1
  50. package/dist/commands/clear.js +5 -0
  51. package/dist/commands/command-helpers.d.ts.map +1 -1
  52. package/dist/commands/command-helpers.js +8 -0
  53. package/dist/commands/curl.d.ts.map +1 -1
  54. package/dist/commands/curl.js +2 -1
  55. package/dist/commands/declare.d.ts +5 -0
  56. package/dist/commands/declare.d.ts.map +1 -1
  57. package/dist/commands/declare.js +5 -0
  58. package/dist/commands/deluser.d.ts +12 -0
  59. package/dist/commands/deluser.d.ts.map +1 -1
  60. package/dist/commands/deluser.js +72 -6
  61. package/dist/commands/df.d.ts +5 -0
  62. package/dist/commands/df.d.ts.map +1 -1
  63. package/dist/commands/df.js +5 -0
  64. package/dist/commands/du.d.ts +5 -0
  65. package/dist/commands/du.d.ts.map +1 -1
  66. package/dist/commands/du.js +5 -0
  67. package/dist/commands/export.d.ts +5 -0
  68. package/dist/commands/export.d.ts.map +1 -1
  69. package/dist/commands/export.js +5 -0
  70. package/dist/commands/grep.d.ts.map +1 -1
  71. package/dist/commands/grep.js +22 -4
  72. package/dist/commands/groups.d.ts +5 -0
  73. package/dist/commands/groups.d.ts.map +1 -1
  74. package/dist/commands/groups.js +5 -0
  75. package/dist/commands/gzip.d.ts +5 -2
  76. package/dist/commands/gzip.d.ts.map +1 -1
  77. package/dist/commands/gzip.js +54 -28
  78. package/dist/commands/head.d.ts.map +1 -1
  79. package/dist/commands/head.js +12 -3
  80. package/dist/commands/htop.d.ts +5 -0
  81. package/dist/commands/htop.d.ts.map +1 -1
  82. package/dist/commands/htop.js +5 -0
  83. package/dist/commands/kill.d.ts +5 -0
  84. package/dist/commands/kill.d.ts.map +1 -1
  85. package/dist/commands/kill.js +5 -0
  86. package/dist/commands/ln.d.ts +2 -0
  87. package/dist/commands/ln.d.ts.map +1 -1
  88. package/dist/commands/ln.js +22 -0
  89. package/dist/commands/ls.d.ts.map +1 -1
  90. package/dist/commands/ls.js +15 -0
  91. package/dist/commands/lsb-release.d.ts +5 -0
  92. package/dist/commands/lsb-release.d.ts.map +1 -1
  93. package/dist/commands/lsb-release.js +5 -0
  94. package/dist/commands/man.d.ts.map +1 -1
  95. package/dist/commands/man.js +30 -136
  96. package/dist/commands/mkdir.d.ts +5 -0
  97. package/dist/commands/mkdir.d.ts.map +1 -1
  98. package/dist/commands/mkdir.js +5 -0
  99. package/dist/commands/mv.d.ts +5 -0
  100. package/dist/commands/mv.d.ts.map +1 -1
  101. package/dist/commands/mv.js +5 -0
  102. package/dist/commands/nano.d.ts +5 -0
  103. package/dist/commands/nano.d.ts.map +1 -1
  104. package/dist/commands/nano.js +5 -0
  105. package/dist/commands/neofetch.d.ts +5 -0
  106. package/dist/commands/neofetch.d.ts.map +1 -1
  107. package/dist/commands/neofetch.js +14 -5
  108. package/dist/commands/passwd.d.ts +8 -0
  109. package/dist/commands/passwd.d.ts.map +1 -1
  110. package/dist/commands/passwd.js +32 -11
  111. package/dist/commands/ping.d.ts +5 -0
  112. package/dist/commands/ping.d.ts.map +1 -1
  113. package/dist/commands/ping.js +5 -0
  114. package/dist/commands/printf.d.ts +5 -0
  115. package/dist/commands/printf.d.ts.map +1 -1
  116. package/dist/commands/printf.js +43 -12
  117. package/dist/commands/ps.d.ts +5 -0
  118. package/dist/commands/ps.d.ts.map +1 -1
  119. package/dist/commands/ps.js +5 -0
  120. package/dist/commands/read.d.ts +5 -0
  121. package/dist/commands/read.d.ts.map +1 -1
  122. package/dist/commands/read.js +5 -0
  123. package/dist/commands/registry.d.ts.map +1 -1
  124. package/dist/commands/registry.js +4 -1
  125. package/dist/commands/rm.d.ts +5 -0
  126. package/dist/commands/rm.d.ts.map +1 -1
  127. package/dist/commands/rm.js +5 -0
  128. package/dist/commands/runtime.d.ts.map +1 -1
  129. package/dist/commands/runtime.js +1 -57
  130. package/dist/commands/sed.d.ts +5 -0
  131. package/dist/commands/sed.d.ts.map +1 -1
  132. package/dist/commands/sed.js +5 -0
  133. package/dist/commands/set.d.ts +5 -6
  134. package/dist/commands/set.d.ts.map +1 -1
  135. package/dist/commands/set.js +5 -22
  136. package/dist/commands/sh.d.ts +6 -0
  137. package/dist/commands/sh.d.ts.map +1 -1
  138. package/dist/commands/sh.js +6 -0
  139. package/dist/commands/shift.d.ts +10 -0
  140. package/dist/commands/shift.d.ts.map +1 -1
  141. package/dist/commands/shift.js +10 -0
  142. package/dist/commands/sleep.d.ts +5 -0
  143. package/dist/commands/sleep.d.ts.map +1 -1
  144. package/dist/commands/sleep.js +5 -0
  145. package/dist/commands/sort.d.ts +5 -0
  146. package/dist/commands/sort.d.ts.map +1 -1
  147. package/dist/commands/sort.js +5 -0
  148. package/dist/commands/source.d.ts +5 -0
  149. package/dist/commands/source.d.ts.map +1 -1
  150. package/dist/commands/source.js +5 -0
  151. package/dist/commands/stat.d.ts +7 -0
  152. package/dist/commands/stat.d.ts.map +1 -0
  153. package/dist/commands/stat.js +56 -0
  154. package/dist/commands/su.d.ts +13 -0
  155. package/dist/commands/su.d.ts.map +1 -1
  156. package/dist/commands/su.js +45 -14
  157. package/dist/commands/sudo.d.ts.map +1 -1
  158. package/dist/commands/sudo.js +5 -0
  159. package/dist/commands/tail.d.ts +5 -0
  160. package/dist/commands/tail.d.ts.map +1 -1
  161. package/dist/commands/tail.js +15 -3
  162. package/dist/commands/tar.d.ts +5 -0
  163. package/dist/commands/tar.d.ts.map +1 -1
  164. package/dist/commands/tar.js +40 -10
  165. package/dist/commands/tee.d.ts +5 -0
  166. package/dist/commands/tee.d.ts.map +1 -1
  167. package/dist/commands/tee.js +5 -0
  168. package/dist/commands/touch.d.ts +5 -0
  169. package/dist/commands/touch.d.ts.map +1 -1
  170. package/dist/commands/touch.js +5 -0
  171. package/dist/commands/tr.d.ts.map +1 -1
  172. package/dist/commands/tr.js +45 -10
  173. package/dist/commands/tree.d.ts +5 -0
  174. package/dist/commands/tree.d.ts.map +1 -1
  175. package/dist/commands/tree.js +5 -0
  176. package/dist/commands/true.d.ts +10 -0
  177. package/dist/commands/true.d.ts.map +1 -1
  178. package/dist/commands/true.js +10 -0
  179. package/dist/commands/type.d.ts +5 -0
  180. package/dist/commands/type.d.ts.map +1 -1
  181. package/dist/commands/type.js +5 -0
  182. package/dist/commands/uname.d.ts +5 -0
  183. package/dist/commands/uname.d.ts.map +1 -1
  184. package/dist/commands/uname.js +5 -0
  185. package/dist/commands/uniq.d.ts +5 -0
  186. package/dist/commands/uniq.d.ts.map +1 -1
  187. package/dist/commands/uniq.js +5 -0
  188. package/dist/commands/unset.d.ts +5 -0
  189. package/dist/commands/unset.d.ts.map +1 -1
  190. package/dist/commands/unset.js +5 -0
  191. package/dist/commands/uptime.d.ts +5 -0
  192. package/dist/commands/uptime.d.ts.map +1 -1
  193. package/dist/commands/uptime.js +5 -0
  194. package/dist/commands/wc.d.ts +5 -0
  195. package/dist/commands/wc.d.ts.map +1 -1
  196. package/dist/commands/wc.js +5 -0
  197. package/dist/commands/wget.d.ts +5 -0
  198. package/dist/commands/wget.d.ts.map +1 -1
  199. package/dist/commands/wget.js +16 -1
  200. package/dist/commands/who.d.ts +5 -0
  201. package/dist/commands/who.d.ts.map +1 -1
  202. package/dist/commands/who.js +5 -0
  203. package/dist/commands/whoami.d.ts +5 -0
  204. package/dist/commands/whoami.d.ts.map +1 -1
  205. package/dist/commands/whoami.js +5 -0
  206. package/dist/commands/xargs.d.ts +5 -0
  207. package/dist/commands/xargs.d.ts.map +1 -1
  208. package/dist/commands/xargs.js +5 -0
  209. package/dist/self-standalone.js +254 -30
  210. package/dist/types/commands.d.ts +36 -0
  211. package/dist/types/commands.d.ts.map +1 -1
  212. package/dist/utils/tokenize.d.ts +20 -0
  213. package/dist/utils/tokenize.d.ts.map +1 -0
  214. package/dist/utils/tokenize.js +74 -0
  215. package/examples/web.min.js +2 -2
  216. package/package.json +2 -2
  217. package/src/SSHClient/index.ts +6 -3
  218. package/src/SSHMimic/executor.ts +21 -44
  219. package/src/SSHMimic/index.ts +7 -5
  220. package/src/SSHMimic/sftp.ts +28 -21
  221. package/src/VirtualPackageManager/index.ts +29 -1
  222. package/src/VirtualShell/shell.ts +34 -4
  223. package/src/VirtualShell/shellParser.ts +2 -103
  224. package/src/VirtualUserManager/index.ts +43 -19
  225. package/src/commands/adduser.ts +86 -13
  226. package/src/commands/alias.ts +5 -0
  227. package/src/commands/apt.ts +5 -0
  228. package/src/commands/awk.ts +154 -29
  229. package/src/commands/cd.ts +0 -4
  230. package/src/commands/clear.ts +5 -0
  231. package/src/commands/command-helpers.ts +9 -0
  232. package/src/commands/curl.ts +2 -1
  233. package/src/commands/declare.ts +5 -0
  234. package/src/commands/deluser.ts +84 -7
  235. package/src/commands/df.ts +5 -0
  236. package/src/commands/du.ts +5 -0
  237. package/src/commands/export.ts +5 -0
  238. package/src/commands/grep.ts +21 -8
  239. package/src/commands/groups.ts +5 -0
  240. package/src/commands/gzip.ts +61 -28
  241. package/src/commands/head.ts +14 -4
  242. package/src/commands/htop.ts +5 -0
  243. package/src/commands/kill.ts +5 -0
  244. package/src/commands/ln.ts +22 -0
  245. package/src/commands/ls.ts +17 -0
  246. package/src/commands/lsb-release.ts +5 -0
  247. package/src/commands/man.ts +38 -143
  248. package/src/commands/manuals/adduser.txt +11 -0
  249. package/src/commands/manuals/apt-cache.txt +12 -0
  250. package/src/commands/manuals/apt.txt +20 -0
  251. package/src/commands/manuals/awk.txt +13 -0
  252. package/src/commands/manuals/cat.txt +14 -0
  253. package/src/commands/manuals/cd.txt +16 -0
  254. package/src/commands/manuals/chmod.txt +16 -0
  255. package/src/commands/manuals/clear.txt +10 -0
  256. package/src/commands/manuals/cp.txt +10 -0
  257. package/src/commands/manuals/curl.txt +20 -0
  258. package/src/commands/manuals/date.txt +14 -0
  259. package/src/commands/manuals/declare.txt +12 -0
  260. package/src/commands/manuals/deluser.txt +10 -0
  261. package/src/commands/manuals/df.txt +10 -0
  262. package/src/commands/manuals/dpkg-query.txt +11 -0
  263. package/src/commands/manuals/dpkg.txt +14 -0
  264. package/src/commands/manuals/du.txt +11 -0
  265. package/src/commands/manuals/echo.txt +11 -0
  266. package/src/commands/manuals/false.txt +10 -0
  267. package/src/commands/manuals/find.txt +11 -0
  268. package/src/commands/manuals/free.txt +12 -0
  269. package/src/commands/manuals/grep.txt +13 -0
  270. package/src/commands/manuals/groups.txt +10 -0
  271. package/src/commands/manuals/gzip.txt +11 -0
  272. package/src/commands/manuals/head.txt +10 -0
  273. package/src/commands/manuals/help.txt +11 -0
  274. package/src/commands/manuals/history.txt +11 -0
  275. package/src/commands/manuals/hostname.txt +10 -0
  276. package/src/commands/manuals/id.txt +10 -0
  277. package/src/commands/manuals/kill.txt +13 -0
  278. package/src/commands/manuals/ls.txt +20 -0
  279. package/src/commands/manuals/lsb_release.txt +14 -0
  280. package/src/commands/manuals/mkdir.txt +10 -0
  281. package/src/commands/manuals/mv.txt +10 -0
  282. package/src/commands/manuals/nano.txt +11 -0
  283. package/src/commands/manuals/neofetch.txt +10 -0
  284. package/src/commands/manuals/node.txt +13 -0
  285. package/src/commands/manuals/npm.txt +13 -0
  286. package/src/commands/manuals/npx.txt +13 -0
  287. package/src/commands/manuals/passwd.txt +11 -0
  288. package/src/commands/manuals/ping.txt +10 -0
  289. package/src/commands/manuals/printf.txt +11 -0
  290. package/src/commands/manuals/ps.txt +10 -0
  291. package/src/commands/manuals/pwd.txt +10 -0
  292. package/src/commands/manuals/python3.txt +13 -0
  293. package/src/commands/manuals/readlink.txt +10 -0
  294. package/src/commands/manuals/return.txt +10 -0
  295. package/src/commands/manuals/rm.txt +10 -0
  296. package/src/commands/manuals/sed.txt +11 -0
  297. package/src/commands/manuals/set.txt +11 -0
  298. package/src/commands/manuals/shift.txt +10 -0
  299. package/src/commands/manuals/sleep.txt +10 -0
  300. package/src/commands/manuals/sort.txt +12 -0
  301. package/src/commands/manuals/source.txt +11 -0
  302. package/src/commands/manuals/ssh.txt +11 -0
  303. package/src/commands/manuals/stat.txt +10 -0
  304. package/src/commands/manuals/su.txt +13 -0
  305. package/src/commands/manuals/sudo.txt +11 -0
  306. package/src/commands/manuals/tail.txt +10 -0
  307. package/src/commands/manuals/tar.txt +19 -0
  308. package/src/commands/manuals/tee.txt +10 -0
  309. package/src/commands/manuals/test.txt +11 -0
  310. package/src/commands/manuals/touch.txt +11 -0
  311. package/src/commands/manuals/tr.txt +10 -0
  312. package/src/commands/manuals/trap.txt +10 -0
  313. package/src/commands/manuals/true.txt +10 -0
  314. package/src/commands/manuals/type.txt +10 -0
  315. package/src/commands/manuals/uname.txt +12 -0
  316. package/src/commands/manuals/uniq.txt +12 -0
  317. package/src/commands/manuals/unset.txt +10 -0
  318. package/src/commands/manuals/uptime.txt +11 -0
  319. package/src/commands/manuals/wc.txt +12 -0
  320. package/src/commands/manuals/wget.txt +12 -0
  321. package/src/commands/manuals/which.txt +10 -0
  322. package/src/commands/manuals/whoami.txt +10 -0
  323. package/src/commands/manuals/xargs.txt +10 -0
  324. package/src/commands/mkdir.ts +5 -0
  325. package/src/commands/mv.ts +5 -0
  326. package/src/commands/nano.ts +5 -0
  327. package/src/commands/neofetch.ts +15 -6
  328. package/src/commands/passwd.ts +35 -12
  329. package/src/commands/ping.ts +5 -0
  330. package/src/commands/printf.ts +30 -13
  331. package/src/commands/ps.ts +5 -0
  332. package/src/commands/read.ts +5 -0
  333. package/src/commands/registry.ts +4 -1
  334. package/src/commands/rm.ts +5 -0
  335. package/src/commands/runtime.ts +1 -61
  336. package/src/commands/sed.ts +5 -0
  337. package/src/commands/set.ts +5 -24
  338. package/src/commands/sh.ts +9 -3
  339. package/src/commands/shift.ts +10 -0
  340. package/src/commands/sleep.ts +5 -0
  341. package/src/commands/sort.ts +5 -0
  342. package/src/commands/source.ts +5 -0
  343. package/src/commands/stat.ts +61 -0
  344. package/src/commands/su.ts +54 -16
  345. package/src/commands/sudo.ts +5 -0
  346. package/src/commands/tail.ts +17 -3
  347. package/src/commands/tar.ts +38 -15
  348. package/src/commands/tee.ts +5 -0
  349. package/src/commands/touch.ts +5 -0
  350. package/src/commands/tr.ts +54 -10
  351. package/src/commands/tree.ts +5 -0
  352. package/src/commands/true.ts +10 -0
  353. package/src/commands/type.ts +5 -0
  354. package/src/commands/uname.ts +5 -0
  355. package/src/commands/uniq.ts +5 -0
  356. package/src/commands/unset.ts +5 -0
  357. package/src/commands/uptime.ts +5 -0
  358. package/src/commands/wc.ts +5 -0
  359. package/src/commands/wget.ts +17 -1
  360. package/src/commands/who.ts +5 -0
  361. package/src/commands/whoami.ts +5 -0
  362. package/src/commands/xargs.ts +5 -0
  363. package/src/self-standalone.ts +316 -33
  364. package/src/types/commands.ts +37 -0
  365. package/src/utils/tokenize.ts +78 -0
  366. package/tests/new-features.test.ts +2 -2
  367. package/builds/web-iife.min.js +0 -13
  368. package/builds/web-iife.min.js.map +0 -7
@@ -1 +1 @@
1
- {"version":3,"file":"du.d.ts","sourceRoot":"","sources":["../../src/commands/du.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD,eAAO,MAAM,SAAS,EAAE,WA8CvB,CAAC"}
1
+ {"version":3,"file":"du.d.ts","sourceRoot":"","sources":["../../src/commands/du.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,SAAS,EAAE,WA8CvB,CAAC"}
@@ -1,5 +1,10 @@
1
1
  import { ifFlag } from "./command-helpers";
2
2
  import { resolvePath } from "./helpers";
3
+ /**
4
+ * Estimate file and directory space usage.
5
+ * @category system
6
+ * @params ["[-h] [-s] [path]"]
7
+ */
3
8
  export const duCommand = {
4
9
  name: "du",
5
10
  description: "Estimate file space usage",
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Set or display shell environment variables for child processes.
4
+ * @category shell
5
+ * @params ["[VAR=value]"]
6
+ */
2
7
  export declare const exportCommand: ShellModule;
3
8
  //# sourceMappingURL=export.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../src/commands/export.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,eAAO,MAAM,aAAa,EAAE,WAwB3B,CAAC"}
1
+ {"version":3,"file":"export.d.ts","sourceRoot":"","sources":["../../src/commands/export.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;;;GAIG;AACH,eAAO,MAAM,aAAa,EAAE,WAwB3B,CAAC"}
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Set or display shell environment variables for child processes.
3
+ * @category shell
4
+ * @params ["[VAR=value]"]
5
+ */
1
6
  export const exportCommand = {
2
7
  name: "export",
3
8
  description: "Set shell environment variable",
@@ -1 +1 @@
1
- {"version":3,"file":"grep.d.ts","sourceRoot":"","sources":["../../src/commands/grep.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WA6FzB,CAAC"}
1
+ {"version":3,"file":"grep.d.ts","sourceRoot":"","sources":["../../src/commands/grep.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WA0GzB,CAAC"}
@@ -12,12 +12,15 @@ export const grepCommand = {
12
12
  params: ["[-i] [-v] [-n] [-r] <pattern> [file...]"],
13
13
  run: ({ authUser, shell, cwd, args, stdin }) => {
14
14
  const { flags, positionals } = parseArgs(args, {
15
- flags: ["-i", "-v", "-n", "-r"],
15
+ flags: ["-i", "-v", "-n", "-r", "-c", "-l", "-L", "-q", "--quiet", "--silent"],
16
16
  });
17
17
  const caseInsensitive = flags.has("-i");
18
18
  const invertMatch = flags.has("-v");
19
19
  const showLineNumbers = flags.has("-n");
20
20
  const recursive = flags.has("-r");
21
+ const countOnly = flags.has("-c");
22
+ const filesWithMatches = flags.has("-l");
23
+ const quiet = flags.has("-q") || flags.has("--quiet") || flags.has("--silent");
21
24
  const pattern = positionals[0];
22
25
  const files = positionals.slice(1);
23
26
  if (!pattern) {
@@ -72,7 +75,12 @@ export const grepCommand = {
72
75
  if (files.length === 0) {
73
76
  if (!stdin)
74
77
  return { stdout: "", exitCode: 1 };
75
- results.push(...matchLines(stdin));
78
+ const matched = matchLines(stdin);
79
+ if (countOnly)
80
+ return { stdout: `${matched.length}\n`, exitCode: matched.length > 0 ? 0 : 1 };
81
+ if (quiet)
82
+ return { exitCode: matched.length > 0 ? 0 : 1 };
83
+ results.push(...matched);
76
84
  }
77
85
  else {
78
86
  const resolvedPaths = files.flatMap((f) => {
@@ -84,7 +92,17 @@ export const grepCommand = {
84
92
  assertPathAccess(authUser, filePath, "grep");
85
93
  const content = shell.vfs.readFile(filePath);
86
94
  const prefix = resolvedPaths.length > 1 ? `${file}:` : "";
87
- results.push(...matchLines(content, prefix));
95
+ const matched = matchLines(content, prefix);
96
+ if (countOnly) {
97
+ results.push(resolvedPaths.length > 1 ? `${file}:${matched.length}` : String(matched.length));
98
+ }
99
+ else if (filesWithMatches) {
100
+ if (matched.length > 0)
101
+ results.push(file);
102
+ }
103
+ else {
104
+ results.push(...matched);
105
+ }
88
106
  }
89
107
  catch {
90
108
  return {
@@ -95,7 +113,7 @@ export const grepCommand = {
95
113
  }
96
114
  }
97
115
  return {
98
- stdout: results.length > 0 ? results.join("\n") : "",
116
+ stdout: results.length > 0 ? `${results.join("\n")}\n` : "",
99
117
  exitCode: results.length > 0 ? 0 : 1,
100
118
  };
101
119
  },
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Print group memberships for a user.
4
+ * @category system
5
+ * @params ["[user]"]
6
+ */
2
7
  export declare const groupsCommand: ShellModule;
3
8
  //# sourceMappingURL=groups.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"groups.d.ts","sourceRoot":"","sources":["../../src/commands/groups.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,eAAO,MAAM,aAAa,EAAE,WAW3B,CAAC"}
1
+ {"version":3,"file":"groups.d.ts","sourceRoot":"","sources":["../../src/commands/groups.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;;;GAIG;AACH,eAAO,MAAM,aAAa,EAAE,WAW3B,CAAC"}
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Print group memberships for a user.
3
+ * @category system
4
+ * @params ["[user]"]
5
+ */
1
6
  export const groupsCommand = {
2
7
  name: "groups",
3
8
  description: "Print group memberships",
@@ -1,9 +1,12 @@
1
1
  import type { ShellModule } from "../types/commands";
2
2
  /**
3
- * Compress files using gzip (stores in VFS as compressed content).
3
+ * Compress files using gzip renames file to `<file>.gz`, removes original.
4
4
  * @category archive
5
- * @params ["<file>"]
6
5
  */
7
6
  export declare const gzipCommand: ShellModule;
7
+ /**
8
+ * Decompress gzip files — renames `<file>.gz` to `<file>`, removes original.
9
+ * @category archive
10
+ */
8
11
  export declare const gunzipCommand: ShellModule;
9
12
  //# sourceMappingURL=gzip.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"gzip.d.ts","sourceRoot":"","sources":["../../src/commands/gzip.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAGrD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WAmBzB,CAAC;AAEF,eAAO,MAAM,aAAa,EAAE,WAyB3B,CAAC"}
1
+ {"version":3,"file":"gzip.d.ts","sourceRoot":"","sources":["../../src/commands/gzip.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAGrD;;;GAGG;AACH,eAAO,MAAM,WAAW,EAAE,WAgDzB,CAAC;AAEF;;;GAGG;AACH,eAAO,MAAM,aAAa,EAAE,WA0B3B,CAAC"}
@@ -1,56 +1,82 @@
1
1
  import { resolvePath } from "./helpers";
2
2
  /**
3
- * Compress files using gzip (stores in VFS as compressed content).
3
+ * Compress files using gzip renames file to `<file>.gz`, removes original.
4
4
  * @category archive
5
- * @params ["<file>"]
6
5
  */
7
6
  export const gzipCommand = {
8
7
  name: "gzip",
9
8
  description: "Compress files",
10
9
  category: "archive",
11
- params: ["<file>"],
10
+ params: ["[-k] [-d] <file>"],
12
11
  run: ({ shell, cwd, args }) => {
13
- const file = args[0];
12
+ if (!shell.packageManager.isInstalled("gzip")) {
13
+ return {
14
+ stderr: "bash: gzip: command not found\nHint: install it with: apt install gzip\n",
15
+ exitCode: 127,
16
+ };
17
+ }
18
+ const keepOrig = args.includes("-k") || args.includes("--keep");
19
+ const decompress = args.includes("-d");
20
+ const file = args.find((a) => !a.startsWith("-"));
14
21
  if (!file)
15
- return { stderr: "gzip: no file specified", exitCode: 1 };
22
+ return { stderr: "gzip: no file specified\n", exitCode: 1 };
16
23
  const p = resolvePath(cwd, file);
17
- try {
18
- shell.vfs.compressFile(p);
24
+ if (decompress) {
25
+ // gzip -d = gunzip
26
+ if (!file.endsWith(".gz")) {
27
+ return { stderr: `gzip: ${file}: unknown suffix -- ignored\n`, exitCode: 1 };
28
+ }
29
+ if (!shell.vfs.exists(p)) {
30
+ return { stderr: `gzip: ${file}: No such file or directory\n`, exitCode: 1 };
31
+ }
32
+ const content = shell.vfs.readFile(p);
33
+ const dest = p.slice(0, -3);
34
+ shell.vfs.writeFile(dest, content);
35
+ if (!keepOrig)
36
+ shell.vfs.remove(p);
19
37
  return { exitCode: 0 };
20
38
  }
21
- catch {
22
- return {
23
- stderr: `gzip: ${file}: No such file or directory`,
24
- exitCode: 1,
25
- };
39
+ if (!shell.vfs.exists(p)) {
40
+ return { stderr: `gzip: ${file}: No such file or directory\n`, exitCode: 1 };
41
+ }
42
+ if (file.endsWith(".gz")) {
43
+ return { stderr: `gzip: ${file}: already has .gz suffix -- unchanged\n`, exitCode: 1 };
26
44
  }
45
+ const rawContent = shell.vfs.readFileRaw(p);
46
+ const gzPath = `${p}.gz`;
47
+ shell.vfs.writeFile(gzPath, rawContent, { compress: true });
48
+ if (!keepOrig)
49
+ shell.vfs.remove(p);
50
+ return { exitCode: 0 };
27
51
  },
28
52
  };
53
+ /**
54
+ * Decompress gzip files — renames `<file>.gz` to `<file>`, removes original.
55
+ * @category archive
56
+ */
29
57
  export const gunzipCommand = {
30
- /**
31
- * Decompress gzip files (or zcat alias).
32
- * @category archive
33
- * @params ["<file>"]
34
- */
35
58
  name: "gunzip",
36
59
  description: "Decompress files",
37
60
  category: "archive",
38
- params: ["<file>"],
39
61
  aliases: ["zcat"],
62
+ params: ["[-k] <file>"],
40
63
  run: ({ shell, cwd, args }) => {
41
- const file = args[0];
64
+ const keepOrig = args.includes("-k") || args.includes("--keep");
65
+ const file = args.find((a) => !a.startsWith("-"));
42
66
  if (!file)
43
- return { stderr: "gunzip: no file specified", exitCode: 1 };
67
+ return { stderr: "gunzip: no file specified\n", exitCode: 1 };
44
68
  const p = resolvePath(cwd, file);
45
- try {
46
- shell.vfs.decompressFile(p);
47
- return { exitCode: 0 };
69
+ if (!shell.vfs.exists(p)) {
70
+ return { stderr: `gunzip: ${file}: No such file or directory\n`, exitCode: 1 };
48
71
  }
49
- catch {
50
- return {
51
- stderr: `gunzip: ${file}: No such file or directory`,
52
- exitCode: 1,
53
- };
72
+ if (!file.endsWith(".gz")) {
73
+ return { stderr: `gunzip: ${file}: unknown suffix -- ignored\n`, exitCode: 1 };
54
74
  }
75
+ const content = shell.vfs.readFile(p);
76
+ const dest = p.slice(0, -3);
77
+ shell.vfs.writeFile(dest, content);
78
+ if (!keepOrig)
79
+ shell.vfs.remove(p);
80
+ return { exitCode: 0 };
55
81
  },
56
82
  };
@@ -1 +1 @@
1
- {"version":3,"file":"head.d.ts","sourceRoot":"","sources":["../../src/commands/head.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WAgCzB,CAAC"}
1
+ {"version":3,"file":"head.d.ts","sourceRoot":"","sources":["../../src/commands/head.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WA0CzB,CAAC"}
@@ -12,9 +12,18 @@ export const headCommand = {
12
12
  params: ["[-n <lines>] [file...]"],
13
13
  run: ({ authUser, shell, cwd, args, stdin }) => {
14
14
  const nArg = getFlag(args, ["-n"]);
15
- const n = typeof nArg === "string" ? parseInt(nArg, 10) : 10;
16
- const positionals = args.filter((a) => !a.startsWith("-") && a !== nArg);
17
- const take = (content) => content.split("\n").slice(0, n).join("\n");
15
+ // Support both -n N and -N shorthand (head -2, head -10)
16
+ const shortN = args.find((a) => /^-\d+$/.test(a));
17
+ const n = typeof nArg === "string"
18
+ ? parseInt(nArg, 10)
19
+ : shortN ? parseInt(shortN.slice(1), 10) : 10;
20
+ const positionals = args.filter((a) => !a.startsWith("-") && a !== nArg && a !== String(n));
21
+ const take = (content) => {
22
+ const lines = content.split("\n");
23
+ // Preserve trailing newline
24
+ const sliced = lines.slice(0, n);
25
+ return sliced.join("\n") + (content.endsWith("\n") && sliced.length === lines.slice(0, n).length ? "\n" : "");
26
+ };
18
27
  if (positionals.length === 0) {
19
28
  return { stdout: take(stdin ?? ""), exitCode: 0 };
20
29
  }
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Interactive system monitor (requires terminal interaction).
4
+ * @category system
5
+ * @params []
6
+ */
2
7
  export declare const htopCommand: ShellModule;
3
8
  //# sourceMappingURL=htop.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"htop.d.ts","sourceRoot":"","sources":["../../src/commands/htop.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,eAAO,MAAM,WAAW,EAAE,WAYzB,CAAC"}
1
+ {"version":3,"file":"htop.d.ts","sourceRoot":"","sources":["../../src/commands/htop.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WAYzB,CAAC"}
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Interactive system monitor (requires terminal interaction).
3
+ * @category system
4
+ * @params []
5
+ */
1
6
  export const htopCommand = {
2
7
  name: "htop",
3
8
  description: "System monitor",
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Send a signal to a process by PID.
4
+ * @category system
5
+ * @params ["[-9] <pid>"]
6
+ */
2
7
  export declare const killCommand: ShellModule;
3
8
  //# sourceMappingURL=kill.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"kill.d.ts","sourceRoot":"","sources":["../../src/commands/kill.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD,eAAO,MAAM,WAAW,EAAE,WAWzB,CAAC"}
1
+ {"version":3,"file":"kill.d.ts","sourceRoot":"","sources":["../../src/commands/kill.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAErD;;;;GAIG;AACH,eAAO,MAAM,WAAW,EAAE,WAWzB,CAAC"}
@@ -1,3 +1,8 @@
1
+ /**
2
+ * Send a signal to a process by PID.
3
+ * @category system
4
+ * @params ["[-9] <pid>"]
5
+ */
1
6
  export const killCommand = {
2
7
  name: "kill",
3
8
  description: "Send signal to process",
@@ -1,3 +1,5 @@
1
1
  import type { ShellModule } from "../types/commands";
2
2
  export declare const lnCommand: ShellModule;
3
+ /** Shell command: print the value of a symbolic link. */
4
+ export declare const readlinkCommand: ShellModule;
3
5
  //# sourceMappingURL=ln.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"ln.d.ts","sourceRoot":"","sources":["../../src/commands/ln.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD,eAAO,MAAM,SAAS,EAAE,WA4CvB,CAAC"}
1
+ {"version":3,"file":"ln.d.ts","sourceRoot":"","sources":["../../src/commands/ln.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD,eAAO,MAAM,SAAS,EAAE,WA4CvB,CAAC;AAEF,yDAAyD;AACzD,eAAO,MAAM,eAAe,EAAE,WAmB7B,CAAC"}
@@ -42,3 +42,25 @@ export const lnCommand = {
42
42
  }
43
43
  },
44
44
  };
45
+ /** Shell command: print the value of a symbolic link. */
46
+ export const readlinkCommand = {
47
+ name: "readlink",
48
+ description: "Print resolved path of symbolic link",
49
+ category: "files",
50
+ params: ["[-f] <path>"],
51
+ run: ({ shell, cwd, args }) => {
52
+ const follow = args.includes("-f") || args.includes("-e");
53
+ const target = args.find((a) => !a.startsWith("-"));
54
+ if (!target)
55
+ return { stderr: "readlink: missing operand\n", exitCode: 1 };
56
+ const p = resolvePath(cwd, target);
57
+ if (!shell.vfs.exists(p)) {
58
+ return { stderr: `readlink: ${target}: No such file or directory\n`, exitCode: 1 };
59
+ }
60
+ if (!shell.vfs.isSymlink(p)) {
61
+ return { stderr: `readlink: ${target}: not a symbolic link\n`, exitCode: 1 };
62
+ }
63
+ const resolved = shell.vfs.resolveSymlink(follow ? p : p);
64
+ return { stdout: `${resolved}\n`, exitCode: 0 };
65
+ },
66
+ };
@@ -1 +1 @@
1
- {"version":3,"file":"ls.d.ts","sourceRoot":"","sources":["../../src/commands/ls.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AA4BrD,eAAO,MAAM,SAAS,EAAE,WA4BvB,CAAC"}
1
+ {"version":3,"file":"ls.d.ts","sourceRoot":"","sources":["../../src/commands/ls.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AA4BrD,eAAO,MAAM,SAAS,EAAE,WA6CvB,CAAC"}
@@ -34,6 +34,21 @@ export const lsCommand = {
34
34
  });
35
35
  const target = resolvePath(cwd, targetArg ?? cwd);
36
36
  assertPathAccess(authUser, target, "ls");
37
+ // If target is a file, show its info directly (ls -l /etc/passwd)
38
+ if (shell.vfs.exists(target)) {
39
+ const st = shell.vfs.stat(target);
40
+ if (st.type === "file" || shell.vfs.isSymlink(target)) {
41
+ if (longFormat) {
42
+ const name = target.split("/").pop() ?? target;
43
+ const size = st.type === "file" ? st.size : 0;
44
+ return {
45
+ stdout: `${formatPermissions(st.mode, false)} 1 root root ${size} ${formatDate(st.updatedAt)} ${name}\n`,
46
+ exitCode: 0,
47
+ };
48
+ }
49
+ return { stdout: target.split("/").pop() ?? target, exitCode: 0 };
50
+ }
51
+ }
37
52
  const items = shell.vfs
38
53
  .list(target)
39
54
  .filter((name) => showHidden || !name.startsWith("."));
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Print Linux distribution information.
4
+ * @category system
5
+ * @params ["[-a] [-i] [-d] [-r] [-c]"]
6
+ */
2
7
  export declare const lsbReleaseCommand: ShellModule;
3
8
  //# sourceMappingURL=lsb-release.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"lsb-release.d.ts","sourceRoot":"","sources":["../../src/commands/lsb-release.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAGrD,eAAO,MAAM,iBAAiB,EAAE,WAsD/B,CAAC"}
1
+ {"version":3,"file":"lsb-release.d.ts","sourceRoot":"","sources":["../../src/commands/lsb-release.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAGrD;;;;GAIG;AACH,eAAO,MAAM,iBAAiB,EAAE,WAsD/B,CAAC"}
@@ -1,4 +1,9 @@
1
1
  import { ifFlag } from "./command-helpers";
2
+ /**
3
+ * Print Linux distribution information.
4
+ * @category system
5
+ * @params ["[-a] [-i] [-d] [-r] [-c]"]
6
+ */
2
7
  export const lsbReleaseCommand = {
3
8
  name: "lsb_release",
4
9
  description: "Print distribution-specific information",
@@ -1 +1 @@
1
- {"version":3,"file":"man.d.ts","sourceRoot":"","sources":["../../src/commands/man.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAiJrD,eAAO,MAAM,UAAU,EAAE,WAoBxB,CAAC"}
1
+ {"version":3,"file":"man.d.ts","sourceRoot":"","sources":["../../src/commands/man.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAwCrD,eAAO,MAAM,UAAU,EAAE,WAoBxB,CAAC"}
@@ -1,144 +1,38 @@
1
- const MAN_PAGES = {
2
- ls: `LS(1) User Commands LS(1)
3
-
4
- NAME
5
- ls - list directory contents
6
-
7
- SYNOPSIS
8
- ls [OPTION]... [FILE]...
9
-
10
- DESCRIPTION
11
- List information about the FILEs (the current directory by default).
12
-
13
- OPTIONS
14
- -l use a long listing format
15
- -a do not ignore entries starting with .
16
- -h with -l, print human readable sizes
17
- -r reverse order while sorting
18
- -t sort by modification time
19
-
20
- AUTHOR
21
- Written by Richard M. Stallman and David MacKenzie.`,
22
- cat: `CAT(1) User Commands CAT(1)
23
-
24
- NAME
25
- cat - concatenate files and print on the standard output
26
-
27
- SYNOPSIS
28
- cat [OPTION]... [FILE]...
29
-
30
- DESCRIPTION
31
- Concatenate FILE(s) to standard output.
32
-
33
- OPTIONS
34
- -n, --number number all output lines
35
- -b, --number-nonblank number nonempty output lines`,
36
- grep: `GREP(1) User Commands GREP(1)
37
-
38
- NAME
39
- grep, egrep, fgrep - print lines that match patterns
40
-
41
- SYNOPSIS
42
- grep [OPTION]... PATTERNS [FILE]...
43
-
44
- OPTIONS
45
- -i, --ignore-case ignore case distinctions in patterns and data
46
- -v, --invert-match select non-matching lines
47
- -n, --line-number print line number with output lines
48
- -r, --recursive read all files under each directory, recursively`,
49
- apt: `APT(8) APT APT(8)
50
-
51
- NAME
52
- apt - command-line interface
53
-
54
- SYNOPSIS
55
- apt [options] command
56
-
57
- DESCRIPTION
58
- apt provides a high-level commandline interface for the package
59
- management system.
60
-
61
- COMMANDS
62
- install pkg... Install packages
63
- remove pkg... Remove packages
64
- update Download package information
65
- upgrade Upgrade installed packages
66
- search term Search in package descriptions
67
- show pkg Show package information
68
- list List packages`,
69
- ssh: `SSH(1) OpenSSH SSH(1)
70
-
71
- NAME
72
- ssh - OpenSSH remote login client
73
-
74
- SYNOPSIS
75
- ssh [-p port] [user@]hostname [command]
76
-
77
- DESCRIPTION
78
- ssh (SSH client) is a program for logging into a remote machine and
79
- for executing commands on a remote machine.`,
80
- curl: `CURL(1) User Commands CURL(1)
81
-
82
- NAME
83
- curl - transfer a URL
84
-
85
- SYNOPSIS
86
- curl [options / URLs]
87
-
88
- DESCRIPTION
89
- curl is a tool for transferring data with URL syntax.
90
-
91
- OPTIONS
92
- -o, --output <file> Write output to <file>
93
- -X, --request <method> Specify request method
94
- -d, --data <data> HTTP POST data
95
- -H, --header <header> Pass custom header
96
- -s, --silent Silent mode
97
- -I, --head Show document info only
98
- -L, --location Follow redirects
99
- -v, --verbose Make the operation more talkative`,
100
- chmod: `CHMOD(1) User Commands CHMOD(1)
101
-
102
- NAME
103
- chmod - change file mode bits
104
-
105
- SYNOPSIS
106
- chmod [OPTION]... MODE[,MODE]... FILE...
107
- chmod [OPTION]... OCTAL-MODE FILE...
108
-
109
- DESCRIPTION
110
- Change the file mode bits of each given file according to MODE.
111
-
112
- EXAMPLES
113
- chmod 755 script.sh rwxr-xr-x
114
- chmod 644 file.txt rw-r--r--
115
- chmod +x script.sh add execute permission`,
116
- tar: `TAR(1) GNU tar Manual TAR(1)
117
-
118
- NAME
119
- tar - an archiving utility
120
-
121
- SYNOPSIS
122
- tar [OPTION...] [FILE]...
123
-
124
- DESCRIPTION
125
- tar saves many files together into a single tape or disk archive,
126
- and can restore individual files from the archive.
127
-
128
- OPTIONS
129
- -c, --create create a new archive
130
- -x, --extract extract files from an archive
131
- -z, --gzip filter the archive through gzip
132
- -f, --file=ARCHIVE use archive file or device ARCHIVE
133
- -v, --verbose verbosely list files processed
134
- -t, --list list the contents of an archive`,
1
+ const MANUAL_ALIASES = {
2
+ gunzip: "gzip",
135
3
  };
4
+ const manualCache = new Map();
5
+ const manualsBaseUrl = new URL("./manuals/", import.meta.url);
6
+ async function dynamicImport(specifier) {
7
+ const importer = new Function("moduleName", "return import(moduleName)");
8
+ return importer(specifier);
9
+ }
10
+ async function loadBundledManual(commandName) {
11
+ const normalized = commandName.toLowerCase();
12
+ const lookupName = MANUAL_ALIASES[normalized] ?? normalized;
13
+ const cacheKey = `builtin:${lookupName}`;
14
+ if (manualCache.has(cacheKey)) {
15
+ return manualCache.get(cacheKey) ?? null;
16
+ }
17
+ try {
18
+ const fsModule = (await dynamicImport("node:fs/promises"));
19
+ const manualUrl = new URL(`${lookupName}.txt`, manualsBaseUrl);
20
+ const content = await fsModule.readFile(manualUrl, "utf8");
21
+ const page = content.replace(/\n$/, "");
22
+ manualCache.set(cacheKey, page);
23
+ return page;
24
+ }
25
+ catch {
26
+ manualCache.set(cacheKey, null);
27
+ return null;
28
+ }
29
+ }
136
30
  export const manCommand = {
137
31
  name: "man",
138
32
  description: "Interface to the system reference manuals",
139
33
  category: "shell",
140
34
  params: ["<command>"],
141
- run: ({ args, shell }) => {
35
+ run: async ({ args, shell }) => {
142
36
  const name = args[0];
143
37
  if (!name)
144
38
  return { stderr: "What manual page do you want?", exitCode: 1 };
@@ -147,7 +41,7 @@ export const manCommand = {
147
41
  if (shell.vfs.exists(manPath)) {
148
42
  return { stdout: shell.vfs.readFile(manPath), exitCode: 0 };
149
43
  }
150
- const page = MAN_PAGES[name.toLowerCase()];
44
+ const page = await loadBundledManual(name);
151
45
  if (page)
152
46
  return { stdout: page, exitCode: 0 };
153
47
  return { stderr: `No manual entry for ${name}`, exitCode: 16 };
@@ -1,3 +1,8 @@
1
1
  import type { ShellModule } from "../types/commands";
2
+ /**
3
+ * Create one or more directories.
4
+ * @category files
5
+ * @params ["<dir>"]
6
+ */
2
7
  export declare const mkdirCommand: ShellModule;
3
8
  //# sourceMappingURL=mkdir.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"mkdir.d.ts","sourceRoot":"","sources":["../../src/commands/mkdir.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD,eAAO,MAAM,YAAY,EAAE,WAqB1B,CAAC"}
1
+ {"version":3,"file":"mkdir.d.ts","sourceRoot":"","sources":["../../src/commands/mkdir.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,mBAAmB,CAAC;AAIrD;;;;GAIG;AACH,eAAO,MAAM,YAAY,EAAE,WAqB1B,CAAC"}
@@ -1,5 +1,10 @@
1
1
  import { getArg } from "./command-helpers";
2
2
  import { assertPathAccess, resolvePath } from "./helpers";
3
+ /**
4
+ * Create one or more directories.
5
+ * @category files
6
+ * @params ["<dir>"]
7
+ */
3
8
  export const mkdirCommand = {
4
9
  name: "mkdir",
5
10
  description: "Make directories",