@synap-core/cli 1.11.0 → 1.13.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (533) hide show
  1. package/LICENSE +21 -0
  2. package/README.md +40 -198
  3. package/dist/build-info.json +6 -0
  4. package/dist/commands/agent-run.js +3 -2
  5. package/dist/commands/agent-run.js.map +1 -1
  6. package/dist/commands/agents.d.ts +32 -17
  7. package/dist/commands/agents.js +203 -237
  8. package/dist/commands/agents.js.map +1 -1
  9. package/dist/commands/app.d.ts +143 -0
  10. package/dist/commands/app.js +524 -0
  11. package/dist/commands/app.js.map +1 -0
  12. package/dist/commands/automate.d.ts +21 -0
  13. package/dist/commands/automate.js +42 -0
  14. package/dist/commands/automate.js.map +1 -0
  15. package/dist/commands/automation-schema.test.d.ts +16 -0
  16. package/dist/commands/automation-schema.test.js +77 -0
  17. package/dist/commands/automation-schema.test.js.map +1 -0
  18. package/dist/commands/automation.d.ts +12 -0
  19. package/dist/commands/automation.js +116 -66
  20. package/dist/commands/automation.js.map +1 -1
  21. package/dist/commands/box.d.ts +42 -0
  22. package/dist/commands/box.js +89 -0
  23. package/dist/commands/box.js.map +1 -0
  24. package/dist/commands/bridge-setup.d.ts +14 -1
  25. package/dist/commands/bridge-setup.js +395 -129
  26. package/dist/commands/bridge-setup.js.map +1 -1
  27. package/dist/commands/cap-connections.d.ts +4 -4
  28. package/dist/commands/cap-connections.js +14 -14
  29. package/dist/commands/cap-connections.js.map +1 -1
  30. package/dist/commands/capability.d.ts +3 -1
  31. package/dist/commands/capability.js +249 -176
  32. package/dist/commands/capability.js.map +1 -1
  33. package/dist/commands/catalog.d.ts +275 -0
  34. package/dist/commands/catalog.js +481 -0
  35. package/dist/commands/catalog.js.map +1 -0
  36. package/dist/commands/cell.d.ts +155 -8
  37. package/dist/commands/cell.js +416 -40
  38. package/dist/commands/cell.js.map +1 -1
  39. package/dist/commands/centrality.js +1 -13
  40. package/dist/commands/centrality.js.map +1 -1
  41. package/dist/commands/close-questions.d.ts +27 -0
  42. package/dist/commands/close-questions.js +49 -0
  43. package/dist/commands/close-questions.js.map +1 -0
  44. package/dist/commands/close-questions.test.d.ts +1 -0
  45. package/dist/commands/close-questions.test.js +52 -0
  46. package/dist/commands/close-questions.test.js.map +1 -0
  47. package/dist/commands/connect.d.ts +36 -13
  48. package/dist/commands/connect.js +68 -167
  49. package/dist/commands/connect.js.map +1 -1
  50. package/dist/commands/connections.d.ts +3 -2
  51. package/dist/commands/connections.js +95 -25
  52. package/dist/commands/connections.js.map +1 -1
  53. package/dist/commands/context.js +79 -44
  54. package/dist/commands/context.js.map +1 -1
  55. package/dist/commands/data-extra.d.ts +34 -0
  56. package/dist/commands/data-extra.js +203 -25
  57. package/dist/commands/data-extra.js.map +1 -1
  58. package/dist/commands/data.d.ts +120 -2
  59. package/dist/commands/data.js +295 -21
  60. package/dist/commands/data.js.map +1 -1
  61. package/dist/commands/diagnose.d.ts +66 -4
  62. package/dist/commands/diagnose.js +285 -28
  63. package/dist/commands/diagnose.js.map +1 -1
  64. package/dist/commands/doc.d.ts +11 -4
  65. package/dist/commands/doc.js +39 -14
  66. package/dist/commands/doc.js.map +1 -1
  67. package/dist/commands/doctor.d.ts +133 -3
  68. package/dist/commands/doctor.js +761 -41
  69. package/dist/commands/doctor.js.map +1 -1
  70. package/dist/commands/explain.js +5 -5
  71. package/dist/commands/explain.js.map +1 -1
  72. package/dist/commands/hooks.d.ts +19 -0
  73. package/dist/commands/hooks.js +70 -0
  74. package/dist/commands/hooks.js.map +1 -0
  75. package/dist/commands/import.d.ts +393 -13
  76. package/dist/commands/import.js +1150 -54
  77. package/dist/commands/import.js.map +1 -1
  78. package/dist/commands/init.d.ts +34 -9
  79. package/dist/commands/init.js +481 -981
  80. package/dist/commands/init.js.map +1 -1
  81. package/dist/commands/keys.d.ts +1 -0
  82. package/dist/commands/keys.js +15 -2
  83. package/dist/commands/keys.js.map +1 -1
  84. package/dist/commands/knowledge.d.ts +22 -6
  85. package/dist/commands/knowledge.js +121 -57
  86. package/dist/commands/knowledge.js.map +1 -1
  87. package/dist/commands/lens.d.ts +37 -1
  88. package/dist/commands/lens.js +194 -72
  89. package/dist/commands/lens.js.map +1 -1
  90. package/dist/commands/market-authoring.d.ts +29 -2
  91. package/dist/commands/market-authoring.js +348 -7
  92. package/dist/commands/market-authoring.js.map +1 -1
  93. package/dist/commands/market-official.d.ts +58 -0
  94. package/dist/commands/market-official.js +84 -0
  95. package/dist/commands/market-official.js.map +1 -0
  96. package/dist/commands/market.d.ts +400 -16
  97. package/dist/commands/market.js +1802 -146
  98. package/dist/commands/market.js.map +1 -1
  99. package/dist/commands/mcp.d.ts +60 -25
  100. package/dist/commands/mcp.js +251 -64
  101. package/dist/commands/mcp.js.map +1 -1
  102. package/dist/commands/observe.category.test.d.ts +1 -0
  103. package/dist/commands/observe.category.test.js +59 -0
  104. package/dist/commands/observe.category.test.js.map +1 -0
  105. package/dist/commands/observe.d.ts +3 -0
  106. package/dist/commands/observe.js +7 -5
  107. package/dist/commands/observe.js.map +1 -1
  108. package/dist/commands/observe.title.test.d.ts +1 -0
  109. package/dist/commands/observe.title.test.js +37 -0
  110. package/dist/commands/observe.title.test.js.map +1 -0
  111. package/dist/commands/open.d.ts +39 -9
  112. package/dist/commands/open.js +80 -25
  113. package/dist/commands/open.js.map +1 -1
  114. package/dist/commands/playbook.d.ts +42 -0
  115. package/dist/commands/playbook.js +171 -0
  116. package/dist/commands/playbook.js.map +1 -0
  117. package/dist/commands/pod.js +1 -1
  118. package/dist/commands/pod.js.map +1 -1
  119. package/dist/commands/pods.d.ts +11 -1
  120. package/dist/commands/pods.js +129 -131
  121. package/dist/commands/pods.js.map +1 -1
  122. package/dist/commands/proposals-actions.d.ts +62 -0
  123. package/dist/commands/proposals-actions.js +143 -8
  124. package/dist/commands/proposals-actions.js.map +1 -1
  125. package/dist/commands/proposals-await.d.ts +68 -0
  126. package/dist/commands/proposals-await.js +248 -0
  127. package/dist/commands/proposals-await.js.map +1 -0
  128. package/dist/commands/proton-setup.d.ts +73 -0
  129. package/dist/commands/proton-setup.js +579 -0
  130. package/dist/commands/proton-setup.js.map +1 -0
  131. package/dist/commands/providers.d.ts +23 -0
  132. package/dist/commands/providers.js +126 -1
  133. package/dist/commands/providers.js.map +1 -1
  134. package/dist/commands/raycast.js +6 -2
  135. package/dist/commands/raycast.js.map +1 -1
  136. package/dist/commands/rule.d.ts +150 -0
  137. package/dist/commands/rule.js +447 -0
  138. package/dist/commands/rule.js.map +1 -0
  139. package/dist/commands/session-feed-wait.d.ts +48 -0
  140. package/dist/commands/session-feed-wait.js +261 -0
  141. package/dist/commands/session-feed-wait.js.map +1 -0
  142. package/dist/commands/session-post.d.ts +40 -0
  143. package/dist/commands/session-post.js +96 -0
  144. package/dist/commands/session-post.js.map +1 -0
  145. package/dist/commands/session-wait.d.ts +116 -0
  146. package/dist/commands/session-wait.js +224 -0
  147. package/dist/commands/session-wait.js.map +1 -0
  148. package/dist/commands/sessions.d.ts +54 -0
  149. package/dist/commands/sessions.js +501 -58
  150. package/dist/commands/sessions.js.map +1 -1
  151. package/dist/commands/skill-manage.d.ts +21 -0
  152. package/dist/commands/skill-manage.js +136 -19
  153. package/dist/commands/skill-manage.js.map +1 -1
  154. package/dist/commands/skills-commands.d.ts +2 -0
  155. package/dist/commands/skills-commands.js +9 -1
  156. package/dist/commands/skills-commands.js.map +1 -1
  157. package/dist/commands/skills-commands.test.d.ts +1 -0
  158. package/dist/commands/skills-commands.test.js +57 -0
  159. package/dist/commands/skills-commands.test.js.map +1 -0
  160. package/dist/commands/skills.js +16 -0
  161. package/dist/commands/skills.js.map +1 -1
  162. package/dist/commands/status.d.ts +1 -4
  163. package/dist/commands/status.js +6 -35
  164. package/dist/commands/status.js.map +1 -1
  165. package/dist/commands/statusline.backoff.test.d.ts +13 -0
  166. package/dist/commands/statusline.backoff.test.js +100 -0
  167. package/dist/commands/statusline.backoff.test.js.map +1 -0
  168. package/dist/commands/statusline.js +16 -9
  169. package/dist/commands/statusline.js.map +1 -1
  170. package/dist/commands/sync-status.d.ts +12 -0
  171. package/dist/commands/sync-status.js +125 -0
  172. package/dist/commands/sync-status.js.map +1 -0
  173. package/dist/commands/templates-retire.d.ts +34 -0
  174. package/dist/commands/templates-retire.js +192 -0
  175. package/dist/commands/templates-retire.js.map +1 -0
  176. package/dist/commands/tools.js +6 -21
  177. package/dist/commands/tools.js.map +1 -1
  178. package/dist/commands/tracks.d.ts +112 -0
  179. package/dist/commands/tracks.js +543 -0
  180. package/dist/commands/tracks.js.map +1 -0
  181. package/dist/commands/update.d.ts +3 -11
  182. package/dist/commands/update.js +5 -134
  183. package/dist/commands/update.js.map +1 -1
  184. package/dist/commands/upload.d.ts +41 -3
  185. package/dist/commands/upload.js +120 -18
  186. package/dist/commands/upload.js.map +1 -1
  187. package/dist/commands/vendor.d.ts +28 -0
  188. package/dist/commands/vendor.js +110 -0
  189. package/dist/commands/vendor.js.map +1 -0
  190. package/dist/commands/versions.js +6 -0
  191. package/dist/commands/versions.js.map +1 -1
  192. package/dist/commands/view.js +10 -5
  193. package/dist/commands/view.js.map +1 -1
  194. package/dist/commands/whoami.d.ts +30 -3
  195. package/dist/commands/whoami.js +186 -23
  196. package/dist/commands/whoami.js.map +1 -1
  197. package/dist/commands/worker-accounts.d.ts +149 -0
  198. package/dist/commands/worker-accounts.js +339 -0
  199. package/dist/commands/worker-accounts.js.map +1 -0
  200. package/dist/commands/worker-accounts.test.d.ts +1 -0
  201. package/dist/commands/worker-accounts.test.js +224 -0
  202. package/dist/commands/worker-accounts.test.js.map +1 -0
  203. package/dist/commands/worker.d.ts +331 -0
  204. package/dist/commands/worker.js +1067 -0
  205. package/dist/commands/worker.js.map +1 -0
  206. package/dist/commands/worker.test.d.ts +1 -0
  207. package/dist/commands/worker.test.js +427 -0
  208. package/dist/commands/worker.test.js.map +1 -0
  209. package/dist/commands/workspace-ops.d.ts +35 -0
  210. package/dist/commands/workspace-ops.js +153 -0
  211. package/dist/commands/workspace-ops.js.map +1 -0
  212. package/dist/index.d.ts +6 -6
  213. package/dist/index.js +1043 -186
  214. package/dist/index.js.map +1 -1
  215. package/dist/lib/agent-connections.d.ts +31 -0
  216. package/dist/lib/agent-connections.js +33 -0
  217. package/dist/lib/agent-connections.js.map +1 -0
  218. package/dist/lib/agent-detect.d.ts +27 -0
  219. package/dist/lib/agent-detect.js +71 -0
  220. package/dist/lib/agent-detect.js.map +1 -0
  221. package/dist/lib/agent-door.d.ts +136 -0
  222. package/dist/lib/agent-door.js +429 -0
  223. package/dist/lib/agent-door.js.map +1 -0
  224. package/dist/lib/agents-config.d.ts +2 -0
  225. package/dist/lib/agents-config.js +4 -9
  226. package/dist/lib/agents-config.js.map +1 -1
  227. package/dist/lib/approval-poll.d.ts +31 -2
  228. package/dist/lib/approval-poll.js +20 -7
  229. package/dist/lib/approval-poll.js.map +1 -1
  230. package/dist/lib/atomic-file.d.ts +48 -0
  231. package/dist/lib/atomic-file.js +129 -0
  232. package/dist/lib/atomic-file.js.map +1 -0
  233. package/dist/lib/auth.d.ts +17 -11
  234. package/dist/lib/auth.js +47 -64
  235. package/dist/lib/auth.js.map +1 -1
  236. package/dist/lib/batch-approval.d.ts +85 -0
  237. package/dist/lib/batch-approval.js +170 -0
  238. package/dist/lib/batch-approval.js.map +1 -0
  239. package/dist/lib/box/egress.d.ts +82 -0
  240. package/dist/lib/box/egress.js +264 -0
  241. package/dist/lib/box/egress.js.map +1 -0
  242. package/dist/lib/box/evidence.d.ts +86 -0
  243. package/dist/lib/box/evidence.js +121 -0
  244. package/dist/lib/box/evidence.js.map +1 -0
  245. package/dist/lib/box/job-server.d.ts +72 -0
  246. package/dist/lib/box/job-server.js +246 -0
  247. package/dist/lib/box/job-server.js.map +1 -0
  248. package/dist/lib/box/provisioner.d.ts +83 -0
  249. package/dist/lib/box/provisioner.js +312 -0
  250. package/dist/lib/box/provisioner.js.map +1 -0
  251. package/dist/lib/box/proxmox.d.ts +112 -0
  252. package/dist/lib/box/proxmox.js +211 -0
  253. package/dist/lib/box/proxmox.js.map +1 -0
  254. package/dist/lib/box/wire.d.ts +98 -0
  255. package/dist/lib/box/wire.js +70 -0
  256. package/dist/lib/box/wire.js.map +1 -0
  257. package/dist/lib/capture-lane.d.ts +6 -5
  258. package/dist/lib/capture-lane.js +6 -5
  259. package/dist/lib/capture-lane.js.map +1 -1
  260. package/dist/lib/capture-structure.d.ts +230 -11
  261. package/dist/lib/capture-structure.js +251 -13
  262. package/dist/lib/capture-structure.js.map +1 -1
  263. package/dist/lib/catalog-templates.d.ts +59 -0
  264. package/dist/lib/catalog-templates.js +126 -0
  265. package/dist/lib/catalog-templates.js.map +1 -0
  266. package/dist/lib/cli-build.d.ts +19 -0
  267. package/dist/lib/cli-build.js +37 -0
  268. package/dist/lib/cli-build.js.map +1 -0
  269. package/dist/lib/client-header.test.d.ts +1 -0
  270. package/dist/lib/client-header.test.js +85 -0
  271. package/dist/lib/client-header.test.js.map +1 -0
  272. package/dist/lib/conversation-headers.d.ts +33 -0
  273. package/dist/lib/conversation-headers.js +69 -0
  274. package/dist/lib/conversation-headers.js.map +1 -0
  275. package/dist/lib/cp-packages.d.ts +167 -11
  276. package/dist/lib/cp-packages.js +253 -21
  277. package/dist/lib/cp-packages.js.map +1 -1
  278. package/dist/lib/credential-class.d.ts +144 -0
  279. package/dist/lib/credential-class.js +138 -0
  280. package/dist/lib/credential-class.js.map +1 -0
  281. package/dist/lib/describe-lens.d.ts +35 -0
  282. package/dist/lib/describe-lens.js +40 -0
  283. package/dist/lib/describe-lens.js.map +1 -1
  284. package/dist/lib/device-connect.d.ts +125 -0
  285. package/dist/lib/device-connect.js +256 -0
  286. package/dist/lib/device-connect.js.map +1 -0
  287. package/dist/lib/directory-lens.d.ts +99 -0
  288. package/dist/lib/directory-lens.js +187 -0
  289. package/dist/lib/directory-lens.js.map +1 -0
  290. package/dist/lib/exporter-coverage.d.ts +71 -0
  291. package/dist/lib/exporter-coverage.js +97 -0
  292. package/dist/lib/exporter-coverage.js.map +1 -0
  293. package/dist/lib/goal-words.d.ts +38 -0
  294. package/dist/lib/goal-words.js +112 -0
  295. package/dist/lib/goal-words.js.map +1 -0
  296. package/dist/lib/hub-client.d.ts +57 -15
  297. package/dist/lib/hub-client.js +396 -82
  298. package/dist/lib/hub-client.js.map +1 -1
  299. package/dist/lib/init-connect.d.ts +41 -0
  300. package/dist/lib/init-connect.js +75 -0
  301. package/dist/lib/init-connect.js.map +1 -0
  302. package/dist/lib/init-exit.d.ts +24 -0
  303. package/dist/lib/init-exit.js +41 -0
  304. package/dist/lib/init-exit.js.map +1 -0
  305. package/dist/lib/init-flow.d.ts +25 -0
  306. package/dist/lib/init-flow.js +40 -0
  307. package/dist/lib/init-flow.js.map +1 -0
  308. package/dist/lib/init-handoff.d.ts +24 -0
  309. package/dist/lib/init-handoff.js +26 -0
  310. package/dist/lib/init-handoff.js.map +1 -0
  311. package/dist/lib/init-output.d.ts +18 -0
  312. package/dist/lib/init-output.js +43 -0
  313. package/dist/lib/init-output.js.map +1 -0
  314. package/dist/lib/init-pod.d.ts +45 -0
  315. package/dist/lib/init-pod.js +36 -0
  316. package/dist/lib/init-pod.js.map +1 -0
  317. package/dist/lib/installed.d.ts +210 -11
  318. package/dist/lib/installed.js +234 -36
  319. package/dist/lib/installed.js.map +1 -1
  320. package/dist/lib/key-approval.d.ts +57 -0
  321. package/dist/lib/key-approval.js +117 -0
  322. package/dist/lib/key-approval.js.map +1 -0
  323. package/dist/lib/key-diagnosis.d.ts +56 -0
  324. package/dist/lib/key-diagnosis.js +227 -0
  325. package/dist/lib/key-diagnosis.js.map +1 -0
  326. package/dist/lib/key-doctor.d.ts +136 -0
  327. package/dist/lib/key-doctor.js +286 -0
  328. package/dist/lib/key-doctor.js.map +1 -0
  329. package/dist/lib/key-locations.d.ts +120 -0
  330. package/dist/lib/key-locations.js +326 -0
  331. package/dist/lib/key-locations.js.map +1 -0
  332. package/dist/lib/key-source.d.ts +68 -0
  333. package/dist/lib/key-source.js +109 -0
  334. package/dist/lib/key-source.js.map +1 -0
  335. package/dist/lib/key-state.d.ts +70 -0
  336. package/dist/lib/key-state.js +115 -0
  337. package/dist/lib/key-state.js.map +1 -0
  338. package/dist/lib/kind-package.d.ts +181 -0
  339. package/dist/lib/kind-package.js +679 -0
  340. package/dist/lib/kind-package.js.map +1 -0
  341. package/dist/lib/knowledge-title.d.ts +25 -0
  342. package/dist/lib/knowledge-title.js +47 -0
  343. package/dist/lib/knowledge-title.js.map +1 -0
  344. package/dist/lib/knowledge-title.test.d.ts +1 -0
  345. package/dist/lib/knowledge-title.test.js +34 -0
  346. package/dist/lib/knowledge-title.test.js.map +1 -0
  347. package/dist/lib/machine-instance.d.ts +64 -0
  348. package/dist/lib/machine-instance.js +142 -0
  349. package/dist/lib/machine-instance.js.map +1 -0
  350. package/dist/lib/mcp-bridge.d.ts +49 -0
  351. package/dist/lib/mcp-bridge.js +180 -0
  352. package/dist/lib/mcp-bridge.js.map +1 -0
  353. package/dist/lib/mcp-bridge.test.d.ts +1 -0
  354. package/dist/lib/mcp-bridge.test.js +118 -0
  355. package/dist/lib/mcp-bridge.test.js.map +1 -0
  356. package/dist/lib/mcp-call.d.ts +30 -0
  357. package/dist/lib/mcp-call.js +107 -0
  358. package/dist/lib/mcp-call.js.map +1 -0
  359. package/dist/lib/mcp-snippets.d.ts +53 -0
  360. package/dist/lib/mcp-snippets.js +82 -0
  361. package/dist/lib/mcp-snippets.js.map +1 -0
  362. package/dist/lib/next-steps.d.ts +8 -0
  363. package/dist/lib/next-steps.js +31 -1
  364. package/dist/lib/next-steps.js.map +1 -1
  365. package/dist/lib/openclaw.js +3 -2
  366. package/dist/lib/openclaw.js.map +1 -1
  367. package/dist/lib/package-wire.d.ts +179 -0
  368. package/dist/lib/package-wire.js +68 -0
  369. package/dist/lib/package-wire.js.map +1 -0
  370. package/dist/lib/pair-link.d.ts +38 -0
  371. package/dist/lib/pair-link.js +68 -0
  372. package/dist/lib/pair-link.js.map +1 -0
  373. package/dist/lib/pod-moved.d.ts +70 -0
  374. package/dist/lib/pod-moved.js +146 -0
  375. package/dist/lib/pod-moved.js.map +1 -0
  376. package/dist/lib/pod-reach.d.ts +39 -0
  377. package/dist/lib/pod-reach.js +117 -0
  378. package/dist/lib/pod-reach.js.map +1 -0
  379. package/dist/lib/pod-reach.test.d.ts +1 -0
  380. package/dist/lib/pod-reach.test.js +67 -0
  381. package/dist/lib/pod-reach.test.js.map +1 -0
  382. package/dist/lib/pod-wide.d.ts +40 -0
  383. package/dist/lib/pod-wide.js +46 -0
  384. package/dist/lib/pod-wide.js.map +1 -0
  385. package/dist/lib/pod.d.ts +74 -112
  386. package/dist/lib/pod.js +146 -415
  387. package/dist/lib/pod.js.map +1 -1
  388. package/dist/lib/project-ref.d.ts +9 -3
  389. package/dist/lib/project-ref.js +10 -4
  390. package/dist/lib/project-ref.js.map +1 -1
  391. package/dist/lib/register-claude-code-mcp.test.d.ts +1 -0
  392. package/dist/lib/register-claude-code-mcp.test.js +78 -0
  393. package/dist/lib/register-claude-code-mcp.test.js.map +1 -0
  394. package/dist/lib/review-credential.d.ts +119 -0
  395. package/dist/lib/review-credential.js +149 -0
  396. package/dist/lib/review-credential.js.map +1 -0
  397. package/dist/lib/safe-open.d.ts +49 -0
  398. package/dist/lib/safe-open.js +119 -0
  399. package/dist/lib/safe-open.js.map +1 -0
  400. package/dist/lib/session-feed.d.ts +185 -0
  401. package/dist/lib/session-feed.js +257 -0
  402. package/dist/lib/session-feed.js.map +1 -0
  403. package/dist/lib/session-lens.d.ts +40 -1
  404. package/dist/lib/session-lens.js +54 -4
  405. package/dist/lib/session-lens.js.map +1 -1
  406. package/dist/lib/superwhisper-import.d.ts +8 -0
  407. package/dist/lib/superwhisper-import.js +14 -7
  408. package/dist/lib/superwhisper-import.js.map +1 -1
  409. package/dist/lib/superwhisper-title.test.d.ts +1 -0
  410. package/dist/lib/superwhisper-title.test.js +18 -0
  411. package/dist/lib/superwhisper-title.test.js.map +1 -0
  412. package/dist/lib/targets.d.ts +152 -10
  413. package/dist/lib/targets.js +974 -325
  414. package/dist/lib/targets.js.map +1 -1
  415. package/dist/lib/template-file.d.ts +4 -0
  416. package/dist/lib/template-file.js.map +1 -1
  417. package/dist/lib/template-lifecycle.d.ts +217 -0
  418. package/dist/lib/template-lifecycle.js +433 -0
  419. package/dist/lib/template-lifecycle.js.map +1 -0
  420. package/dist/lib/template-steps.d.ts +88 -0
  421. package/dist/lib/template-steps.js +118 -0
  422. package/dist/lib/template-steps.js.map +1 -0
  423. package/dist/lib/time-ago.d.ts +2 -0
  424. package/dist/lib/time-ago.js +15 -0
  425. package/dist/lib/time-ago.js.map +1 -0
  426. package/dist/lib/wake-hook-settings.d.ts +57 -0
  427. package/dist/lib/wake-hook-settings.js +153 -0
  428. package/dist/lib/wake-hook-settings.js.map +1 -0
  429. package/dist/lib/wake-state.d.ts +65 -0
  430. package/dist/lib/wake-state.js +122 -0
  431. package/dist/lib/wake-state.js.map +1 -0
  432. package/dist/utils/logger.js +5 -2
  433. package/dist/utils/logger.js.map +1 -1
  434. package/package.json +26 -17
  435. package/skills/README.md +13 -11
  436. package/skills/agent-os/SKILL.md +214 -99
  437. package/skills/manifest.json +1 -1
  438. package/skills/onboard/SKILL.md +55 -26
  439. package/skills/synap/README.md +5 -8
  440. package/skills/synap/SKILL.md +1149 -289
  441. package/skills/synap/_order.txt +7 -0
  442. package/skills/synap/_skill.yaml +1 -1
  443. package/skills/synap/automations.md +15 -0
  444. package/skills/synap/capture.md +5 -0
  445. package/skills/synap/cli-operations.md +24 -18
  446. package/skills/synap/code-skills.md +70 -0
  447. package/skills/synap/concepts.md +36 -0
  448. package/skills/synap/content-os.md +10 -1
  449. package/skills/synap/creative-loop.md +15 -10
  450. package/skills/synap/crm.md +21 -52
  451. package/skills/synap/document-embeds.md +143 -47
  452. package/skills/synap/escalation-ladder.md +20 -10
  453. package/skills/synap/focus-sessions.md +56 -21
  454. package/skills/synap/from-intent.md +158 -0
  455. package/skills/synap/governance-rules.md +5 -5
  456. package/skills/synap/governance.md +10 -7
  457. package/skills/synap/hand-off.md +33 -0
  458. package/skills/synap/inline-patterns.md +15 -7
  459. package/skills/synap/lenses.md +34 -16
  460. package/skills/synap/linking.md +42 -41
  461. package/skills/synap/mcp-remote-servers.md +64 -0
  462. package/skills/synap/mental-model.md +17 -15
  463. package/skills/synap/operating-mode-rules.md +2 -2
  464. package/skills/synap/processes.md +118 -0
  465. package/skills/synap/quick-reference.md +7 -2
  466. package/skills/synap/reading.md +3 -1
  467. package/skills/synap/reflexes.md +12 -42
  468. package/skills/synap/viewframe-cells.md +38 -5
  469. package/skills/synap/work-flow.md +1 -1
  470. package/skills/synap/work-model.md +110 -0
  471. package/skills/synap/worked-examples.md +4 -5
  472. package/skills/synap/workspace-design.md +15 -11
  473. package/skills/synap/writes.md +105 -25
  474. package/skills/synap/writing-titles.md +63 -0
  475. package/skills/synap-app/SKILL.md +149 -67
  476. package/skills/synap-app/_skill.yaml +1 -1
  477. package/skills/synap-app/creating-the-base-app.md +12 -7
  478. package/skills/synap-app/governance.md +27 -16
  479. package/skills/synap-app/install-commands.md +18 -9
  480. package/skills/synap-app/overview.md +16 -9
  481. package/skills/synap-app/using-the-sdk.md +75 -25
  482. package/skills/synap-design/SKILL.md +474 -0
  483. package/skills/synap-design/_order.txt +4 -0
  484. package/skills/synap-design/_skill.yaml +21 -0
  485. package/skills/synap-design/loop.md +134 -0
  486. package/skills/synap-design/overview.md +44 -0
  487. package/skills/synap-design/principles.md +130 -0
  488. package/skills/synap-design/system.md +133 -0
  489. package/skills/synap-market/SKILL.md +306 -16
  490. package/skills/synap-market/_skill.yaml +1 -1
  491. package/skills/synap-market/author-and-publish.md +145 -8
  492. package/skills/synap-market/governance-and-catalog.md +7 -0
  493. package/skills/synap-market/install.md +79 -1
  494. package/skills/synap-market/overview.md +74 -6
  495. package/skills/synap-schema/SKILL.md +172 -10
  496. package/skills/synap-schema/_order.txt +2 -0
  497. package/skills/synap-schema/_skill.yaml +4 -2
  498. package/skills/synap-schema/common-mistakes.md +4 -2
  499. package/skills/synap-schema/discover-profiles.md +1 -1
  500. package/skills/synap-schema/entity-scope.md +15 -3
  501. package/skills/synap-schema/extend-first.md +29 -0
  502. package/skills/synap-schema/extend-vs-create.md +1 -1
  503. package/skills/synap-schema/intent-vocabulary-ssot.md +111 -0
  504. package/skills/synap-schema/property-types.md +1 -1
  505. package/skills/synap-schema/relations.md +1 -1
  506. package/skills/synap-ui/SKILL.md +19 -12
  507. package/skills/synap-ui/_skill.yaml +1 -1
  508. package/skills/synap-ui/ai-companion.md +1 -1
  509. package/skills/synap-ui/arranging-bento.md +2 -0
  510. package/skills/synap-ui/bento-layouts.md +10 -10
  511. package/skills/synap-ui/bento-recipes.md +313 -543
  512. package/skills/synap-ui/four-builds.md +5 -0
  513. package/skills/synap-ui/view-types.md +2 -2
  514. package/skills/synap-ui/widget-catalog.md +22 -278
  515. package/templates/automations/bookmark-enrichment.automation.json +290 -13
  516. package/templates/automations/url-bookmark-capture.automation.json +73 -11
  517. package/templates/box/runner.py +206 -0
  518. package/templates/skills/authoring-playbooks/SKILL.md +6 -3
  519. package/templates/skills/authoring-playbooks/reference/stages-contract.md +15 -0
  520. package/templates/skills/authoring-playbooks/reference/worked-example.md +3 -0
  521. package/dist/commands/infra.d.ts +0 -21
  522. package/dist/commands/infra.js +0 -262
  523. package/dist/commands/infra.js.map +0 -1
  524. package/node_modules/@synap/hub-rest-client/dist/index.cjs +0 -1261
  525. package/node_modules/@synap/hub-rest-client/dist/index.d.cts +0 -1647
  526. package/node_modules/@synap/hub-rest-client/dist/index.d.ts +0 -1647
  527. package/node_modules/@synap/hub-rest-client/dist/index.js +0 -1231
  528. package/node_modules/@synap/hub-rest-client/package.json +0 -45
  529. package/node_modules/@synap/hub-rest-client/src/client.ts +0 -1631
  530. package/node_modules/@synap/hub-rest-client/src/errors.ts +0 -30
  531. package/node_modules/@synap/hub-rest-client/src/index.ts +0 -153
  532. package/node_modules/@synap/hub-rest-client/src/setup.ts +0 -133
  533. package/node_modules/@synap/hub-rest-client/src/types.ts +0 -1299
@@ -0,0 +1,85 @@
1
+ /**
2
+ * One-click approval for the agent keys `synap init` mints (V1 D5).
3
+ *
4
+ * Codex and Cursor each mint their agent key with `requireApproval`, and
5
+ * `provisionAgentKey` used to open one review page per key and block on it.
6
+ * Connecting both meant two pages and two clicks, one after the other.
7
+ *
8
+ * Now `init` mints every key that needs approval FIRST (deferred), opens ONE
9
+ * page (`/approve-agents?keys=…` on the pod admin, backed by
10
+ * `POST /api/hub/setup/agent/pending/approve-batch`), and polls every key
11
+ * until the person approves them together. The approved keys are then handed
12
+ * to the installers through `takePreApprovedKey`, so each installer's own
13
+ * `provisionAgentKey` call returns the key the person already approved instead
14
+ * of minting a second one.
15
+ *
16
+ * A pod older than the batch door has no `/approve-agents` page: `init`
17
+ * probes the batch lookup door first and, when it is missing, opens each
18
+ * key's own review page instead (every pod version serves those).
19
+ */
20
+ import type { TargetName } from "./targets.js";
21
+ /** How a target's installer mints its agent key — ONE table, read by both. */
22
+ export interface KeyMintSpec {
23
+ agentType: string;
24
+ idempotent: boolean;
25
+ }
26
+ /**
27
+ * The targets whose installer mints an agent key that needs the person's
28
+ * approval. Claude Code mints without approval, so it is not here. The installers read their spec from this table
29
+ * (`installCodex` / `installCursor`), so the pre-mint cannot ask for a key the
30
+ * installer would not have asked for.
31
+ */
32
+ export declare const TARGET_KEY_MINT: Partial<Record<TargetName, KeyMintSpec>>;
33
+ export interface ReadyAgentKey {
34
+ hubApiKey: string;
35
+ agentUserId: string;
36
+ }
37
+ /** Take (once) the key already minted — and approved — for `agentType`. */
38
+ export declare function takePreApprovedKey(agentType: string): ReadyAgentKey | undefined;
39
+ /**
40
+ * Hand an installer a key that is already approved — the device flow returns
41
+ * one per agent the person approved with the computer (`device-connect.ts`).
42
+ * The installer's own `provisionAgentKey` call then takes it instead of minting,
43
+ * and `approveAgentKeysAtOnce` asks for nothing more for that agent.
44
+ */
45
+ export declare function presetApprovedKey(agentType: string, key: ReadyAgentKey): void;
46
+ /** The ONE review page for several pending keys, on the same origin as a single key's review URL. */
47
+ export declare function batchReviewUrl(reviewUrl: string, keyIds: readonly string[]): string;
48
+ /**
49
+ * Does this pod serve the batch approval page? Its lookup door answers 401/400
50
+ * without a signed-in session; a pod older than it answers 404. Unreachable
51
+ * reads as "no": the per-key pages work on every pod.
52
+ */
53
+ export declare function podSupportsBatchApproval(podUrl: string): Promise<boolean>;
54
+ /** One pending key, as the wait sees it. */
55
+ export interface PendingKeyWait {
56
+ podUrl: string;
57
+ pendingKey: string;
58
+ pendingToken: string;
59
+ humanApiKey: string;
60
+ }
61
+ export interface BatchApprovalDeps {
62
+ provision?: typeof import("./targets.js").provisionAgentKey;
63
+ /**
64
+ * Wait for one pending key to go live. Default `waitForKeyLive`: it asks
65
+ * about the pending key WITH the pending key (`/auth/key-state`), so the
66
+ * wait still sees the approval when the person's own key is the one that
67
+ * approval just replaced (2026-10-12). Older pods: the per-key pending door.
68
+ */
69
+ wait?: (p: PendingKeyWait) => Promise<import("./key-approval.js").KeyWaitOutcome>;
70
+ openUrl?: (url: string) => void;
71
+ supportsBatch?: (podUrl: string) => Promise<boolean>;
72
+ }
73
+ export interface BatchApprovalResult {
74
+ /** Targets the person did not approve (rejected, timed out, or the mint failed). */
75
+ notApproved: TargetName[];
76
+ /** Why, per target, for the one warning line `init` prints. */
77
+ reasons: Partial<Record<TargetName, string>>;
78
+ }
79
+ /**
80
+ * Mint every approval-gated key for `targets`, open one page, wait for all.
81
+ * Returns the targets the person did NOT approve (rejected, timed out, or
82
+ * failed to mint): `init` skips those instead of asking again, and prints
83
+ * one line for each.
84
+ */
85
+ export declare function approveAgentKeysAtOnce(podUrl: string, humanApiKey: string, targets: readonly TargetName[], deps?: BatchApprovalDeps): Promise<BatchApprovalResult>;
@@ -0,0 +1,170 @@
1
+ /**
2
+ * One-click approval for the agent keys `synap init` mints (V1 D5).
3
+ *
4
+ * Codex and Cursor each mint their agent key with `requireApproval`, and
5
+ * `provisionAgentKey` used to open one review page per key and block on it.
6
+ * Connecting both meant two pages and two clicks, one after the other.
7
+ *
8
+ * Now `init` mints every key that needs approval FIRST (deferred), opens ONE
9
+ * page (`/approve-agents?keys=…` on the pod admin, backed by
10
+ * `POST /api/hub/setup/agent/pending/approve-batch`), and polls every key
11
+ * until the person approves them together. The approved keys are then handed
12
+ * to the installers through `takePreApprovedKey`, so each installer's own
13
+ * `provisionAgentKey` call returns the key the person already approved instead
14
+ * of minting a second one.
15
+ *
16
+ * A pod older than the batch door has no `/approve-agents` page: `init`
17
+ * probes the batch lookup door first and, when it is missing, opens each
18
+ * key's own review page instead (every pod version serves those).
19
+ */
20
+ import chalk from "chalk";
21
+ import { log } from "../utils/logger.js";
22
+ import { openPodPage } from "./safe-open.js";
23
+ /**
24
+ * The targets whose installer mints an agent key that needs the person's
25
+ * approval. Claude Code mints without approval, so it is not here. The installers read their spec from this table
26
+ * (`installCodex` / `installCursor`), so the pre-mint cannot ask for a key the
27
+ * installer would not have asked for.
28
+ */
29
+ export const TARGET_KEY_MINT = {
30
+ codex: { agentType: "codex", idempotent: true },
31
+ cursor: { agentType: "cursor", idempotent: true },
32
+ };
33
+ const ready = new Map();
34
+ /** Take (once) the key already minted — and approved — for `agentType`. */
35
+ export function takePreApprovedKey(agentType) {
36
+ const key = ready.get(agentType);
37
+ ready.delete(agentType);
38
+ return key;
39
+ }
40
+ /**
41
+ * Hand an installer a key that is already approved — the device flow returns
42
+ * one per agent the person approved with the computer (`device-connect.ts`).
43
+ * The installer's own `provisionAgentKey` call then takes it instead of minting,
44
+ * and `approveAgentKeysAtOnce` asks for nothing more for that agent.
45
+ */
46
+ export function presetApprovedKey(agentType, key) {
47
+ ready.set(agentType, key);
48
+ }
49
+ /** The ONE review page for several pending keys, on the same origin as a single key's review URL. */
50
+ export function batchReviewUrl(reviewUrl, keyIds) {
51
+ const origin = new URL(reviewUrl).origin;
52
+ return `${origin}/approve-agents?keys=${keyIds.map(encodeURIComponent).join(",")}`;
53
+ }
54
+ /**
55
+ * Does this pod serve the batch approval page? Its lookup door answers 401/400
56
+ * without a signed-in session; a pod older than it answers 404. Unreachable
57
+ * reads as "no": the per-key pages work on every pod.
58
+ */
59
+ export async function podSupportsBatchApproval(podUrl) {
60
+ const res = await fetch(`${podUrl.replace(/\/$/, "")}/api/hub/setup/agent/pending/lookup`, {
61
+ method: "POST",
62
+ headers: { "Content-Type": "application/json" },
63
+ body: JSON.stringify({ keyIds: [] }),
64
+ signal: AbortSignal.timeout(10_000),
65
+ }).catch(() => null);
66
+ return res !== null && res.status !== 404;
67
+ }
68
+ /**
69
+ * Mint every approval-gated key for `targets`, open one page, wait for all.
70
+ * Returns the targets the person did NOT approve (rejected, timed out, or
71
+ * failed to mint): `init` skips those instead of asking again, and prints
72
+ * one line for each.
73
+ */
74
+ export async function approveAgentKeysAtOnce(podUrl, humanApiKey, targets, deps = {}) {
75
+ const provision = deps.provision ?? (await import("./targets.js")).provisionAgentKey;
76
+ const wait = deps.wait ?? (await import("./key-approval.js")).waitForKeyLive;
77
+ const openUrl = deps.openUrl ?? (await import("./targets.js")).openBrowserUrl;
78
+ const supportsBatch = deps.supportsBatch ?? podSupportsBatchApproval;
79
+ const podBase = podUrl.replace(/\/$/, "");
80
+ const pending = [];
81
+ const notApproved = [];
82
+ const reasons = {};
83
+ for (const target of targets) {
84
+ const spec = TARGET_KEY_MINT[target];
85
+ if (!spec)
86
+ continue;
87
+ // Approved already (with the computer, in the device flow): nothing to ask.
88
+ if (ready.has(spec.agentType))
89
+ continue;
90
+ try {
91
+ const r = await provision(podUrl, humanApiKey, spec.agentType, {
92
+ idempotent: spec.idempotent,
93
+ deferApproval: true,
94
+ });
95
+ if (r.pending) {
96
+ pending.push({
97
+ target,
98
+ agentType: spec.agentType,
99
+ hubApiKey: r.hubApiKey,
100
+ agentUserId: r.agentUserId,
101
+ ...r.pending,
102
+ });
103
+ }
104
+ else {
105
+ // Already valid (reused) or active on mint: nothing to approve.
106
+ ready.set(spec.agentType, { hubApiKey: r.hubApiKey, agentUserId: r.agentUserId });
107
+ }
108
+ }
109
+ catch (err) {
110
+ notApproved.push(target);
111
+ reasons[target] = err instanceof Error ? err.message : String(err);
112
+ }
113
+ }
114
+ if (pending.length === 0)
115
+ return { notApproved, reasons };
116
+ // One key keeps its own review page (which every pod version serves); so do
117
+ // several on a pod that predates the batch page.
118
+ const batch = pending.length > 1 && (await supportsBatch(podUrl));
119
+ const urls = batch
120
+ ? [batchReviewUrl(pending[0].reviewUrl, pending.map((p) => p.pendingToken))]
121
+ : pending.map((p) => p.reviewUrl);
122
+ log.blank();
123
+ log.info(batch
124
+ ? `Approve your ${pending.length} agents in one step:`
125
+ : pending.length > 1
126
+ ? `Approve each of your ${pending.length} agents:`
127
+ : "Approve your agent:");
128
+ for (const url of urls) {
129
+ log.dim(url);
130
+ // A pod-supplied link: opened only on this pod's own / pod-admin origin.
131
+ openPodPage(url, podUrl, openUrl);
132
+ }
133
+ process.stdout.write(chalk.dim(" Waiting for approval"));
134
+ const ticker = setInterval(() => process.stdout.write(chalk.dim(".")), 2000);
135
+ try {
136
+ const outcomes = await Promise.allSettled(pending.map((p) => wait({ podUrl: podBase, pendingKey: p.hubApiKey, pendingToken: p.pendingToken, humanApiKey })));
137
+ process.stdout.write("\n");
138
+ const { clearPendingAgentKey } = await import("./pod.js");
139
+ outcomes.forEach((o, i) => {
140
+ const p = pending[i];
141
+ const outcome = o.status === "fulfilled" ? o.value : null;
142
+ if (outcome === "approved") {
143
+ // Live now: the recorded request is done; the installer writes the key.
144
+ clearPendingAgentKey(p.agentType, podUrl);
145
+ ready.set(p.agentType, { hubApiKey: p.hubApiKey, agentUserId: p.agentUserId });
146
+ return;
147
+ }
148
+ notApproved.push(p.target);
149
+ if (outcome === "rejected") {
150
+ clearPendingAgentKey(p.agentType, podUrl);
151
+ reasons[p.target] = "It was declined on the pod.";
152
+ }
153
+ else if (outcome === "timeout") {
154
+ // Still filed and recorded: the next connect resumes this request.
155
+ reasons[p.target] = `Nobody approved it in time — approve it at ${p.reviewUrl}, then run: synap doctor --fix`;
156
+ }
157
+ else {
158
+ reasons[p.target] = o.status === "rejected" && o.reason instanceof Error ? o.reason.message : String(o.status === "rejected" ? o.reason : "unknown");
159
+ }
160
+ });
161
+ }
162
+ finally {
163
+ clearInterval(ticker);
164
+ }
165
+ const approved = pending.length - pending.filter((p) => notApproved.includes(p.target)).length;
166
+ if (approved > 0)
167
+ log.success(`Approved ${approved} agent${approved > 1 ? "s" : ""}.`);
168
+ return { notApproved, reasons };
169
+ }
170
+ //# sourceMappingURL=batch-approval.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"batch-approval.js","sourceRoot":"","sources":["../../src/lib/batch-approval.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,82 @@
1
+ /**
2
+ * The run box's ONE way out: an HTTP(S) proxy on the provisioner, bound to the
3
+ * box bridge. A box has no gateway and no resolver; everything it fetches goes
4
+ * through here, and here decides (runbox design C4 "Egress"):
5
+ *
6
+ * setup phase → the package registries only (PyPI, npm)
7
+ * run phase → the hosts the script declared, nothing else
8
+ *
9
+ * A name that passes is resolved HERE, every address it resolves to is checked
10
+ * against internal ranges (RFC1918, loopback, link-local and cloud metadata,
11
+ * CGNAT = the tailnet), and the connection goes to the address that was
12
+ * checked, never to a second lookup — so a declared host that resolves to the
13
+ * pod (DNS rebinding) is refused. Every refusal is recorded for the evidence
14
+ * bundle. The bridge firewall is the wall; this is the policy.
15
+ */
16
+ import http from "node:http";
17
+ import net from "node:net";
18
+ export type BoxPhase = "setup" | "run";
19
+ /** Hosts a box may reach while it installs declared packages. */
20
+ export declare const REGISTRY_HOSTS: readonly string[];
21
+ /** Ports a bare allow entry opens: the web only. */
22
+ export declare const ALLOWED_PORTS: readonly number[];
23
+ export interface BlockedEgress {
24
+ host: string;
25
+ port: number;
26
+ phase: BoxPhase;
27
+ reason: string;
28
+ at: string;
29
+ }
30
+ /**
31
+ * True when a box must not connect to this address. An unparsable address is
32
+ * forbidden: the check fails closed.
33
+ */
34
+ export declare function isForbiddenAddress(ip: string): boolean;
35
+ /** Lower-cased, trailing dot dropped, brackets of an IPv6 literal removed. */
36
+ export declare function normalizeHost(host: string): string;
37
+ /**
38
+ * `host` matches an allow entry exactly, or a `*.example.com` entry as a
39
+ * strict subdomain (never the apex, never a suffix like `evilexample.com`).
40
+ */
41
+ export declare function hostMatches(host: string, allow: readonly string[]): boolean;
42
+ export interface EgressPolicy {
43
+ phase: BoxPhase;
44
+ /** The script's declared hosts (the run-phase allowlist). */
45
+ runHosts: readonly string[];
46
+ }
47
+ export type EgressDecision = {
48
+ allow: true;
49
+ } | {
50
+ allow: false;
51
+ reason: string;
52
+ };
53
+ /**
54
+ * The name-level decision, before any lookup. A bare entry opens the web
55
+ * ports (80, 443); a `host:port` entry opens that port on that host only.
56
+ */
57
+ export declare function decideByName(host: string, port: number, policy: EgressPolicy): EgressDecision;
58
+ export type Resolver = (host: string) => Promise<string[]>;
59
+ /**
60
+ * The full decision: by name, then by every resolved address. Returns the ONE
61
+ * address to connect to, so the connection never re-resolves.
62
+ */
63
+ export declare function decideEgress(host: string, port: number, policy: EgressPolicy, resolve?: Resolver): Promise<{
64
+ allow: true;
65
+ address: string;
66
+ } | {
67
+ allow: false;
68
+ reason: string;
69
+ }>;
70
+ export interface EgressProxyOptions {
71
+ /** The policy for a box, by its address on the bridge; null = not a live box. */
72
+ policyFor: (sourceIp: string) => EgressPolicy | null;
73
+ onBlock: (sourceIp: string, block: BlockedEgress) => void;
74
+ resolve?: Resolver;
75
+ /** Connect to the checked address (tests replace it). */
76
+ connect?: (address: string, port: number) => net.Socket;
77
+ }
78
+ /**
79
+ * An HTTP proxy: CONNECT for HTTPS (a tunnel to the checked address), and
80
+ * absolute-form requests for plain HTTP. Anything else is refused.
81
+ */
82
+ export declare function createEgressProxy(opts: EgressProxyOptions): http.Server;
@@ -0,0 +1,264 @@
1
+ /**
2
+ * The run box's ONE way out: an HTTP(S) proxy on the provisioner, bound to the
3
+ * box bridge. A box has no gateway and no resolver; everything it fetches goes
4
+ * through here, and here decides (runbox design C4 "Egress"):
5
+ *
6
+ * setup phase → the package registries only (PyPI, npm)
7
+ * run phase → the hosts the script declared, nothing else
8
+ *
9
+ * A name that passes is resolved HERE, every address it resolves to is checked
10
+ * against internal ranges (RFC1918, loopback, link-local and cloud metadata,
11
+ * CGNAT = the tailnet), and the connection goes to the address that was
12
+ * checked, never to a second lookup — so a declared host that resolves to the
13
+ * pod (DNS rebinding) is refused. Every refusal is recorded for the evidence
14
+ * bundle. The bridge firewall is the wall; this is the policy.
15
+ */
16
+ import dns from "node:dns/promises";
17
+ import http from "node:http";
18
+ import net from "node:net";
19
+ /** Hosts a box may reach while it installs declared packages. */
20
+ export const REGISTRY_HOSTS = [
21
+ "pypi.org",
22
+ "files.pythonhosted.org",
23
+ "registry.npmjs.org",
24
+ ];
25
+ /** Ports a bare allow entry opens: the web only. */
26
+ export const ALLOWED_PORTS = [80, 443];
27
+ // ─── addresses ───────────────────────────────────────────────────────────────
28
+ function v4ToInt(ip) {
29
+ return ip.split(".").reduce((acc, o) => (acc << 8) + Number(o), 0) >>> 0;
30
+ }
31
+ function inV4(ip, cidr) {
32
+ const [base, bits] = cidr.split("/");
33
+ const mask = Number(bits) === 0 ? 0 : (~0 << (32 - Number(bits))) >>> 0;
34
+ return (ip & mask) === (v4ToInt(base) & mask);
35
+ }
36
+ /** IPv4 ranges a box must never reach, whatever name led there. */
37
+ const FORBIDDEN_V4 = [
38
+ "0.0.0.0/8", // "this network"
39
+ "10.0.0.0/8", // RFC1918: vmbr1 (the pod at 10.10.0.10) and the box bridge
40
+ "100.64.0.0/10", // CGNAT: the tailnet
41
+ "127.0.0.0/8", // loopback
42
+ "169.254.0.0/16", // link-local, incl. cloud metadata 169.254.169.254
43
+ "172.16.0.0/12", // RFC1918
44
+ "192.0.0.0/24", // IETF protocol assignments
45
+ "192.168.0.0/16", // RFC1918: the LAN, the Proxmox host
46
+ "198.18.0.0/15", // benchmarking
47
+ "224.0.0.0/4", // multicast
48
+ "240.0.0.0/4", // reserved, incl. broadcast
49
+ ];
50
+ /** Expands a valid IPv6 literal to 8 hextets (zone id dropped, embedded v4 folded). */
51
+ function v6Hextets(ip) {
52
+ let addr = ip.split("%")[0].toLowerCase();
53
+ const embedded = /^(.*:)(\d+\.\d+\.\d+\.\d+)$/.exec(addr);
54
+ if (embedded) {
55
+ if (!net.isIPv4(embedded[2]))
56
+ return null;
57
+ const n = v4ToInt(embedded[2]);
58
+ addr = `${embedded[1]}${(n >>> 16).toString(16)}:${(n & 0xffff).toString(16)}`;
59
+ }
60
+ const parts = addr.split("::");
61
+ if (parts.length > 2)
62
+ return null;
63
+ const left = parts[0] ? parts[0].split(":") : [];
64
+ const right = parts.length === 2 && parts[1] ? parts[1].split(":") : [];
65
+ const missing = 8 - left.length - right.length;
66
+ if (parts.length === 1 ? missing !== 0 : missing < 0)
67
+ return null;
68
+ const out = [...left, ...Array(missing).fill("0"), ...right].map((h) => parseInt(h, 16));
69
+ return out.every((h) => Number.isInteger(h) && h >= 0 && h <= 0xffff) ? out : null;
70
+ }
71
+ /**
72
+ * True when a box must not connect to this address. An unparsable address is
73
+ * forbidden: the check fails closed.
74
+ */
75
+ export function isForbiddenAddress(ip) {
76
+ if (net.isIPv4(ip)) {
77
+ const n = v4ToInt(ip);
78
+ return FORBIDDEN_V4.some((c) => inV4(n, c));
79
+ }
80
+ if (!net.isIPv6(ip))
81
+ return true;
82
+ const h = v6Hextets(ip);
83
+ if (!h)
84
+ return true;
85
+ // IPv4-mapped (::ffff:a.b.c.d) and NAT64 (64:ff9b::a.b.c.d) carry a v4 address.
86
+ const isMapped = h.slice(0, 5).every((x) => x === 0) && h[5] === 0xffff;
87
+ const isNat64 = h[0] === 0x64 && h[1] === 0xff9b && h.slice(2, 6).every((x) => x === 0);
88
+ if (isMapped || isNat64) {
89
+ const v4 = `${h[6] >>> 8}.${h[6] & 0xff}.${h[7] >>> 8}.${h[7] & 0xff}`;
90
+ return isForbiddenAddress(v4);
91
+ }
92
+ // ::/96 holds ::, ::1 and the deprecated IPv4-compatible ::a.b.c.d: none is a public peer.
93
+ if (h.slice(0, 6).every((x) => x === 0))
94
+ return true;
95
+ // 6to4 (2002::/16) carries a v4 address in hextets 1-2.
96
+ if (h[0] === 0x2002)
97
+ return isForbiddenAddress(`${h[1] >>> 8}.${h[1] & 0xff}.${h[2] >>> 8}.${h[2] & 0xff}`);
98
+ if (h[0] === 0x2001 && h[1] === 0)
99
+ return true; // Teredo 2001::/32 (an obfuscated v4 inside)
100
+ if (h[0] === 0x2001 && h[1] === 0x0db8)
101
+ return true; // documentation 2001:db8::/32
102
+ if ((h[0] & 0xfe00) === 0xfc00)
103
+ return true; // fc00::/7 unique local
104
+ if ((h[0] & 0xffc0) === 0xfe80)
105
+ return true; // fe80::/10 link-local
106
+ if ((h[0] & 0xff00) === 0xff00)
107
+ return true; // multicast
108
+ return false;
109
+ }
110
+ // ─── names ───────────────────────────────────────────────────────────────────
111
+ /** Lower-cased, trailing dot dropped, brackets of an IPv6 literal removed. */
112
+ export function normalizeHost(host) {
113
+ return host.trim().toLowerCase().replace(/^\[(.*)\]$/, "$1").replace(/\.$/, "");
114
+ }
115
+ /**
116
+ * `host` matches an allow entry exactly, or a `*.example.com` entry as a
117
+ * strict subdomain (never the apex, never a suffix like `evilexample.com`).
118
+ */
119
+ export function hostMatches(host, allow) {
120
+ const h = normalizeHost(host);
121
+ return allow.some((raw) => {
122
+ const a = normalizeHost(raw);
123
+ if (a.startsWith("*."))
124
+ return h.endsWith(a.slice(1)) && h.length > a.length - 1;
125
+ return h === a;
126
+ });
127
+ }
128
+ /** An allow entry split into its host and, when it names one, its port. */
129
+ function splitEntry(entry) {
130
+ const m = /^(.*):(\d{1,5})$/.exec(entry.trim());
131
+ return m && !m[1].includes(":") ? { host: m[1], port: Number(m[2]) } : { host: entry, port: null };
132
+ }
133
+ /**
134
+ * The name-level decision, before any lookup. A bare entry opens the web
135
+ * ports (80, 443); a `host:port` entry opens that port on that host only.
136
+ */
137
+ export function decideByName(host, port, policy) {
138
+ const h = normalizeHost(host);
139
+ if (net.isIP(h))
140
+ return { allow: false, reason: "an address literal is never allowed; declare a host name" };
141
+ const entries = (policy.phase === "setup" ? REGISTRY_HOSTS : policy.runHosts).map(splitEntry);
142
+ const named = entries.filter((e) => hostMatches(h, [e.host]));
143
+ if (named.length === 0) {
144
+ return {
145
+ allow: false,
146
+ reason: policy.phase === "setup"
147
+ ? "only the package registries are reachable while packages install"
148
+ : "not a host this script declared",
149
+ };
150
+ }
151
+ const portOk = named.some((e) => (e.port === null ? ALLOWED_PORTS.includes(port) : e.port === port));
152
+ if (!portOk)
153
+ return { allow: false, reason: `port ${port} is not declared for this host` };
154
+ return { allow: true };
155
+ }
156
+ const systemResolver = async (host) => (await dns.lookup(host, { all: true, verbatim: true })).map((a) => a.address);
157
+ /**
158
+ * The full decision: by name, then by every resolved address. Returns the ONE
159
+ * address to connect to, so the connection never re-resolves.
160
+ */
161
+ export async function decideEgress(host, port, policy, resolve = systemResolver) {
162
+ const byName = decideByName(host, port, policy);
163
+ if (!byName.allow)
164
+ return byName;
165
+ let addresses;
166
+ try {
167
+ addresses = await resolve(normalizeHost(host));
168
+ }
169
+ catch (err) {
170
+ return { allow: false, reason: `could not resolve: ${err.message}` };
171
+ }
172
+ if (addresses.length === 0)
173
+ return { allow: false, reason: "resolved to no address" };
174
+ const bad = addresses.find(isForbiddenAddress);
175
+ if (bad)
176
+ return { allow: false, reason: `resolves to an internal address (${bad})` };
177
+ return { allow: true, address: addresses[0] };
178
+ }
179
+ function sourceIpOf(sock) {
180
+ return (sock.remoteAddress ?? "").replace(/^::ffff:/, "");
181
+ }
182
+ function splitHostPort(authority, defaultPort) {
183
+ const m = /^(\[[^\]]+\]|[^:]+)(?::(\d+))?$/.exec(authority);
184
+ if (!m)
185
+ return null;
186
+ return { host: m[1], port: m[2] ? Number(m[2]) : defaultPort };
187
+ }
188
+ /**
189
+ * An HTTP proxy: CONNECT for HTTPS (a tunnel to the checked address), and
190
+ * absolute-form requests for plain HTTP. Anything else is refused.
191
+ */
192
+ export function createEgressProxy(opts) {
193
+ const resolve = opts.resolve ?? systemResolver;
194
+ const connect = opts.connect ?? ((address, port) => net.connect({ host: address, port }));
195
+ async function gate(sock, host, port) {
196
+ const src = sourceIpOf(sock);
197
+ const policy = opts.policyFor(src);
198
+ if (!policy)
199
+ return { status: 403, reason: "not a running box" };
200
+ const d = await decideEgress(host, port, policy, resolve);
201
+ if (!d.allow) {
202
+ opts.onBlock(src, { host: normalizeHost(host), port, phase: policy.phase, reason: d.reason, at: new Date().toISOString() });
203
+ return { status: 403, reason: d.reason };
204
+ }
205
+ return { address: d.address };
206
+ }
207
+ const server = http.createServer(async (req, res) => {
208
+ let target;
209
+ try {
210
+ target = new URL(req.url ?? "");
211
+ }
212
+ catch {
213
+ res.writeHead(400).end("absolute-form request required\n");
214
+ return;
215
+ }
216
+ if (target.protocol !== "http:") {
217
+ res.writeHead(400).end("only http:// is proxied in absolute form; use CONNECT for https\n");
218
+ return;
219
+ }
220
+ const port = target.port ? Number(target.port) : 80;
221
+ const g = await gate(req.socket, target.hostname, port);
222
+ if (!("address" in g)) {
223
+ res.writeHead(g.status, { "content-type": "text/plain" }).end(`synap box egress refused: ${g.reason}\n`);
224
+ return;
225
+ }
226
+ const upstream = http.request({
227
+ host: g.address,
228
+ port,
229
+ method: req.method,
230
+ path: target.pathname + target.search,
231
+ headers: { ...req.headers, host: target.host },
232
+ createConnection: () => connect(g.address, port),
233
+ }, (up) => {
234
+ res.writeHead(up.statusCode ?? 502, up.headers);
235
+ up.pipe(res);
236
+ });
237
+ upstream.on("error", () => res.headersSent ? res.destroy() : res.writeHead(502).end());
238
+ req.pipe(upstream);
239
+ });
240
+ server.on("connect", async (req, client, head) => {
241
+ const hp = splitHostPort(req.url ?? "", 443);
242
+ if (!hp) {
243
+ client.end("HTTP/1.1 400 Bad Request\r\n\r\n");
244
+ return;
245
+ }
246
+ const g = await gate(client, hp.host, hp.port);
247
+ if (!("address" in g)) {
248
+ client.end(`HTTP/1.1 ${g.status} Forbidden\r\ncontent-type: text/plain\r\n\r\nsynap box egress refused: ${g.reason}\n`);
249
+ return;
250
+ }
251
+ const upstream = connect(g.address, hp.port);
252
+ upstream.once("connect", () => {
253
+ client.write("HTTP/1.1 200 Connection Established\r\n\r\n");
254
+ if (head.length)
255
+ upstream.write(head);
256
+ upstream.pipe(client);
257
+ client.pipe(upstream);
258
+ });
259
+ upstream.on("error", () => client.destroy());
260
+ client.on("error", () => upstream.destroy());
261
+ });
262
+ return server;
263
+ }
264
+ //# sourceMappingURL=egress.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"egress.js","sourceRoot":"","sources":["../../../src/lib/box/egress.ts"],"names":[],"mappings":"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"}