@aigne/afs-cli 1.11.0-beta.6 → 1.11.0-beta.7

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 (317) hide show
  1. package/dist/cli.cjs +27 -353
  2. package/dist/cli.d.cts +2 -1
  3. package/dist/cli.d.mts +2 -1
  4. package/dist/cli.mjs +28 -353
  5. package/dist/cli.mjs.map +1 -1
  6. package/dist/config/afs-loader.cjs +123 -0
  7. package/dist/config/afs-loader.d.cts +14 -0
  8. package/dist/config/afs-loader.d.cts.map +1 -0
  9. package/dist/config/afs-loader.d.mts +14 -0
  10. package/dist/config/afs-loader.d.mts.map +1 -0
  11. package/dist/config/afs-loader.mjs +122 -0
  12. package/dist/config/afs-loader.mjs.map +1 -0
  13. package/dist/config/loader.cjs +2 -2
  14. package/dist/config/loader.mjs +2 -2
  15. package/dist/{commands/mount.cjs → config/mount-commands.cjs} +13 -49
  16. package/dist/config/mount-commands.d.cts +20 -0
  17. package/dist/config/mount-commands.d.cts.map +1 -0
  18. package/dist/config/mount-commands.d.mts +20 -0
  19. package/dist/config/mount-commands.d.mts.map +1 -0
  20. package/dist/{commands/mount.mjs → config/mount-commands.mjs} +14 -49
  21. package/dist/config/mount-commands.mjs.map +1 -0
  22. package/dist/config/schema.cjs +9 -1
  23. package/dist/config/schema.mjs +9 -1
  24. package/dist/config/schema.mjs.map +1 -1
  25. package/dist/core/commands/delete.cjs +41 -0
  26. package/dist/core/commands/delete.d.cts +18 -0
  27. package/dist/core/commands/delete.d.cts.map +1 -0
  28. package/dist/core/commands/delete.d.mts +18 -0
  29. package/dist/core/commands/delete.d.mts.map +1 -0
  30. package/dist/core/commands/delete.mjs +42 -0
  31. package/dist/core/commands/delete.mjs.map +1 -0
  32. package/dist/core/commands/exec.cjs +95 -0
  33. package/dist/core/commands/exec.d.cts +26 -0
  34. package/dist/core/commands/exec.d.cts.map +1 -0
  35. package/dist/core/commands/exec.d.mts +26 -0
  36. package/dist/core/commands/exec.d.mts.map +1 -0
  37. package/dist/core/commands/exec.mjs +96 -0
  38. package/dist/core/commands/exec.mjs.map +1 -0
  39. package/dist/core/commands/explain.cjs +254 -0
  40. package/dist/core/commands/explain.d.cts +25 -0
  41. package/dist/core/commands/explain.d.cts.map +1 -0
  42. package/dist/core/commands/explain.d.mts +25 -0
  43. package/dist/core/commands/explain.d.mts.map +1 -0
  44. package/dist/core/commands/explain.mjs +255 -0
  45. package/dist/core/commands/explain.mjs.map +1 -0
  46. package/dist/core/commands/explore.cjs +30 -0
  47. package/dist/core/commands/explore.d.mts +2 -0
  48. package/dist/core/commands/explore.mjs +31 -0
  49. package/dist/core/commands/explore.mjs.map +1 -0
  50. package/dist/core/commands/index.cjs +36 -0
  51. package/dist/core/commands/index.d.cts +21 -0
  52. package/dist/core/commands/index.d.cts.map +1 -0
  53. package/dist/core/commands/index.d.mts +24 -0
  54. package/dist/core/commands/index.d.mts.map +1 -0
  55. package/dist/core/commands/index.mjs +37 -0
  56. package/dist/core/commands/index.mjs.map +1 -0
  57. package/dist/core/commands/ls.cjs +57 -0
  58. package/dist/core/commands/ls.d.cts +21 -0
  59. package/dist/core/commands/ls.d.cts.map +1 -0
  60. package/dist/core/commands/ls.d.mts +21 -0
  61. package/dist/core/commands/ls.d.mts.map +1 -0
  62. package/dist/core/commands/ls.mjs +58 -0
  63. package/dist/core/commands/ls.mjs.map +1 -0
  64. package/dist/core/commands/mount.cjs +139 -0
  65. package/dist/core/commands/mount.d.cts +33 -0
  66. package/dist/core/commands/mount.d.cts.map +1 -0
  67. package/dist/core/commands/mount.d.mts +33 -0
  68. package/dist/core/commands/mount.d.mts.map +1 -0
  69. package/dist/core/commands/mount.mjs +140 -0
  70. package/dist/core/commands/mount.mjs.map +1 -0
  71. package/dist/core/commands/read.cjs +48 -0
  72. package/dist/core/commands/read.d.cts +17 -0
  73. package/dist/core/commands/read.d.cts.map +1 -0
  74. package/dist/core/commands/read.d.mts +17 -0
  75. package/dist/core/commands/read.d.mts.map +1 -0
  76. package/dist/core/commands/read.mjs +49 -0
  77. package/dist/core/commands/read.mjs.map +1 -0
  78. package/dist/core/commands/search.cjs +40 -0
  79. package/dist/core/commands/search.d.mts +2 -0
  80. package/dist/core/commands/search.mjs +41 -0
  81. package/dist/core/commands/search.mjs.map +1 -0
  82. package/dist/core/commands/serve.cjs +242 -0
  83. package/dist/core/commands/serve.d.mts +2 -0
  84. package/dist/core/commands/serve.mjs +242 -0
  85. package/dist/core/commands/serve.mjs.map +1 -0
  86. package/dist/core/commands/stat.cjs +53 -0
  87. package/dist/core/commands/stat.d.cts +17 -0
  88. package/dist/core/commands/stat.d.cts.map +1 -0
  89. package/dist/core/commands/stat.d.mts +17 -0
  90. package/dist/core/commands/stat.d.mts.map +1 -0
  91. package/dist/core/commands/stat.mjs +54 -0
  92. package/dist/core/commands/stat.mjs.map +1 -0
  93. package/dist/core/commands/types.cjs +13 -0
  94. package/dist/core/commands/types.d.cts +54 -0
  95. package/dist/core/commands/types.d.cts.map +1 -0
  96. package/dist/core/commands/types.d.mts +54 -0
  97. package/dist/core/commands/types.d.mts.map +1 -0
  98. package/dist/core/commands/types.mjs +14 -0
  99. package/dist/core/commands/types.mjs.map +1 -0
  100. package/dist/core/commands/write.cjs +70 -0
  101. package/dist/core/commands/write.d.cts +20 -0
  102. package/dist/core/commands/write.d.cts.map +1 -0
  103. package/dist/core/commands/write.d.mts +20 -0
  104. package/dist/core/commands/write.d.mts.map +1 -0
  105. package/dist/core/commands/write.mjs +71 -0
  106. package/dist/core/commands/write.mjs.map +1 -0
  107. package/dist/core/executor/index.cjs +196 -0
  108. package/dist/core/executor/index.d.cts +77 -0
  109. package/dist/core/executor/index.d.cts.map +1 -0
  110. package/dist/core/executor/index.d.mts +77 -0
  111. package/dist/core/executor/index.d.mts.map +1 -0
  112. package/dist/core/executor/index.mjs +195 -0
  113. package/dist/core/executor/index.mjs.map +1 -0
  114. package/dist/core/formatters/delete.cjs +37 -0
  115. package/dist/core/formatters/delete.d.cts +18 -0
  116. package/dist/core/formatters/delete.d.cts.map +1 -0
  117. package/dist/core/formatters/delete.d.mts +18 -0
  118. package/dist/core/formatters/delete.d.mts.map +1 -0
  119. package/dist/core/formatters/delete.mjs +37 -0
  120. package/dist/core/formatters/delete.mjs.map +1 -0
  121. package/dist/core/formatters/exec.cjs +60 -0
  122. package/dist/core/formatters/exec.d.cts +18 -0
  123. package/dist/core/formatters/exec.d.cts.map +1 -0
  124. package/dist/core/formatters/exec.d.mts +18 -0
  125. package/dist/core/formatters/exec.d.mts.map +1 -0
  126. package/dist/core/formatters/exec.mjs +60 -0
  127. package/dist/core/formatters/exec.mjs.map +1 -0
  128. package/dist/core/formatters/explain.cjs +97 -0
  129. package/dist/core/formatters/explain.d.cts +11 -0
  130. package/dist/core/formatters/explain.d.cts.map +1 -0
  131. package/dist/core/formatters/explain.d.mts +11 -0
  132. package/dist/core/formatters/explain.d.mts.map +1 -0
  133. package/dist/core/formatters/explain.mjs +96 -0
  134. package/dist/core/formatters/explain.mjs.map +1 -0
  135. package/dist/core/formatters/index.d.mts +9 -0
  136. package/dist/core/formatters/ls.cjs +179 -0
  137. package/dist/core/formatters/ls.d.cts +20 -0
  138. package/dist/core/formatters/ls.d.cts.map +1 -0
  139. package/dist/core/formatters/ls.d.mts +20 -0
  140. package/dist/core/formatters/ls.d.mts.map +1 -0
  141. package/dist/core/formatters/ls.mjs +179 -0
  142. package/dist/core/formatters/ls.mjs.map +1 -0
  143. package/dist/core/formatters/mount.cjs +55 -0
  144. package/dist/core/formatters/mount.d.cts +15 -0
  145. package/dist/core/formatters/mount.d.cts.map +1 -0
  146. package/dist/core/formatters/mount.d.mts +15 -0
  147. package/dist/core/formatters/mount.d.mts.map +1 -0
  148. package/dist/core/formatters/mount.mjs +55 -0
  149. package/dist/core/formatters/mount.mjs.map +1 -0
  150. package/dist/core/formatters/read.cjs +100 -0
  151. package/dist/core/formatters/read.d.cts +22 -0
  152. package/dist/core/formatters/read.d.cts.map +1 -0
  153. package/dist/core/formatters/read.d.mts +22 -0
  154. package/dist/core/formatters/read.d.mts.map +1 -0
  155. package/dist/core/formatters/read.mjs +100 -0
  156. package/dist/core/formatters/read.mjs.map +1 -0
  157. package/dist/core/formatters/search.cjs +44 -0
  158. package/dist/core/formatters/search.d.mts +1 -0
  159. package/dist/core/formatters/search.mjs +44 -0
  160. package/dist/core/formatters/search.mjs.map +1 -0
  161. package/dist/core/formatters/stat.cjs +155 -0
  162. package/dist/core/formatters/stat.d.cts +15 -0
  163. package/dist/core/formatters/stat.d.cts.map +1 -0
  164. package/dist/core/formatters/stat.d.mts +15 -0
  165. package/dist/core/formatters/stat.d.mts.map +1 -0
  166. package/dist/core/formatters/stat.mjs +155 -0
  167. package/dist/core/formatters/stat.mjs.map +1 -0
  168. package/dist/core/formatters/write.cjs +51 -0
  169. package/dist/core/formatters/write.d.cts +22 -0
  170. package/dist/core/formatters/write.d.cts.map +1 -0
  171. package/dist/core/formatters/write.d.mts +22 -0
  172. package/dist/core/formatters/write.d.mts.map +1 -0
  173. package/dist/core/formatters/write.mjs +51 -0
  174. package/dist/core/formatters/write.mjs.map +1 -0
  175. package/dist/core/helpers/exec-args.cjs +142 -0
  176. package/dist/core/helpers/exec-args.d.cts +46 -0
  177. package/dist/core/helpers/exec-args.d.cts.map +1 -0
  178. package/dist/core/helpers/exec-args.d.mts +46 -0
  179. package/dist/core/helpers/exec-args.d.mts.map +1 -0
  180. package/dist/core/helpers/exec-args.mjs +139 -0
  181. package/dist/core/helpers/exec-args.mjs.map +1 -0
  182. package/dist/core/helpers/stdin.cjs +41 -0
  183. package/dist/core/helpers/stdin.d.cts +15 -0
  184. package/dist/core/helpers/stdin.d.cts.map +1 -0
  185. package/dist/core/helpers/stdin.d.mts +15 -0
  186. package/dist/core/helpers/stdin.d.mts.map +1 -0
  187. package/dist/core/helpers/stdin.mjs +41 -0
  188. package/dist/core/helpers/stdin.mjs.map +1 -0
  189. package/dist/core/index.cjs +49 -0
  190. package/dist/core/index.d.cts +24 -0
  191. package/dist/core/index.d.mts +25 -0
  192. package/dist/core/index.mjs +24 -0
  193. package/dist/core/path-utils.cjs +1 -0
  194. package/dist/core/path-utils.mjs +3 -0
  195. package/dist/core/types.d.cts +24 -0
  196. package/dist/core/types.d.cts.map +1 -0
  197. package/dist/core/types.d.mts +24 -0
  198. package/dist/core/types.d.mts.map +1 -0
  199. package/dist/errors.cjs +0 -11
  200. package/dist/errors.mjs +1 -11
  201. package/dist/errors.mjs.map +1 -1
  202. package/dist/explorer/actions.cjs +67 -32
  203. package/dist/explorer/actions.mjs +66 -32
  204. package/dist/explorer/actions.mjs.map +1 -1
  205. package/dist/explorer/components/dialog.cjs +170 -46
  206. package/dist/explorer/components/dialog.mjs +170 -46
  207. package/dist/explorer/components/dialog.mjs.map +1 -1
  208. package/dist/explorer/components/metadata-panel.cjs +86 -3
  209. package/dist/explorer/components/metadata-panel.mjs +86 -3
  210. package/dist/explorer/components/metadata-panel.mjs.map +1 -1
  211. package/dist/explorer/screen.cjs +63 -27
  212. package/dist/explorer/screen.d.cts +23 -0
  213. package/dist/explorer/screen.d.cts.map +1 -0
  214. package/dist/explorer/screen.d.mts +23 -0
  215. package/dist/explorer/screen.d.mts.map +1 -0
  216. package/dist/explorer/screen.mjs +63 -27
  217. package/dist/explorer/screen.mjs.map +1 -1
  218. package/dist/explorer/theme.cjs +1 -1
  219. package/dist/explorer/theme.mjs +1 -1
  220. package/dist/explorer/theme.mjs.map +1 -1
  221. package/dist/index.cjs +7 -1
  222. package/dist/index.d.cts +4 -1
  223. package/dist/index.d.mts +4 -1
  224. package/dist/index.mjs +4 -1
  225. package/dist/mcp/http-transport.cjs +68 -0
  226. package/dist/mcp/http-transport.mjs +68 -0
  227. package/dist/mcp/http-transport.mjs.map +1 -0
  228. package/dist/mcp/prompts.cjs +48 -0
  229. package/dist/mcp/prompts.mjs +48 -0
  230. package/dist/mcp/prompts.mjs.map +1 -0
  231. package/dist/mcp/resources.cjs +25 -0
  232. package/dist/mcp/resources.mjs +25 -0
  233. package/dist/mcp/resources.mjs.map +1 -0
  234. package/dist/mcp/server.cjs +30 -0
  235. package/dist/mcp/server.mjs +30 -0
  236. package/dist/mcp/server.mjs.map +1 -0
  237. package/dist/mcp/tools.cjs +196 -0
  238. package/dist/mcp/tools.mjs +196 -0
  239. package/dist/mcp/tools.mjs.map +1 -0
  240. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/index.d.cts +10 -0
  241. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/index.d.cts.map +1 -0
  242. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/index.d.mts +10 -0
  243. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/index.d.mts.map +1 -0
  244. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/types.d.cts +46 -0
  245. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/types.d.cts.map +1 -0
  246. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/types.d.mts +46 -0
  247. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/types.d.mts.map +1 -0
  248. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/urlpattern.cjs +902 -0
  249. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/urlpattern.mjs +902 -0
  250. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/dist/urlpattern.mjs.map +1 -0
  251. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/index.cjs +6 -0
  252. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/index.mjs +8 -0
  253. package/dist/node_modules/.pnpm/urlpattern-polyfill@10.1.0/node_modules/urlpattern-polyfill/index.mjs.map +1 -0
  254. package/dist/path-utils.d.cts +50 -0
  255. package/dist/path-utils.d.cts.map +1 -0
  256. package/dist/path-utils.d.mts +50 -0
  257. package/dist/path-utils.d.mts.map +1 -0
  258. package/dist/repl.cjs +485 -0
  259. package/dist/repl.d.cts +15 -0
  260. package/dist/repl.d.cts.map +1 -0
  261. package/dist/repl.d.mts +16 -0
  262. package/dist/repl.d.mts.map +1 -0
  263. package/dist/repl.mjs +485 -0
  264. package/dist/repl.mjs.map +1 -0
  265. package/dist/serve.cjs +146 -0
  266. package/dist/serve.d.cts +41 -0
  267. package/dist/serve.d.cts.map +1 -0
  268. package/dist/serve.d.mts +41 -0
  269. package/dist/serve.d.mts.map +1 -0
  270. package/dist/serve.mjs +146 -0
  271. package/dist/serve.mjs.map +1 -0
  272. package/dist/ui/header.cjs +1 -40
  273. package/dist/ui/header.mjs +1 -39
  274. package/dist/ui/header.mjs.map +1 -1
  275. package/dist/ui/index.cjs +2 -9
  276. package/dist/ui/index.mjs +2 -7
  277. package/dist/ui/index.mjs.map +1 -1
  278. package/dist/ui/terminal.cjs +1 -10
  279. package/dist/ui/terminal.mjs +1 -8
  280. package/dist/ui/terminal.mjs.map +1 -1
  281. package/package.json +29 -16
  282. package/dist/commands/exec.cjs +0 -164
  283. package/dist/commands/exec.mjs +0 -160
  284. package/dist/commands/exec.mjs.map +0 -1
  285. package/dist/commands/explain.cjs +0 -244
  286. package/dist/commands/explain.mjs +0 -242
  287. package/dist/commands/explain.mjs.map +0 -1
  288. package/dist/commands/index.cjs +0 -8
  289. package/dist/commands/index.mjs +0 -10
  290. package/dist/commands/ls.cjs +0 -242
  291. package/dist/commands/ls.mjs +0 -242
  292. package/dist/commands/ls.mjs.map +0 -1
  293. package/dist/commands/mount.mjs.map +0 -1
  294. package/dist/commands/read.cjs +0 -264
  295. package/dist/commands/read.mjs +0 -263
  296. package/dist/commands/read.mjs.map +0 -1
  297. package/dist/commands/serve.cjs +0 -144
  298. package/dist/commands/serve.mjs +0 -143
  299. package/dist/commands/serve.mjs.map +0 -1
  300. package/dist/commands/stat.cjs +0 -195
  301. package/dist/commands/stat.mjs +0 -195
  302. package/dist/commands/stat.mjs.map +0 -1
  303. package/dist/commands/write.cjs +0 -85
  304. package/dist/commands/write.mjs +0 -85
  305. package/dist/commands/write.mjs.map +0 -1
  306. package/dist/config/provider-factory.cjs +0 -400
  307. package/dist/config/provider-factory.mjs +0 -401
  308. package/dist/config/provider-factory.mjs.map +0 -1
  309. package/dist/config/uri-parser.cjs +0 -285
  310. package/dist/config/uri-parser.mjs +0 -285
  311. package/dist/config/uri-parser.mjs.map +0 -1
  312. package/dist/runtime.cjs +0 -120
  313. package/dist/runtime.mjs +0 -120
  314. package/dist/runtime.mjs.map +0 -1
  315. package/dist/utils/meta.cjs +0 -51
  316. package/dist/utils/meta.mjs +0 -49
  317. package/dist/utils/meta.mjs.map +0 -1
package/dist/serve.cjs ADDED
@@ -0,0 +1,146 @@
1
+ const require_rolldown_runtime = require('./_virtual/rolldown_runtime.cjs');
2
+ const require_index = require('./ui/index.cjs');
3
+ const require_afs_loader = require('./config/afs-loader.cjs');
4
+ let node_http = require("node:http");
5
+ let _aigne_afs_http = require("@aigne/afs-http");
6
+
7
+ //#region src/serve.ts
8
+ /**
9
+ * Create an AFSModule wrapper around AFS instance
10
+ */
11
+ function createAFSModule(afs, readonly) {
12
+ return {
13
+ name: "afs-server",
14
+ accessMode: readonly ? "readonly" : "readwrite",
15
+ async list(path, options) {
16
+ return afs.list(path, options);
17
+ },
18
+ async read(path, options) {
19
+ return afs.read(path, options);
20
+ },
21
+ async write(path, content, options) {
22
+ if (readonly) throw new Error("Server is in readonly mode");
23
+ return afs.write(path, content, options);
24
+ },
25
+ async delete(path, options) {
26
+ if (readonly) throw new Error("Server is in readonly mode");
27
+ return afs.delete(path, options);
28
+ },
29
+ async search(path, query, options) {
30
+ return afs.search(path, query, options);
31
+ },
32
+ async stat(path, options) {
33
+ return afs.stat(path, options);
34
+ },
35
+ async explain(path, options) {
36
+ return afs.explain(path, options);
37
+ },
38
+ async exec(path, args, options) {
39
+ if (readonly) throw new Error("Server is in readonly mode");
40
+ return afs.exec(path, args, options);
41
+ },
42
+ async rename(oldPath, newPath, options) {
43
+ if (readonly) throw new Error("Server is in readonly mode");
44
+ return afs.rename(oldPath, newPath, options);
45
+ }
46
+ };
47
+ }
48
+ /**
49
+ * Start an AFS HTTP server
50
+ *
51
+ * Loads AFS from config in cwd, wraps it as an AFSModule, and starts
52
+ * an HTTP server. Blocks until the server is shut down (Ctrl+C / SIGTERM).
53
+ */
54
+ async function startServe(options) {
55
+ const { cwd, host = "localhost", port = 3e3, path: basePath = "/afs", readonly = false, cors = false, token, maxBodySize = 10 * 1024 * 1024, onExit, onProgress, extraProviders } = options;
56
+ const { afs, failures } = await require_afs_loader.createAFS(cwd, { onProgress });
57
+ if (extraProviders) for (const { provider, mountPath } of extraProviders) try {
58
+ await afs.mount(provider, mountPath);
59
+ } catch (e) {
60
+ const msg = e instanceof Error ? e.message : String(e);
61
+ console.warn(` ${require_index.colors.yellow("⚠")} extra provider ${mountPath}: ${msg}`);
62
+ }
63
+ if (failures.length > 0) {
64
+ console.warn(`${failures.length} provider(s) failed to mount:`);
65
+ for (const f of failures) console.warn(` ${require_index.colors.yellow("⚠")} ${f.path}: ${f.reason}`);
66
+ }
67
+ const mounts = afs.getMounts();
68
+ const handler = (0, _aigne_afs_http.createAFSHttpHandler)({
69
+ module: createAFSModule(afs, readonly),
70
+ maxBodySize,
71
+ token
72
+ });
73
+ const server = (0, node_http.createServer)(async (req, res) => {
74
+ const url = new URL(req.url || "/", `http://${req.headers.host}`);
75
+ const timestamp = (/* @__PURE__ */ new Date()).toISOString();
76
+ console.error(`${timestamp} ${req.method} ${url.pathname}`);
77
+ if (cors) {
78
+ res.setHeader("Access-Control-Allow-Origin", "*");
79
+ res.setHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
80
+ res.setHeader("Access-Control-Allow-Headers", "Content-Type, Authorization");
81
+ if (req.method === "OPTIONS") {
82
+ res.writeHead(204);
83
+ res.end();
84
+ return;
85
+ }
86
+ }
87
+ if (!url.pathname.startsWith(basePath)) {
88
+ res.writeHead(404, { "Content-Type": "application/json" });
89
+ res.end(JSON.stringify({
90
+ code: 1,
91
+ error: "Not found"
92
+ }));
93
+ return;
94
+ }
95
+ const headers = new Headers();
96
+ for (const [key, value] of Object.entries(req.headers)) if (value) headers.append(key, Array.isArray(value) ? value.join(", ") : value);
97
+ const chunks = [];
98
+ for await (const chunk of req) chunks.push(chunk);
99
+ const body = Buffer.concat(chunks);
100
+ const request = new Request(`http://${req.headers.host}${req.url}`, {
101
+ method: req.method,
102
+ headers,
103
+ body: body.length > 0 ? body : void 0
104
+ });
105
+ try {
106
+ const response = await handler(request);
107
+ res.writeHead(response.status, { "Content-Type": response.headers.get("Content-Type") || "application/json" });
108
+ const responseBody = await response.text();
109
+ res.end(responseBody);
110
+ } catch (error) {
111
+ console.error("Error handling request:", error);
112
+ res.writeHead(500, { "Content-Type": "application/json" });
113
+ res.end(JSON.stringify({
114
+ code: 5,
115
+ error: "Internal server error"
116
+ }));
117
+ }
118
+ });
119
+ await new Promise((resolve, reject) => {
120
+ server.listen(port, host, () => resolve());
121
+ server.on("error", reject);
122
+ });
123
+ const serverUrl = `http://${host}:${port}${basePath}`;
124
+ console.log(require_index.colors.green("AFS HTTP Server started"));
125
+ console.log(require_index.colors.bold("Mounted providers:"));
126
+ for (const m of mounts) console.log(` ${require_index.colors.cyan(m.path.padEnd(20))} ${require_index.colors.dim(m.module.name)}`);
127
+ console.log("");
128
+ console.log(`${require_index.colors.dim("Listening on:")} ${require_index.colors.brightCyan(serverUrl)}`);
129
+ console.log(require_index.colors.dim("Press Ctrl+C to stop"));
130
+ let shuttingDown = false;
131
+ const shutdown = async () => {
132
+ if (shuttingDown) return;
133
+ shuttingDown = true;
134
+ console.error("\nShutting down server...");
135
+ server.close();
136
+ if (onExit) await onExit();
137
+ };
138
+ process.on("SIGINT", shutdown);
139
+ process.on("SIGTERM", shutdown);
140
+ await new Promise((resolve) => {
141
+ server.on("close", resolve);
142
+ });
143
+ }
144
+
145
+ //#endregion
146
+ exports.startServe = startServe;
@@ -0,0 +1,41 @@
1
+ import { CreateAFSOptions } from "./config/afs-loader.cjs";
2
+ import { AFSModule } from "@aigne/afs";
3
+
4
+ //#region src/serve.d.ts
5
+ interface StartServeOptions {
6
+ /** Working directory containing .afs-config/config.toml */
7
+ cwd: string;
8
+ /** Host to bind (default: "localhost") */
9
+ host?: string;
10
+ /** Port to listen on (default: 3000) */
11
+ port?: number;
12
+ /** API base path (default: "/afs") */
13
+ path?: string;
14
+ /** Read-only mode (default: false) */
15
+ readonly?: boolean;
16
+ /** Enable CORS (default: false) */
17
+ cors?: boolean;
18
+ /** Authorization token */
19
+ token?: string;
20
+ /** Maximum request body size in bytes (default: 10MB) */
21
+ maxBodySize?: number;
22
+ /** Callback when server is shutting down */
23
+ onExit?: () => Promise<void>;
24
+ /** AFS loading progress callback */
25
+ onProgress?: CreateAFSOptions["onProgress"];
26
+ /** Pre-created providers to mount directly (e.g. mock-based providers that can't be recreated from URI) */
27
+ extraProviders?: Array<{
28
+ provider: AFSModule;
29
+ mountPath: string;
30
+ }>;
31
+ }
32
+ /**
33
+ * Start an AFS HTTP server
34
+ *
35
+ * Loads AFS from config in cwd, wraps it as an AFSModule, and starts
36
+ * an HTTP server. Blocks until the server is shut down (Ctrl+C / SIGTERM).
37
+ */
38
+ declare function startServe(options: StartServeOptions): Promise<void>;
39
+ //#endregion
40
+ export { StartServeOptions, startServe };
41
+ //# sourceMappingURL=serve.d.cts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"serve.d.cts","names":[],"sources":["../src/serve.ts"],"mappings":";;;;UAciB,iBAAA;EAsBoB;EApBnC,GAAA;EAoBsB;EAlBtB,IAAA;EAFA;EAIA,IAAA;EAAA;EAEA,IAAA;EAEA;EAAA,QAAA;EAIA;EAFA,IAAA;EAMA;EAJA,KAAA;EAMA;EAJA,WAAA;EAMA;EAJA,MAAA,SAAe,OAAA;EAIU;EAFzB,UAAA,GAAa,gBAAA;EAEiC;EAA9C,cAAA,GAAiB,KAAA;IAAQ,QAAA,EAAU,SAAA;IAAW,SAAA;EAAA;AAAA;;;;;;;iBA0D1B,UAAA,CAAW,OAAA,EAAS,iBAAA,GAAoB,OAAA"}
@@ -0,0 +1,41 @@
1
+ import { CreateAFSOptions } from "./config/afs-loader.mjs";
2
+ import { AFSModule } from "@aigne/afs";
3
+
4
+ //#region src/serve.d.ts
5
+ interface StartServeOptions {
6
+ /** Working directory containing .afs-config/config.toml */
7
+ cwd: string;
8
+ /** Host to bind (default: "localhost") */
9
+ host?: string;
10
+ /** Port to listen on (default: 3000) */
11
+ port?: number;
12
+ /** API base path (default: "/afs") */
13
+ path?: string;
14
+ /** Read-only mode (default: false) */
15
+ readonly?: boolean;
16
+ /** Enable CORS (default: false) */
17
+ cors?: boolean;
18
+ /** Authorization token */
19
+ token?: string;
20
+ /** Maximum request body size in bytes (default: 10MB) */
21
+ maxBodySize?: number;
22
+ /** Callback when server is shutting down */
23
+ onExit?: () => Promise<void>;
24
+ /** AFS loading progress callback */
25
+ onProgress?: CreateAFSOptions["onProgress"];
26
+ /** Pre-created providers to mount directly (e.g. mock-based providers that can't be recreated from URI) */
27
+ extraProviders?: Array<{
28
+ provider: AFSModule;
29
+ mountPath: string;
30
+ }>;
31
+ }
32
+ /**
33
+ * Start an AFS HTTP server
34
+ *
35
+ * Loads AFS from config in cwd, wraps it as an AFSModule, and starts
36
+ * an HTTP server. Blocks until the server is shut down (Ctrl+C / SIGTERM).
37
+ */
38
+ declare function startServe(options: StartServeOptions): Promise<void>;
39
+ //#endregion
40
+ export { StartServeOptions, startServe };
41
+ //# sourceMappingURL=serve.d.mts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"serve.d.mts","names":[],"sources":["../src/serve.ts"],"mappings":";;;;UAciB,iBAAA;EAsBoB;EApBnC,GAAA;EAoBsB;EAlBtB,IAAA;EAFA;EAIA,IAAA;EAAA;EAEA,IAAA;EAEA;EAAA,QAAA;EAIA;EAFA,IAAA;EAMA;EAJA,KAAA;EAMA;EAJA,WAAA;EAMA;EAJA,MAAA,SAAe,OAAA;EAIU;EAFzB,UAAA,GAAa,gBAAA;EAEiC;EAA9C,cAAA,GAAiB,KAAA;IAAQ,QAAA,EAAU,SAAA;IAAW,SAAA;EAAA;AAAA;;;;;;;iBA0D1B,UAAA,CAAW,OAAA,EAAS,iBAAA,GAAoB,OAAA"}
package/dist/serve.mjs ADDED
@@ -0,0 +1,146 @@
1
+ import { colors } from "./ui/index.mjs";
2
+ import { createAFS } from "./config/afs-loader.mjs";
3
+ import { createServer } from "node:http";
4
+ import { createAFSHttpHandler } from "@aigne/afs-http";
5
+
6
+ //#region src/serve.ts
7
+ /**
8
+ * Create an AFSModule wrapper around AFS instance
9
+ */
10
+ function createAFSModule(afs, readonly) {
11
+ return {
12
+ name: "afs-server",
13
+ accessMode: readonly ? "readonly" : "readwrite",
14
+ async list(path, options) {
15
+ return afs.list(path, options);
16
+ },
17
+ async read(path, options) {
18
+ return afs.read(path, options);
19
+ },
20
+ async write(path, content, options) {
21
+ if (readonly) throw new Error("Server is in readonly mode");
22
+ return afs.write(path, content, options);
23
+ },
24
+ async delete(path, options) {
25
+ if (readonly) throw new Error("Server is in readonly mode");
26
+ return afs.delete(path, options);
27
+ },
28
+ async search(path, query, options) {
29
+ return afs.search(path, query, options);
30
+ },
31
+ async stat(path, options) {
32
+ return afs.stat(path, options);
33
+ },
34
+ async explain(path, options) {
35
+ return afs.explain(path, options);
36
+ },
37
+ async exec(path, args, options) {
38
+ if (readonly) throw new Error("Server is in readonly mode");
39
+ return afs.exec(path, args, options);
40
+ },
41
+ async rename(oldPath, newPath, options) {
42
+ if (readonly) throw new Error("Server is in readonly mode");
43
+ return afs.rename(oldPath, newPath, options);
44
+ }
45
+ };
46
+ }
47
+ /**
48
+ * Start an AFS HTTP server
49
+ *
50
+ * Loads AFS from config in cwd, wraps it as an AFSModule, and starts
51
+ * an HTTP server. Blocks until the server is shut down (Ctrl+C / SIGTERM).
52
+ */
53
+ async function startServe(options) {
54
+ const { cwd, host = "localhost", port = 3e3, path: basePath = "/afs", readonly = false, cors = false, token, maxBodySize = 10 * 1024 * 1024, onExit, onProgress, extraProviders } = options;
55
+ const { afs, failures } = await createAFS(cwd, { onProgress });
56
+ if (extraProviders) for (const { provider, mountPath } of extraProviders) try {
57
+ await afs.mount(provider, mountPath);
58
+ } catch (e) {
59
+ const msg = e instanceof Error ? e.message : String(e);
60
+ console.warn(` ${colors.yellow("⚠")} extra provider ${mountPath}: ${msg}`);
61
+ }
62
+ if (failures.length > 0) {
63
+ console.warn(`${failures.length} provider(s) failed to mount:`);
64
+ for (const f of failures) console.warn(` ${colors.yellow("⚠")} ${f.path}: ${f.reason}`);
65
+ }
66
+ const mounts = afs.getMounts();
67
+ const handler = createAFSHttpHandler({
68
+ module: createAFSModule(afs, readonly),
69
+ maxBodySize,
70
+ token
71
+ });
72
+ const server = createServer(async (req, res) => {
73
+ const url = new URL(req.url || "/", `http://${req.headers.host}`);
74
+ const timestamp = (/* @__PURE__ */ new Date()).toISOString();
75
+ console.error(`${timestamp} ${req.method} ${url.pathname}`);
76
+ if (cors) {
77
+ res.setHeader("Access-Control-Allow-Origin", "*");
78
+ res.setHeader("Access-Control-Allow-Methods", "GET, POST, PUT, DELETE, OPTIONS");
79
+ res.setHeader("Access-Control-Allow-Headers", "Content-Type, Authorization");
80
+ if (req.method === "OPTIONS") {
81
+ res.writeHead(204);
82
+ res.end();
83
+ return;
84
+ }
85
+ }
86
+ if (!url.pathname.startsWith(basePath)) {
87
+ res.writeHead(404, { "Content-Type": "application/json" });
88
+ res.end(JSON.stringify({
89
+ code: 1,
90
+ error: "Not found"
91
+ }));
92
+ return;
93
+ }
94
+ const headers = new Headers();
95
+ for (const [key, value] of Object.entries(req.headers)) if (value) headers.append(key, Array.isArray(value) ? value.join(", ") : value);
96
+ const chunks = [];
97
+ for await (const chunk of req) chunks.push(chunk);
98
+ const body = Buffer.concat(chunks);
99
+ const request = new Request(`http://${req.headers.host}${req.url}`, {
100
+ method: req.method,
101
+ headers,
102
+ body: body.length > 0 ? body : void 0
103
+ });
104
+ try {
105
+ const response = await handler(request);
106
+ res.writeHead(response.status, { "Content-Type": response.headers.get("Content-Type") || "application/json" });
107
+ const responseBody = await response.text();
108
+ res.end(responseBody);
109
+ } catch (error) {
110
+ console.error("Error handling request:", error);
111
+ res.writeHead(500, { "Content-Type": "application/json" });
112
+ res.end(JSON.stringify({
113
+ code: 5,
114
+ error: "Internal server error"
115
+ }));
116
+ }
117
+ });
118
+ await new Promise((resolve, reject) => {
119
+ server.listen(port, host, () => resolve());
120
+ server.on("error", reject);
121
+ });
122
+ const serverUrl = `http://${host}:${port}${basePath}`;
123
+ console.log(colors.green("AFS HTTP Server started"));
124
+ console.log(colors.bold("Mounted providers:"));
125
+ for (const m of mounts) console.log(` ${colors.cyan(m.path.padEnd(20))} ${colors.dim(m.module.name)}`);
126
+ console.log("");
127
+ console.log(`${colors.dim("Listening on:")} ${colors.brightCyan(serverUrl)}`);
128
+ console.log(colors.dim("Press Ctrl+C to stop"));
129
+ let shuttingDown = false;
130
+ const shutdown = async () => {
131
+ if (shuttingDown) return;
132
+ shuttingDown = true;
133
+ console.error("\nShutting down server...");
134
+ server.close();
135
+ if (onExit) await onExit();
136
+ };
137
+ process.on("SIGINT", shutdown);
138
+ process.on("SIGTERM", shutdown);
139
+ await new Promise((resolve) => {
140
+ server.on("close", resolve);
141
+ });
142
+ }
143
+
144
+ //#endregion
145
+ export { startServe };
146
+ //# sourceMappingURL=serve.mjs.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"serve.mjs","names":[],"sources":["../src/serve.ts"],"sourcesContent":["/**\n * AFS Serve - Standalone serve function\n *\n * Starts an HTTP server exposing AFS providers over HTTP transport.\n * Can be called programmatically (e.g., from playground) without yargs.\n */\n\nimport type { IncomingMessage, ServerResponse } from \"node:http\";\nimport { createServer } from \"node:http\";\nimport type { AFS, AFSModule } from \"@aigne/afs\";\nimport { createAFSHttpHandler } from \"@aigne/afs-http\";\nimport { type CreateAFSOptions, createAFS } from \"./config/afs-loader.js\";\nimport { colors } from \"./ui/index.js\";\n\nexport interface StartServeOptions {\n /** Working directory containing .afs-config/config.toml */\n cwd: string;\n /** Host to bind (default: \"localhost\") */\n host?: string;\n /** Port to listen on (default: 3000) */\n port?: number;\n /** API base path (default: \"/afs\") */\n path?: string;\n /** Read-only mode (default: false) */\n readonly?: boolean;\n /** Enable CORS (default: false) */\n cors?: boolean;\n /** Authorization token */\n token?: string;\n /** Maximum request body size in bytes (default: 10MB) */\n maxBodySize?: number;\n /** Callback when server is shutting down */\n onExit?: () => Promise<void>;\n /** AFS loading progress callback */\n onProgress?: CreateAFSOptions[\"onProgress\"];\n /** Pre-created providers to mount directly (e.g. mock-based providers that can't be recreated from URI) */\n extraProviders?: Array<{ provider: AFSModule; mountPath: string }>;\n}\n\n/**\n * Create an AFSModule wrapper around AFS instance\n */\nfunction createAFSModule(afs: AFS, readonly: boolean): AFSModule {\n return {\n name: \"afs-server\",\n accessMode: readonly ? \"readonly\" : \"readwrite\",\n async list(path, options) {\n return afs.list(path, options);\n },\n async read(path, options) {\n return afs.read(path, options);\n },\n async write(path, content, options) {\n if (readonly) {\n throw new Error(\"Server is in readonly mode\");\n }\n return afs.write(path, content, options);\n },\n async delete(path, options) {\n if (readonly) {\n throw new Error(\"Server is in readonly mode\");\n }\n return afs.delete(path, options);\n },\n async search(path, query, options) {\n return afs.search(path, query, options);\n },\n async stat(path, options) {\n return afs.stat(path, options);\n },\n async explain(path, options) {\n return afs.explain(path, options);\n },\n async exec(path, args, options) {\n if (readonly) {\n throw new Error(\"Server is in readonly mode\");\n }\n return afs.exec(path, args, options);\n },\n async rename(oldPath, newPath, options) {\n if (readonly) {\n throw new Error(\"Server is in readonly mode\");\n }\n return afs.rename(oldPath, newPath, options);\n },\n };\n}\n\n/**\n * Start an AFS HTTP server\n *\n * Loads AFS from config in cwd, wraps it as an AFSModule, and starts\n * an HTTP server. Blocks until the server is shut down (Ctrl+C / SIGTERM).\n */\nexport async function startServe(options: StartServeOptions): Promise<void> {\n const {\n cwd,\n host = \"localhost\",\n port = 3000,\n path: basePath = \"/afs\",\n readonly = false,\n cors = false,\n token,\n maxBodySize = 10 * 1024 * 1024,\n onExit,\n onProgress,\n extraProviders,\n } = options;\n\n // Load AFS from config\n const { afs, failures } = await createAFS(cwd, { onProgress });\n\n // Mount extra providers (mock-based, not in config.toml)\n if (extraProviders) {\n for (const { provider, mountPath } of extraProviders) {\n try {\n await afs.mount(provider, mountPath);\n } catch (e) {\n const msg = e instanceof Error ? e.message : String(e);\n console.warn(` ${colors.yellow(\"⚠\")} extra provider ${mountPath}: ${msg}`);\n }\n }\n }\n\n if (failures.length > 0) {\n console.warn(`${failures.length} provider(s) failed to mount:`);\n for (const f of failures) {\n console.warn(` ${colors.yellow(\"⚠\")} ${f.path}: ${f.reason}`);\n }\n }\n\n const mounts = afs.getMounts();\n\n // Create module wrapper and HTTP handler\n const module = createAFSModule(afs, readonly);\n const handler = createAFSHttpHandler({ module, maxBodySize, token });\n\n // Create HTTP server\n const server = createServer(async (req: IncomingMessage, res: ServerResponse) => {\n const url = new URL(req.url || \"/\", `http://${req.headers.host}`);\n const timestamp = new Date().toISOString();\n console.error(`${timestamp} ${req.method} ${url.pathname}`);\n\n // CORS support\n if (cors) {\n res.setHeader(\"Access-Control-Allow-Origin\", \"*\");\n res.setHeader(\"Access-Control-Allow-Methods\", \"GET, POST, PUT, DELETE, OPTIONS\");\n res.setHeader(\"Access-Control-Allow-Headers\", \"Content-Type, Authorization\");\n\n if (req.method === \"OPTIONS\") {\n res.writeHead(204);\n res.end();\n return;\n }\n }\n\n // Check base path\n if (!url.pathname.startsWith(basePath)) {\n res.writeHead(404, { \"Content-Type\": \"application/json\" });\n res.end(JSON.stringify({ code: 1, error: \"Not found\" }));\n return;\n }\n\n // Convert to Web Standard Request\n const headers = new Headers();\n for (const [key, value] of Object.entries(req.headers)) {\n if (value) {\n headers.append(key, Array.isArray(value) ? value.join(\", \") : value);\n }\n }\n\n const chunks: Buffer[] = [];\n for await (const chunk of req) {\n chunks.push(chunk);\n }\n const body = Buffer.concat(chunks);\n\n const request = new Request(`http://${req.headers.host}${req.url}`, {\n method: req.method,\n headers,\n body: body.length > 0 ? body : undefined,\n });\n\n try {\n const response = await handler(request);\n res.writeHead(response.status, {\n \"Content-Type\": response.headers.get(\"Content-Type\") || \"application/json\",\n });\n const responseBody = await response.text();\n res.end(responseBody);\n } catch (error) {\n console.error(\"Error handling request:\", error);\n res.writeHead(500, { \"Content-Type\": \"application/json\" });\n res.end(JSON.stringify({ code: 5, error: \"Internal server error\" }));\n }\n });\n\n // Start listening\n await new Promise<void>((resolve, reject) => {\n server.listen(port, host, () => resolve());\n server.on(\"error\", reject);\n });\n\n const serverUrl = `http://${host}:${port}${basePath}`;\n\n // Print server info\n console.log(colors.green(\"AFS HTTP Server started\"));\n console.log(colors.bold(\"Mounted providers:\"));\n for (const m of mounts) {\n console.log(` ${colors.cyan(m.path.padEnd(20))} ${colors.dim(m.module.name)}`);\n }\n console.log(\"\");\n console.log(`${colors.dim(\"Listening on:\")} ${colors.brightCyan(serverUrl)}`);\n console.log(colors.dim(\"Press Ctrl+C to stop\"));\n\n // Graceful shutdown\n let shuttingDown = false;\n const shutdown = async () => {\n if (shuttingDown) return;\n shuttingDown = true;\n console.error(\"\\nShutting down server...\");\n server.close();\n if (onExit) {\n await onExit();\n }\n };\n\n process.on(\"SIGINT\", shutdown);\n process.on(\"SIGTERM\", shutdown);\n\n // Block until server closes\n await new Promise<void>((resolve) => {\n server.on(\"close\", resolve);\n });\n}\n"],"mappings":"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"}
@@ -1,13 +1,6 @@
1
- const require_terminal = require('./terminal.cjs');
2
1
 
3
2
  //#region src/ui/header.ts
4
3
  /**
5
- * CLI Header and Branding
6
- *
7
- * Displays the AFS logo, version, and status information
8
- * in interactive (human) mode.
9
- */
10
- /**
11
4
  * ASCII art logo for AFS
12
5
  * Clean, compact design using Unicode block characters
13
6
  */
@@ -15,37 +8,5 @@ const LOGO = `
15
8
  ▄▀█ █▀▀ █▀
16
9
  █▀█ █▀░ ▄█
17
10
  `.trimStart();
18
- /**
19
- * Tagline displayed below the logo
20
- */
21
- const TAGLINE = "Agentic File System";
22
- /**
23
- * Check if header should be displayed
24
- * Header is shown when:
25
- * - stdout is a TTY
26
- * - AFS_NO_HEADER is not set
27
- */
28
- function shouldShowHeader() {
29
- return require_terminal.isTTY() && !require_terminal.isHeaderDisabled();
30
- }
31
- /**
32
- * Format the CLI header with logo, version, and status
33
- */
34
- function formatHeader(options) {
35
- const { version, mountCount } = options;
36
- const coloredLogo = require_terminal.colors.brightCyan(LOGO);
37
- const coloredTagline = require_terminal.colors.dim(TAGLINE);
38
- const versionPart = require_terminal.colors.green(`v${version}`);
39
- const mountPart = require_terminal.colors.yellow(`${mountCount} ${mountCount === 1 ? "mount" : "mounts"}`);
40
- return `${coloredLogo}${coloredTagline}\n\n${`${versionPart} ${require_terminal.colors.dim("•")} ${mountPart}`}\n`;
41
- }
42
- /**
43
- * Print the header to stdout if conditions are met
44
- */
45
- function printHeader(options) {
46
- if (shouldShowHeader()) console.log(formatHeader(options));
47
- }
48
11
 
49
- //#endregion
50
- exports.printHeader = printHeader;
51
- exports.shouldShowHeader = shouldShowHeader;
12
+ //#endregion
@@ -1,13 +1,5 @@
1
- import { colors, isHeaderDisabled, isTTY } from "./terminal.mjs";
2
-
3
1
  //#region src/ui/header.ts
4
2
  /**
5
- * CLI Header and Branding
6
- *
7
- * Displays the AFS logo, version, and status information
8
- * in interactive (human) mode.
9
- */
10
- /**
11
3
  * ASCII art logo for AFS
12
4
  * Clean, compact design using Unicode block characters
13
5
  */
@@ -15,37 +7,7 @@ const LOGO = `
15
7
  ▄▀█ █▀▀ █▀
16
8
  █▀█ █▀░ ▄█
17
9
  `.trimStart();
18
- /**
19
- * Tagline displayed below the logo
20
- */
21
- const TAGLINE = "Agentic File System";
22
- /**
23
- * Check if header should be displayed
24
- * Header is shown when:
25
- * - stdout is a TTY
26
- * - AFS_NO_HEADER is not set
27
- */
28
- function shouldShowHeader() {
29
- return isTTY() && !isHeaderDisabled();
30
- }
31
- /**
32
- * Format the CLI header with logo, version, and status
33
- */
34
- function formatHeader(options) {
35
- const { version, mountCount } = options;
36
- const coloredLogo = colors.brightCyan(LOGO);
37
- const coloredTagline = colors.dim(TAGLINE);
38
- const versionPart = colors.green(`v${version}`);
39
- const mountPart = colors.yellow(`${mountCount} ${mountCount === 1 ? "mount" : "mounts"}`);
40
- return `${coloredLogo}${coloredTagline}\n\n${`${versionPart} ${colors.dim("•")} ${mountPart}`}\n`;
41
- }
42
- /**
43
- * Print the header to stdout if conditions are met
44
- */
45
- function printHeader(options) {
46
- if (shouldShowHeader()) console.log(formatHeader(options));
47
- }
48
10
 
49
11
  //#endregion
50
- export { printHeader, shouldShowHeader };
12
+ export { };
51
13
  //# sourceMappingURL=header.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"header.mjs","names":[],"sources":["../../src/ui/header.ts"],"sourcesContent":["/**\n * CLI Header and Branding\n *\n * Displays the AFS logo, version, and status information\n * in interactive (human) mode.\n */\n\nimport { colors, isHeaderDisabled, isTTY } from \"./terminal.js\";\n\n/**\n * ASCII art logo for AFS\n * Clean, compact design using Unicode block characters\n */\nconst LOGO = `\n▄▀█ █▀▀ █▀\n█▀█ █▀░ ▄█\n`.trimStart();\n\n/**\n * Tagline displayed below the logo\n */\nconst TAGLINE = \"Agentic File System\";\n\n/**\n * Options for header display\n */\nexport interface HeaderOptions {\n version: string;\n mountCount: number;\n}\n\n/**\n * Check if header should be displayed\n * Header is shown when:\n * - stdout is a TTY\n * - AFS_NO_HEADER is not set\n */\nexport function shouldShowHeader(): boolean {\n return isTTY() && !isHeaderDisabled();\n}\n\n/**\n * Format the CLI header with logo, version, and status\n */\nexport function formatHeader(options: HeaderOptions): string {\n const { version, mountCount } = options;\n\n // Colorize the logo\n const coloredLogo = colors.brightCyan(LOGO);\n\n // Colorize the tagline\n const coloredTagline = colors.dim(TAGLINE);\n\n // Format status line\n const versionPart = colors.green(`v${version}`);\n const mountPart = colors.yellow(`${mountCount} ${mountCount === 1 ? \"mount\" : \"mounts\"}`);\n const statusLine = `${versionPart} ${colors.dim(\"•\")} ${mountPart}`;\n\n return `${coloredLogo}${coloredTagline}\\n\\n${statusLine}\\n`;\n}\n\n/**\n * Print the header to stdout if conditions are met\n */\nexport function printHeader(options: HeaderOptions): void {\n if (shouldShowHeader()) {\n console.log(formatHeader(options));\n }\n}\n\n/**\n * Print just the logo with tagline (for exit messages etc.)\n */\nexport function printLogo(): void {\n const coloredLogo = colors.brightCyan(LOGO);\n const coloredTagline = colors.dim(TAGLINE);\n console.log(`${coloredLogo}${coloredTagline}`);\n}\n"],"mappings":";;;;;;;;;;;;;AAaA,MAAM,OAAO;;;EAGX,WAAW;;;;AAKb,MAAM,UAAU;;;;;;;AAgBhB,SAAgB,mBAA4B;AAC1C,QAAO,OAAO,IAAI,CAAC,kBAAkB;;;;;AAMvC,SAAgB,aAAa,SAAgC;CAC3D,MAAM,EAAE,SAAS,eAAe;CAGhC,MAAM,cAAc,OAAO,WAAW,KAAK;CAG3C,MAAM,iBAAiB,OAAO,IAAI,QAAQ;CAG1C,MAAM,cAAc,OAAO,MAAM,IAAI,UAAU;CAC/C,MAAM,YAAY,OAAO,OAAO,GAAG,WAAW,GAAG,eAAe,IAAI,UAAU,WAAW;AAGzF,QAAO,GAAG,cAAc,eAAe,MAFpB,GAAG,YAAY,GAAG,OAAO,IAAI,IAAI,CAAC,GAAG,YAEA;;;;;AAM1D,SAAgB,YAAY,SAA8B;AACxD,KAAI,kBAAkB,CACpB,SAAQ,IAAI,aAAa,QAAQ,CAAC"}
1
+ {"version":3,"file":"header.mjs","names":[],"sources":["../../src/ui/header.ts"],"sourcesContent":["/**\n * CLI Header and Branding\n *\n * Displays the AFS logo, version, and status information\n * in interactive (human) mode.\n */\n\nimport { colors, isHeaderDisabled, isTTY } from \"./terminal.js\";\n\n/**\n * ASCII art logo for AFS\n * Clean, compact design using Unicode block characters\n */\nconst LOGO = `\n▄▀█ █▀▀ █▀\n█▀█ █▀░ ▄█\n`.trimStart();\n\n/**\n * Tagline displayed below the logo\n */\nconst TAGLINE = \"Agentic File System\";\n\n/**\n * Options for header display\n */\nexport interface HeaderOptions {\n version: string;\n mountCount: number;\n}\n\n/**\n * Check if header should be displayed\n * Header is shown when:\n * - stdout is a TTY\n * - AFS_NO_HEADER is not set\n */\nexport function shouldShowHeader(): boolean {\n return isTTY() && !isHeaderDisabled();\n}\n\n/**\n * Format the CLI header with logo, version, and status\n */\nexport function formatHeader(options: HeaderOptions): string {\n const { version, mountCount } = options;\n\n // Colorize the logo\n const coloredLogo = colors.brightCyan(LOGO);\n\n // Colorize the tagline\n const coloredTagline = colors.dim(TAGLINE);\n\n // Format status line\n const versionPart = colors.green(`v${version}`);\n const mountPart = colors.yellow(`${mountCount} ${mountCount === 1 ? \"mount\" : \"mounts\"}`);\n const statusLine = `${versionPart} ${colors.dim(\"•\")} ${mountPart}`;\n\n return `${coloredLogo}${coloredTagline}\\n\\n${statusLine}\\n`;\n}\n\n/**\n * Print the header to stdout if conditions are met\n */\nexport function printHeader(options: HeaderOptions): void {\n if (shouldShowHeader()) {\n console.log(formatHeader(options));\n }\n}\n\n/**\n * Print just the logo with tagline (for exit messages etc.)\n */\nexport function printLogo(): void {\n const coloredLogo = colors.brightCyan(LOGO);\n const coloredTagline = colors.dim(TAGLINE);\n console.log(`${coloredLogo}${coloredTagline}`);\n}\n"],"mappings":";;;;;AAaA,MAAM,OAAO;;;EAGX,WAAW"}
package/dist/ui/index.cjs CHANGED
@@ -1,15 +1,8 @@
1
1
  const require_terminal = require('./terminal.cjs');
2
- const require_header = require('./header.cjs');
2
+ require('./header.cjs');
3
3
 
4
4
  //#region src/ui/index.ts
5
- /**
6
- * UI utilities for CLI output
7
- */
8
5
  const colors = require_terminal.colors;
9
- const printHeader = require_header.printHeader;
10
- const shouldShowHeader = require_header.shouldShowHeader;
11
6
 
12
7
  //#endregion
13
- exports.colors = colors;
14
- exports.printHeader = printHeader;
15
- exports.shouldShowHeader = shouldShowHeader;
8
+ exports.colors = colors;
package/dist/ui/index.mjs CHANGED
@@ -1,14 +1,9 @@
1
1
  import { colors as colors$1 } from "./terminal.mjs";
2
- import { printHeader as printHeader$1, shouldShowHeader as shouldShowHeader$1 } from "./header.mjs";
2
+ import "./header.mjs";
3
3
 
4
4
  //#region src/ui/index.ts
5
- /**
6
- * UI utilities for CLI output
7
- */
8
5
  const colors = colors$1;
9
- const printHeader = printHeader$1;
10
- const shouldShowHeader = shouldShowHeader$1;
11
6
 
12
7
  //#endregion
13
- export { colors, printHeader, shouldShowHeader };
8
+ export { colors };
14
9
  //# sourceMappingURL=index.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"index.mjs","names":["_colors","_printHeader","_shouldShowHeader"],"sources":["../../src/ui/index.ts"],"sourcesContent":["/**\n * UI utilities for CLI output\n */\n\n// Import and re-export header utilities\nimport {\n formatHeader as _formatHeader,\n printHeader as _printHeader,\n printLogo as _printLogo,\n shouldShowHeader as _shouldShowHeader,\n type HeaderOptions,\n} from \"./header.js\";\n// Import and re-export terminal utilities\nimport {\n colors as _colors,\n isColorDisabled as _isColorDisabled,\n isHeaderDisabled as _isHeaderDisabled,\n isTTY as _isTTY,\n shouldUseColors as _shouldUseColors,\n} from \"./terminal.js\";\n\nexport const colors = _colors;\nexport const isColorDisabled = _isColorDisabled;\nexport const isHeaderDisabled = _isHeaderDisabled;\nexport const isTTY = _isTTY;\nexport const shouldUseColors = _shouldUseColors;\nexport const formatHeader = _formatHeader;\nexport const printHeader = _printHeader;\nexport const printLogo = _printLogo;\nexport const shouldShowHeader = _shouldShowHeader;\nexport type { HeaderOptions };\n"],"mappings":";;;;;;;AAqBA,MAAa,SAASA;AAMtB,MAAa,cAAcC;AAE3B,MAAa,mBAAmBC"}
1
+ {"version":3,"file":"index.mjs","names":["_colors"],"sources":["../../src/ui/index.ts"],"sourcesContent":["/**\n * UI utilities for CLI output\n */\n\n// Import and re-export header utilities\nimport {\n formatHeader as _formatHeader,\n printHeader as _printHeader,\n printLogo as _printLogo,\n shouldShowHeader as _shouldShowHeader,\n type HeaderOptions,\n} from \"./header.js\";\n// Import and re-export terminal utilities\nimport {\n colors as _colors,\n isColorDisabled as _isColorDisabled,\n isHeaderDisabled as _isHeaderDisabled,\n isTTY as _isTTY,\n shouldUseColors as _shouldUseColors,\n} from \"./terminal.js\";\n\nexport const colors = _colors;\nexport const isColorDisabled = _isColorDisabled;\nexport const isHeaderDisabled = _isHeaderDisabled;\nexport const isTTY = _isTTY;\nexport const shouldUseColors = _shouldUseColors;\nexport const formatHeader = _formatHeader;\nexport const printHeader = _printHeader;\nexport const printLogo = _printLogo;\nexport const shouldShowHeader = _shouldShowHeader;\nexport type { HeaderOptions };\n"],"mappings":";;;;AAqBA,MAAa,SAASA"}
@@ -46,13 +46,6 @@ function isColorDisabled() {
46
46
  return process.env.NO_COLOR !== void 0;
47
47
  }
48
48
  /**
49
- * Check if header should be displayed
50
- * Disabled by AFS_NO_HEADER environment variable
51
- */
52
- function isHeaderDisabled() {
53
- return process.env.AFS_NO_HEADER !== void 0;
54
- }
55
- /**
56
49
  * Check if we should use colorized output
57
50
  * Colors are enabled when:
58
51
  * - stdout is a TTY
@@ -92,6 +85,4 @@ const colors = {
92
85
  };
93
86
 
94
87
  //#endregion
95
- exports.colors = colors;
96
- exports.isHeaderDisabled = isHeaderDisabled;
97
- exports.isTTY = isTTY;
88
+ exports.colors = colors;
@@ -45,13 +45,6 @@ function isColorDisabled() {
45
45
  return process.env.NO_COLOR !== void 0;
46
46
  }
47
47
  /**
48
- * Check if header should be displayed
49
- * Disabled by AFS_NO_HEADER environment variable
50
- */
51
- function isHeaderDisabled() {
52
- return process.env.AFS_NO_HEADER !== void 0;
53
- }
54
- /**
55
48
  * Check if we should use colorized output
56
49
  * Colors are enabled when:
57
50
  * - stdout is a TTY
@@ -91,5 +84,5 @@ const colors = {
91
84
  };
92
85
 
93
86
  //#endregion
94
- export { colors, isHeaderDisabled, isTTY };
87
+ export { colors };
95
88
  //# sourceMappingURL=terminal.mjs.map
@@ -1 +1 @@
1
- {"version":3,"file":"terminal.mjs","names":[],"sources":["../../src/ui/terminal.ts"],"sourcesContent":["/**\n * Terminal utilities for CLI output\n *\n * Handles:\n * - ANSI color codes\n * - TTY detection\n * - Environment variable checks (NO_COLOR, AFS_NO_HEADER)\n */\n\n/**\n * ANSI color codes\n */\nconst ANSI = {\n reset: \"\\x1b[0m\",\n bold: \"\\x1b[1m\",\n dim: \"\\x1b[2m\",\n\n // Foreground colors\n black: \"\\x1b[30m\",\n red: \"\\x1b[31m\",\n green: \"\\x1b[32m\",\n yellow: \"\\x1b[33m\",\n blue: \"\\x1b[34m\",\n magenta: \"\\x1b[35m\",\n cyan: \"\\x1b[36m\",\n white: \"\\x1b[37m\",\n\n // Bright foreground colors\n brightBlack: \"\\x1b[90m\",\n brightRed: \"\\x1b[91m\",\n brightGreen: \"\\x1b[92m\",\n brightYellow: \"\\x1b[93m\",\n brightBlue: \"\\x1b[94m\",\n brightMagenta: \"\\x1b[95m\",\n brightCyan: \"\\x1b[96m\",\n brightWhite: \"\\x1b[97m\",\n} as const;\n\n/**\n * Check if stdout is a TTY (interactive terminal)\n */\nexport function isTTY(): boolean {\n return process.stdout.isTTY === true;\n}\n\n/**\n * Check if colors should be disabled\n * Respects NO_COLOR environment variable (https://no-color.org/)\n */\nexport function isColorDisabled(): boolean {\n return process.env.NO_COLOR !== undefined;\n}\n\n/**\n * Check if header should be displayed\n * Disabled by AFS_NO_HEADER environment variable\n */\nexport function isHeaderDisabled(): boolean {\n return process.env.AFS_NO_HEADER !== undefined;\n}\n\n/**\n * Check if we should use colorized output\n * Colors are enabled when:\n * - stdout is a TTY\n * - NO_COLOR is not set\n */\nexport function shouldUseColors(): boolean {\n return isTTY() && !isColorDisabled();\n}\n\n/**\n * Color helper functions\n * Returns plain text if colors are disabled\n */\nexport const colors = {\n // Create a colorizer function\n _wrap: (code: string, text: string): string => {\n if (!shouldUseColors()) return text;\n return `${code}${text}${ANSI.reset}`;\n },\n\n // Basic styles\n bold: (text: string) => colors._wrap(ANSI.bold, text),\n dim: (text: string) => colors._wrap(ANSI.dim, text),\n\n // Standard colors\n red: (text: string) => colors._wrap(ANSI.red, text),\n green: (text: string) => colors._wrap(ANSI.green, text),\n yellow: (text: string) => colors._wrap(ANSI.yellow, text),\n blue: (text: string) => colors._wrap(ANSI.blue, text),\n magenta: (text: string) => colors._wrap(ANSI.magenta, text),\n cyan: (text: string) => colors._wrap(ANSI.cyan, text),\n white: (text: string) => colors._wrap(ANSI.white, text),\n\n // Bright colors\n brightCyan: (text: string) => colors._wrap(ANSI.brightCyan, text),\n brightGreen: (text: string) => colors._wrap(ANSI.brightGreen, text),\n brightYellow: (text: string) => colors._wrap(ANSI.brightYellow, text),\n brightRed: (text: string) => colors._wrap(ANSI.brightRed, text),\n\n // Semantic colors (for consistency)\n error: (text: string) => colors._wrap(ANSI.red, text),\n warning: (text: string) => colors._wrap(ANSI.yellow, text),\n success: (text: string) => colors._wrap(ANSI.green, text),\n info: (text: string) => colors._wrap(ANSI.cyan, text),\n path: (text: string) => colors._wrap(ANSI.cyan, text),\n muted: (text: string) => colors._wrap(ANSI.dim, text),\n};\n"],"mappings":";;;;;;;;;;;;AAYA,MAAM,OAAO;CACX,OAAO;CACP,MAAM;CACN,KAAK;CAGL,OAAO;CACP,KAAK;CACL,OAAO;CACP,QAAQ;CACR,MAAM;CACN,SAAS;CACT,MAAM;CACN,OAAO;CAGP,aAAa;CACb,WAAW;CACX,aAAa;CACb,cAAc;CACd,YAAY;CACZ,eAAe;CACf,YAAY;CACZ,aAAa;CACd;;;;AAKD,SAAgB,QAAiB;AAC/B,QAAO,QAAQ,OAAO,UAAU;;;;;;AAOlC,SAAgB,kBAA2B;AACzC,QAAO,QAAQ,IAAI,aAAa;;;;;;AAOlC,SAAgB,mBAA4B;AAC1C,QAAO,QAAQ,IAAI,kBAAkB;;;;;;;;AASvC,SAAgB,kBAA2B;AACzC,QAAO,OAAO,IAAI,CAAC,iBAAiB;;;;;;AAOtC,MAAa,SAAS;CAEpB,QAAQ,MAAc,SAAyB;AAC7C,MAAI,CAAC,iBAAiB,CAAE,QAAO;AAC/B,SAAO,GAAG,OAAO,OAAO,KAAK;;CAI/B,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,MAAM,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CAGnD,MAAM,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACnD,QAAQ,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CACvD,SAAS,SAAiB,OAAO,MAAM,KAAK,QAAQ,KAAK;CACzD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,UAAU,SAAiB,OAAO,MAAM,KAAK,SAAS,KAAK;CAC3D,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,QAAQ,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CAGvD,aAAa,SAAiB,OAAO,MAAM,KAAK,YAAY,KAAK;CACjE,cAAc,SAAiB,OAAO,MAAM,KAAK,aAAa,KAAK;CACnE,eAAe,SAAiB,OAAO,MAAM,KAAK,cAAc,KAAK;CACrE,YAAY,SAAiB,OAAO,MAAM,KAAK,WAAW,KAAK;CAG/D,QAAQ,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACrD,UAAU,SAAiB,OAAO,MAAM,KAAK,QAAQ,KAAK;CAC1D,UAAU,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CACzD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,QAAQ,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACtD"}
1
+ {"version":3,"file":"terminal.mjs","names":[],"sources":["../../src/ui/terminal.ts"],"sourcesContent":["/**\n * Terminal utilities for CLI output\n *\n * Handles:\n * - ANSI color codes\n * - TTY detection\n * - Environment variable checks (NO_COLOR, AFS_NO_HEADER)\n */\n\n/**\n * ANSI color codes\n */\nconst ANSI = {\n reset: \"\\x1b[0m\",\n bold: \"\\x1b[1m\",\n dim: \"\\x1b[2m\",\n\n // Foreground colors\n black: \"\\x1b[30m\",\n red: \"\\x1b[31m\",\n green: \"\\x1b[32m\",\n yellow: \"\\x1b[33m\",\n blue: \"\\x1b[34m\",\n magenta: \"\\x1b[35m\",\n cyan: \"\\x1b[36m\",\n white: \"\\x1b[37m\",\n\n // Bright foreground colors\n brightBlack: \"\\x1b[90m\",\n brightRed: \"\\x1b[91m\",\n brightGreen: \"\\x1b[92m\",\n brightYellow: \"\\x1b[93m\",\n brightBlue: \"\\x1b[94m\",\n brightMagenta: \"\\x1b[95m\",\n brightCyan: \"\\x1b[96m\",\n brightWhite: \"\\x1b[97m\",\n} as const;\n\n/**\n * Check if stdout is a TTY (interactive terminal)\n */\nexport function isTTY(): boolean {\n return process.stdout.isTTY === true;\n}\n\n/**\n * Check if colors should be disabled\n * Respects NO_COLOR environment variable (https://no-color.org/)\n */\nexport function isColorDisabled(): boolean {\n return process.env.NO_COLOR !== undefined;\n}\n\n/**\n * Check if header should be displayed\n * Disabled by AFS_NO_HEADER environment variable\n */\nexport function isHeaderDisabled(): boolean {\n return process.env.AFS_NO_HEADER !== undefined;\n}\n\n/**\n * Check if we should use colorized output\n * Colors are enabled when:\n * - stdout is a TTY\n * - NO_COLOR is not set\n */\nexport function shouldUseColors(): boolean {\n return isTTY() && !isColorDisabled();\n}\n\n/**\n * Color helper functions\n * Returns plain text if colors are disabled\n */\nexport const colors = {\n // Create a colorizer function\n _wrap: (code: string, text: string): string => {\n if (!shouldUseColors()) return text;\n return `${code}${text}${ANSI.reset}`;\n },\n\n // Basic styles\n bold: (text: string) => colors._wrap(ANSI.bold, text),\n dim: (text: string) => colors._wrap(ANSI.dim, text),\n\n // Standard colors\n red: (text: string) => colors._wrap(ANSI.red, text),\n green: (text: string) => colors._wrap(ANSI.green, text),\n yellow: (text: string) => colors._wrap(ANSI.yellow, text),\n blue: (text: string) => colors._wrap(ANSI.blue, text),\n magenta: (text: string) => colors._wrap(ANSI.magenta, text),\n cyan: (text: string) => colors._wrap(ANSI.cyan, text),\n white: (text: string) => colors._wrap(ANSI.white, text),\n\n // Bright colors\n brightCyan: (text: string) => colors._wrap(ANSI.brightCyan, text),\n brightGreen: (text: string) => colors._wrap(ANSI.brightGreen, text),\n brightYellow: (text: string) => colors._wrap(ANSI.brightYellow, text),\n brightRed: (text: string) => colors._wrap(ANSI.brightRed, text),\n\n // Semantic colors (for consistency)\n error: (text: string) => colors._wrap(ANSI.red, text),\n warning: (text: string) => colors._wrap(ANSI.yellow, text),\n success: (text: string) => colors._wrap(ANSI.green, text),\n info: (text: string) => colors._wrap(ANSI.cyan, text),\n path: (text: string) => colors._wrap(ANSI.cyan, text),\n muted: (text: string) => colors._wrap(ANSI.dim, text),\n};\n"],"mappings":";;;;;;;;;;;;AAYA,MAAM,OAAO;CACX,OAAO;CACP,MAAM;CACN,KAAK;CAGL,OAAO;CACP,KAAK;CACL,OAAO;CACP,QAAQ;CACR,MAAM;CACN,SAAS;CACT,MAAM;CACN,OAAO;CAGP,aAAa;CACb,WAAW;CACX,aAAa;CACb,cAAc;CACd,YAAY;CACZ,eAAe;CACf,YAAY;CACZ,aAAa;CACd;;;;AAKD,SAAgB,QAAiB;AAC/B,QAAO,QAAQ,OAAO,UAAU;;;;;;AAOlC,SAAgB,kBAA2B;AACzC,QAAO,QAAQ,IAAI,aAAa;;;;;;;;AAiBlC,SAAgB,kBAA2B;AACzC,QAAO,OAAO,IAAI,CAAC,iBAAiB;;;;;;AAOtC,MAAa,SAAS;CAEpB,QAAQ,MAAc,SAAyB;AAC7C,MAAI,CAAC,iBAAiB,CAAE,QAAO;AAC/B,SAAO,GAAG,OAAO,OAAO,KAAK;;CAI/B,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,MAAM,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CAGnD,MAAM,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACnD,QAAQ,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CACvD,SAAS,SAAiB,OAAO,MAAM,KAAK,QAAQ,KAAK;CACzD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,UAAU,SAAiB,OAAO,MAAM,KAAK,SAAS,KAAK;CAC3D,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,QAAQ,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CAGvD,aAAa,SAAiB,OAAO,MAAM,KAAK,YAAY,KAAK;CACjE,cAAc,SAAiB,OAAO,MAAM,KAAK,aAAa,KAAK;CACnE,eAAe,SAAiB,OAAO,MAAM,KAAK,cAAc,KAAK;CACrE,YAAY,SAAiB,OAAO,MAAM,KAAK,WAAW,KAAK;CAG/D,QAAQ,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACrD,UAAU,SAAiB,OAAO,MAAM,KAAK,QAAQ,KAAK;CAC1D,UAAU,SAAiB,OAAO,MAAM,KAAK,OAAO,KAAK;CACzD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,OAAO,SAAiB,OAAO,MAAM,KAAK,MAAM,KAAK;CACrD,QAAQ,SAAiB,OAAO,MAAM,KAAK,KAAK,KAAK;CACtD"}