@synap-core/cli 1.11.0 → 1.12.2

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 (452) hide show
  1. package/README.md +23 -198
  2. package/dist/build-info.json +6 -0
  3. package/dist/commands/agent-run.js +3 -2
  4. package/dist/commands/agent-run.js.map +1 -1
  5. package/dist/commands/agents.d.ts +33 -17
  6. package/dist/commands/agents.js +203 -237
  7. package/dist/commands/agents.js.map +1 -1
  8. package/dist/commands/app.d.ts +143 -0
  9. package/dist/commands/app.js +523 -0
  10. package/dist/commands/app.js.map +1 -0
  11. package/dist/commands/automate.d.ts +21 -0
  12. package/dist/commands/automate.js +42 -0
  13. package/dist/commands/automate.js.map +1 -0
  14. package/dist/commands/automation-schema.test.d.ts +16 -0
  15. package/dist/commands/automation-schema.test.js +77 -0
  16. package/dist/commands/automation-schema.test.js.map +1 -0
  17. package/dist/commands/automation.d.ts +12 -0
  18. package/dist/commands/automation.js +80 -35
  19. package/dist/commands/automation.js.map +1 -1
  20. package/dist/commands/bridge-setup.d.ts +14 -1
  21. package/dist/commands/bridge-setup.js +392 -128
  22. package/dist/commands/bridge-setup.js.map +1 -1
  23. package/dist/commands/cap-connections.d.ts +4 -4
  24. package/dist/commands/cap-connections.js +14 -14
  25. package/dist/commands/cap-connections.js.map +1 -1
  26. package/dist/commands/capability.d.ts +2 -0
  27. package/dist/commands/capability.js +218 -168
  28. package/dist/commands/capability.js.map +1 -1
  29. package/dist/commands/catalog.d.ts +275 -0
  30. package/dist/commands/catalog.js +481 -0
  31. package/dist/commands/catalog.js.map +1 -0
  32. package/dist/commands/cell.d.ts +155 -8
  33. package/dist/commands/cell.js +416 -40
  34. package/dist/commands/cell.js.map +1 -1
  35. package/dist/commands/centrality.js +1 -13
  36. package/dist/commands/centrality.js.map +1 -1
  37. package/dist/commands/connect.d.ts +38 -13
  38. package/dist/commands/connect.js +68 -167
  39. package/dist/commands/connect.js.map +1 -1
  40. package/dist/commands/connections.d.ts +3 -2
  41. package/dist/commands/connections.js +95 -25
  42. package/dist/commands/connections.js.map +1 -1
  43. package/dist/commands/context.js +7 -1
  44. package/dist/commands/context.js.map +1 -1
  45. package/dist/commands/data-extra.d.ts +34 -0
  46. package/dist/commands/data-extra.js +193 -23
  47. package/dist/commands/data-extra.js.map +1 -1
  48. package/dist/commands/data.d.ts +120 -2
  49. package/dist/commands/data.js +293 -20
  50. package/dist/commands/data.js.map +1 -1
  51. package/dist/commands/diagnose.d.ts +66 -4
  52. package/dist/commands/diagnose.js +285 -28
  53. package/dist/commands/diagnose.js.map +1 -1
  54. package/dist/commands/doc.d.ts +11 -4
  55. package/dist/commands/doc.js +39 -14
  56. package/dist/commands/doc.js.map +1 -1
  57. package/dist/commands/doctor.d.ts +112 -3
  58. package/dist/commands/doctor.js +657 -32
  59. package/dist/commands/doctor.js.map +1 -1
  60. package/dist/commands/explain.js +5 -5
  61. package/dist/commands/explain.js.map +1 -1
  62. package/dist/commands/import.d.ts +368 -13
  63. package/dist/commands/import.js +1064 -54
  64. package/dist/commands/import.js.map +1 -1
  65. package/dist/commands/init.d.ts +20 -9
  66. package/dist/commands/init.js +433 -973
  67. package/dist/commands/init.js.map +1 -1
  68. package/dist/commands/keys.d.ts +1 -0
  69. package/dist/commands/keys.js +15 -2
  70. package/dist/commands/keys.js.map +1 -1
  71. package/dist/commands/knowledge.d.ts +22 -6
  72. package/dist/commands/knowledge.js +117 -55
  73. package/dist/commands/knowledge.js.map +1 -1
  74. package/dist/commands/lens.d.ts +37 -1
  75. package/dist/commands/lens.js +192 -71
  76. package/dist/commands/lens.js.map +1 -1
  77. package/dist/commands/market-authoring.d.ts +29 -2
  78. package/dist/commands/market-authoring.js +348 -7
  79. package/dist/commands/market-authoring.js.map +1 -1
  80. package/dist/commands/market-official.d.ts +58 -0
  81. package/dist/commands/market-official.js +84 -0
  82. package/dist/commands/market-official.js.map +1 -0
  83. package/dist/commands/market.d.ts +400 -16
  84. package/dist/commands/market.js +1802 -146
  85. package/dist/commands/market.js.map +1 -1
  86. package/dist/commands/mcp.d.ts +60 -25
  87. package/dist/commands/mcp.js +251 -64
  88. package/dist/commands/mcp.js.map +1 -1
  89. package/dist/commands/open.d.ts +39 -9
  90. package/dist/commands/open.js +80 -25
  91. package/dist/commands/open.js.map +1 -1
  92. package/dist/commands/playbook.d.ts +42 -0
  93. package/dist/commands/playbook.js +162 -0
  94. package/dist/commands/playbook.js.map +1 -0
  95. package/dist/commands/pod.js +1 -1
  96. package/dist/commands/pod.js.map +1 -1
  97. package/dist/commands/pods.d.ts +5 -0
  98. package/dist/commands/pods.js +97 -116
  99. package/dist/commands/pods.js.map +1 -1
  100. package/dist/commands/proposals-actions.d.ts +62 -0
  101. package/dist/commands/proposals-actions.js +143 -8
  102. package/dist/commands/proposals-actions.js.map +1 -1
  103. package/dist/commands/proposals-await.d.ts +68 -0
  104. package/dist/commands/proposals-await.js +248 -0
  105. package/dist/commands/proposals-await.js.map +1 -0
  106. package/dist/commands/proton-setup.d.ts +73 -0
  107. package/dist/commands/proton-setup.js +577 -0
  108. package/dist/commands/proton-setup.js.map +1 -0
  109. package/dist/commands/providers.d.ts +23 -0
  110. package/dist/commands/providers.js +126 -1
  111. package/dist/commands/providers.js.map +1 -1
  112. package/dist/commands/raycast.js +6 -2
  113. package/dist/commands/raycast.js.map +1 -1
  114. package/dist/commands/rule.d.ts +150 -0
  115. package/dist/commands/rule.js +447 -0
  116. package/dist/commands/rule.js.map +1 -0
  117. package/dist/commands/session-wait.d.ts +111 -0
  118. package/dist/commands/session-wait.js +209 -0
  119. package/dist/commands/session-wait.js.map +1 -0
  120. package/dist/commands/sessions.d.ts +52 -0
  121. package/dist/commands/sessions.js +478 -58
  122. package/dist/commands/sessions.js.map +1 -1
  123. package/dist/commands/skill-manage.d.ts +21 -0
  124. package/dist/commands/skill-manage.js +136 -19
  125. package/dist/commands/skill-manage.js.map +1 -1
  126. package/dist/commands/skills.js +16 -0
  127. package/dist/commands/skills.js.map +1 -1
  128. package/dist/commands/status.d.ts +1 -4
  129. package/dist/commands/status.js +5 -34
  130. package/dist/commands/status.js.map +1 -1
  131. package/dist/commands/statusline.backoff.test.d.ts +13 -0
  132. package/dist/commands/statusline.backoff.test.js +100 -0
  133. package/dist/commands/statusline.backoff.test.js.map +1 -0
  134. package/dist/commands/statusline.js +16 -9
  135. package/dist/commands/statusline.js.map +1 -1
  136. package/dist/commands/sync-status.d.ts +12 -0
  137. package/dist/commands/sync-status.js +125 -0
  138. package/dist/commands/sync-status.js.map +1 -0
  139. package/dist/commands/templates-retire.d.ts +34 -0
  140. package/dist/commands/templates-retire.js +192 -0
  141. package/dist/commands/templates-retire.js.map +1 -0
  142. package/dist/commands/tools.js +6 -21
  143. package/dist/commands/tools.js.map +1 -1
  144. package/dist/commands/tracks.d.ts +51 -0
  145. package/dist/commands/tracks.js +291 -0
  146. package/dist/commands/tracks.js.map +1 -0
  147. package/dist/commands/update.d.ts +3 -11
  148. package/dist/commands/update.js +5 -134
  149. package/dist/commands/update.js.map +1 -1
  150. package/dist/commands/upload.d.ts +41 -3
  151. package/dist/commands/upload.js +120 -18
  152. package/dist/commands/upload.js.map +1 -1
  153. package/dist/commands/vendor.d.ts +28 -0
  154. package/dist/commands/vendor.js +110 -0
  155. package/dist/commands/vendor.js.map +1 -0
  156. package/dist/commands/versions.js +6 -0
  157. package/dist/commands/versions.js.map +1 -1
  158. package/dist/commands/view.js +10 -5
  159. package/dist/commands/view.js.map +1 -1
  160. package/dist/commands/whoami.d.ts +23 -3
  161. package/dist/commands/whoami.js +169 -23
  162. package/dist/commands/whoami.js.map +1 -1
  163. package/dist/commands/worker.d.ts +122 -0
  164. package/dist/commands/worker.js +435 -0
  165. package/dist/commands/worker.js.map +1 -0
  166. package/dist/commands/worker.test.d.ts +1 -0
  167. package/dist/commands/worker.test.js +116 -0
  168. package/dist/commands/worker.test.js.map +1 -0
  169. package/dist/commands/workspace-ops.d.ts +35 -0
  170. package/dist/commands/workspace-ops.js +153 -0
  171. package/dist/commands/workspace-ops.js.map +1 -0
  172. package/dist/index.d.ts +6 -6
  173. package/dist/index.js +900 -180
  174. package/dist/index.js.map +1 -1
  175. package/dist/lib/agent-connections.d.ts +31 -0
  176. package/dist/lib/agent-connections.js +33 -0
  177. package/dist/lib/agent-connections.js.map +1 -0
  178. package/dist/lib/agent-detect.d.ts +27 -0
  179. package/dist/lib/agent-detect.js +71 -0
  180. package/dist/lib/agent-detect.js.map +1 -0
  181. package/dist/lib/agent-door.d.ts +138 -0
  182. package/dist/lib/agent-door.js +426 -0
  183. package/dist/lib/agent-door.js.map +1 -0
  184. package/dist/lib/agents-config.d.ts +2 -0
  185. package/dist/lib/agents-config.js +4 -9
  186. package/dist/lib/agents-config.js.map +1 -1
  187. package/dist/lib/approval-poll.d.ts +31 -2
  188. package/dist/lib/approval-poll.js +20 -7
  189. package/dist/lib/approval-poll.js.map +1 -1
  190. package/dist/lib/atomic-file.d.ts +48 -0
  191. package/dist/lib/atomic-file.js +129 -0
  192. package/dist/lib/atomic-file.js.map +1 -0
  193. package/dist/lib/auth.d.ts +14 -9
  194. package/dist/lib/auth.js +44 -61
  195. package/dist/lib/auth.js.map +1 -1
  196. package/dist/lib/batch-approval.d.ts +85 -0
  197. package/dist/lib/batch-approval.js +170 -0
  198. package/dist/lib/batch-approval.js.map +1 -0
  199. package/dist/lib/capture-lane.d.ts +6 -5
  200. package/dist/lib/capture-lane.js +6 -5
  201. package/dist/lib/capture-lane.js.map +1 -1
  202. package/dist/lib/capture-structure.d.ts +230 -11
  203. package/dist/lib/capture-structure.js +251 -13
  204. package/dist/lib/capture-structure.js.map +1 -1
  205. package/dist/lib/catalog-templates.d.ts +59 -0
  206. package/dist/lib/catalog-templates.js +126 -0
  207. package/dist/lib/catalog-templates.js.map +1 -0
  208. package/dist/lib/cli-build.d.ts +19 -0
  209. package/dist/lib/cli-build.js +37 -0
  210. package/dist/lib/cli-build.js.map +1 -0
  211. package/dist/lib/conversation-headers.d.ts +18 -0
  212. package/dist/lib/conversation-headers.js +32 -0
  213. package/dist/lib/conversation-headers.js.map +1 -0
  214. package/dist/lib/cp-packages.d.ts +167 -11
  215. package/dist/lib/cp-packages.js +253 -21
  216. package/dist/lib/cp-packages.js.map +1 -1
  217. package/dist/lib/credential-class.d.ts +117 -0
  218. package/dist/lib/credential-class.js +116 -0
  219. package/dist/lib/credential-class.js.map +1 -0
  220. package/dist/lib/describe-lens.d.ts +35 -0
  221. package/dist/lib/describe-lens.js +40 -0
  222. package/dist/lib/describe-lens.js.map +1 -1
  223. package/dist/lib/device-connect.d.ts +125 -0
  224. package/dist/lib/device-connect.js +256 -0
  225. package/dist/lib/device-connect.js.map +1 -0
  226. package/dist/lib/directory-lens.d.ts +99 -0
  227. package/dist/lib/directory-lens.js +187 -0
  228. package/dist/lib/directory-lens.js.map +1 -0
  229. package/dist/lib/exporter-coverage.d.ts +71 -0
  230. package/dist/lib/exporter-coverage.js +97 -0
  231. package/dist/lib/exporter-coverage.js.map +1 -0
  232. package/dist/lib/hub-client.d.ts +29 -8
  233. package/dist/lib/hub-client.js +328 -55
  234. package/dist/lib/hub-client.js.map +1 -1
  235. package/dist/lib/init-connect.d.ts +41 -0
  236. package/dist/lib/init-connect.js +75 -0
  237. package/dist/lib/init-connect.js.map +1 -0
  238. package/dist/lib/init-exit.d.ts +24 -0
  239. package/dist/lib/init-exit.js +41 -0
  240. package/dist/lib/init-exit.js.map +1 -0
  241. package/dist/lib/init-flow.d.ts +25 -0
  242. package/dist/lib/init-flow.js +40 -0
  243. package/dist/lib/init-flow.js.map +1 -0
  244. package/dist/lib/init-handoff.d.ts +16 -0
  245. package/dist/lib/init-handoff.js +19 -0
  246. package/dist/lib/init-handoff.js.map +1 -0
  247. package/dist/lib/init-output.d.ts +18 -0
  248. package/dist/lib/init-output.js +43 -0
  249. package/dist/lib/init-output.js.map +1 -0
  250. package/dist/lib/init-pod.d.ts +45 -0
  251. package/dist/lib/init-pod.js +36 -0
  252. package/dist/lib/init-pod.js.map +1 -0
  253. package/dist/lib/installed.d.ts +210 -11
  254. package/dist/lib/installed.js +234 -36
  255. package/dist/lib/installed.js.map +1 -1
  256. package/dist/lib/key-approval.d.ts +57 -0
  257. package/dist/lib/key-approval.js +117 -0
  258. package/dist/lib/key-approval.js.map +1 -0
  259. package/dist/lib/key-diagnosis.d.ts +56 -0
  260. package/dist/lib/key-diagnosis.js +227 -0
  261. package/dist/lib/key-diagnosis.js.map +1 -0
  262. package/dist/lib/key-doctor.d.ts +136 -0
  263. package/dist/lib/key-doctor.js +286 -0
  264. package/dist/lib/key-doctor.js.map +1 -0
  265. package/dist/lib/key-locations.d.ts +120 -0
  266. package/dist/lib/key-locations.js +326 -0
  267. package/dist/lib/key-locations.js.map +1 -0
  268. package/dist/lib/key-source.d.ts +66 -0
  269. package/dist/lib/key-source.js +106 -0
  270. package/dist/lib/key-source.js.map +1 -0
  271. package/dist/lib/key-state.d.ts +70 -0
  272. package/dist/lib/key-state.js +115 -0
  273. package/dist/lib/key-state.js.map +1 -0
  274. package/dist/lib/kind-package.d.ts +181 -0
  275. package/dist/lib/kind-package.js +679 -0
  276. package/dist/lib/kind-package.js.map +1 -0
  277. package/dist/lib/knowledge-title.d.ts +24 -0
  278. package/dist/lib/knowledge-title.js +46 -0
  279. package/dist/lib/knowledge-title.js.map +1 -0
  280. package/dist/lib/knowledge-title.test.d.ts +1 -0
  281. package/dist/lib/knowledge-title.test.js +34 -0
  282. package/dist/lib/knowledge-title.test.js.map +1 -0
  283. package/dist/lib/machine-instance.d.ts +64 -0
  284. package/dist/lib/machine-instance.js +142 -0
  285. package/dist/lib/machine-instance.js.map +1 -0
  286. package/dist/lib/mcp-bridge.d.ts +42 -0
  287. package/dist/lib/mcp-bridge.js +147 -0
  288. package/dist/lib/mcp-bridge.js.map +1 -0
  289. package/dist/lib/mcp-bridge.test.d.ts +1 -0
  290. package/dist/lib/mcp-bridge.test.js +90 -0
  291. package/dist/lib/mcp-bridge.test.js.map +1 -0
  292. package/dist/lib/mcp-call.d.ts +30 -0
  293. package/dist/lib/mcp-call.js +107 -0
  294. package/dist/lib/mcp-call.js.map +1 -0
  295. package/dist/lib/mcp-snippets.d.ts +53 -0
  296. package/dist/lib/mcp-snippets.js +82 -0
  297. package/dist/lib/mcp-snippets.js.map +1 -0
  298. package/dist/lib/next-steps.d.ts +8 -0
  299. package/dist/lib/next-steps.js +31 -1
  300. package/dist/lib/next-steps.js.map +1 -1
  301. package/dist/lib/package-wire.d.ts +179 -0
  302. package/dist/lib/package-wire.js +68 -0
  303. package/dist/lib/package-wire.js.map +1 -0
  304. package/dist/lib/pair-link.d.ts +38 -0
  305. package/dist/lib/pair-link.js +68 -0
  306. package/dist/lib/pair-link.js.map +1 -0
  307. package/dist/lib/pod-wide.d.ts +40 -0
  308. package/dist/lib/pod-wide.js +46 -0
  309. package/dist/lib/pod-wide.js.map +1 -0
  310. package/dist/lib/pod.d.ts +66 -112
  311. package/dist/lib/pod.js +134 -412
  312. package/dist/lib/pod.js.map +1 -1
  313. package/dist/lib/project-ref.d.ts +9 -3
  314. package/dist/lib/project-ref.js +10 -4
  315. package/dist/lib/project-ref.js.map +1 -1
  316. package/dist/lib/review-credential.d.ts +119 -0
  317. package/dist/lib/review-credential.js +147 -0
  318. package/dist/lib/review-credential.js.map +1 -0
  319. package/dist/lib/safe-open.d.ts +49 -0
  320. package/dist/lib/safe-open.js +119 -0
  321. package/dist/lib/safe-open.js.map +1 -0
  322. package/dist/lib/session-lens.d.ts +40 -1
  323. package/dist/lib/session-lens.js +54 -4
  324. package/dist/lib/session-lens.js.map +1 -1
  325. package/dist/lib/superwhisper-import.d.ts +8 -0
  326. package/dist/lib/superwhisper-import.js +14 -7
  327. package/dist/lib/superwhisper-import.js.map +1 -1
  328. package/dist/lib/superwhisper-title.test.d.ts +1 -0
  329. package/dist/lib/superwhisper-title.test.js +18 -0
  330. package/dist/lib/superwhisper-title.test.js.map +1 -0
  331. package/dist/lib/targets.d.ts +134 -10
  332. package/dist/lib/targets.js +962 -258
  333. package/dist/lib/targets.js.map +1 -1
  334. package/dist/lib/template-file.d.ts +4 -0
  335. package/dist/lib/template-file.js.map +1 -1
  336. package/dist/lib/template-lifecycle.d.ts +217 -0
  337. package/dist/lib/template-lifecycle.js +433 -0
  338. package/dist/lib/template-lifecycle.js.map +1 -0
  339. package/dist/lib/template-steps.d.ts +88 -0
  340. package/dist/lib/template-steps.js +118 -0
  341. package/dist/lib/template-steps.js.map +1 -0
  342. package/dist/lib/time-ago.d.ts +2 -0
  343. package/dist/lib/time-ago.js +15 -0
  344. package/dist/lib/time-ago.js.map +1 -0
  345. package/dist/utils/logger.js +5 -2
  346. package/dist/utils/logger.js.map +1 -1
  347. package/package.json +23 -17
  348. package/skills/README.md +12 -10
  349. package/skills/agent-os/SKILL.md +214 -99
  350. package/skills/manifest.json +1 -1
  351. package/skills/onboard/SKILL.md +55 -26
  352. package/skills/synap/README.md +5 -8
  353. package/skills/synap/SKILL.md +1086 -283
  354. package/skills/synap/_order.txt +7 -0
  355. package/skills/synap/_skill.yaml +1 -1
  356. package/skills/synap/automations.md +15 -0
  357. package/skills/synap/capture.md +5 -0
  358. package/skills/synap/cli-operations.md +24 -18
  359. package/skills/synap/concepts.md +28 -0
  360. package/skills/synap/content-os.md +10 -1
  361. package/skills/synap/creative-loop.md +15 -10
  362. package/skills/synap/crm.md +21 -52
  363. package/skills/synap/document-embeds.md +141 -47
  364. package/skills/synap/escalation-ladder.md +20 -10
  365. package/skills/synap/focus-sessions.md +47 -21
  366. package/skills/synap/from-intent.md +142 -0
  367. package/skills/synap/governance-rules.md +4 -4
  368. package/skills/synap/governance.md +10 -7
  369. package/skills/synap/hand-off.md +33 -0
  370. package/skills/synap/inline-patterns.md +15 -7
  371. package/skills/synap/lenses.md +33 -15
  372. package/skills/synap/linking.md +41 -40
  373. package/skills/synap/mcp-remote-servers.md +64 -0
  374. package/skills/synap/mental-model.md +17 -15
  375. package/skills/synap/operating-mode-rules.md +1 -1
  376. package/skills/synap/processes.md +118 -0
  377. package/skills/synap/quick-reference.md +5 -1
  378. package/skills/synap/reading.md +3 -1
  379. package/skills/synap/reflexes.md +12 -42
  380. package/skills/synap/viewframe-cells.md +38 -5
  381. package/skills/synap/work-flow.md +1 -1
  382. package/skills/synap/work-model.md +96 -0
  383. package/skills/synap/worked-examples.md +4 -5
  384. package/skills/synap/workspace-design.md +14 -10
  385. package/skills/synap/writes.md +97 -24
  386. package/skills/synap/writing-titles.md +63 -0
  387. package/skills/synap-app/SKILL.md +2 -2
  388. package/skills/synap-app/_skill.yaml +1 -1
  389. package/skills/synap-app/install-commands.md +1 -1
  390. package/skills/synap-design/SKILL.md +474 -0
  391. package/skills/synap-design/_order.txt +4 -0
  392. package/skills/synap-design/_skill.yaml +21 -0
  393. package/skills/synap-design/loop.md +134 -0
  394. package/skills/synap-design/overview.md +44 -0
  395. package/skills/synap-design/principles.md +130 -0
  396. package/skills/synap-design/system.md +133 -0
  397. package/skills/synap-market/SKILL.md +306 -16
  398. package/skills/synap-market/_skill.yaml +1 -1
  399. package/skills/synap-market/author-and-publish.md +145 -8
  400. package/skills/synap-market/governance-and-catalog.md +7 -0
  401. package/skills/synap-market/install.md +79 -1
  402. package/skills/synap-market/overview.md +74 -6
  403. package/skills/synap-schema/SKILL.md +172 -10
  404. package/skills/synap-schema/_order.txt +2 -0
  405. package/skills/synap-schema/_skill.yaml +4 -2
  406. package/skills/synap-schema/common-mistakes.md +4 -2
  407. package/skills/synap-schema/discover-profiles.md +1 -1
  408. package/skills/synap-schema/entity-scope.md +15 -3
  409. package/skills/synap-schema/extend-first.md +29 -0
  410. package/skills/synap-schema/extend-vs-create.md +1 -1
  411. package/skills/synap-schema/intent-vocabulary-ssot.md +111 -0
  412. package/skills/synap-schema/property-types.md +1 -1
  413. package/skills/synap-schema/relations.md +1 -1
  414. package/skills/synap-ui/SKILL.md +19 -12
  415. package/skills/synap-ui/_skill.yaml +1 -1
  416. package/skills/synap-ui/ai-companion.md +1 -1
  417. package/skills/synap-ui/arranging-bento.md +2 -0
  418. package/skills/synap-ui/bento-layouts.md +10 -10
  419. package/skills/synap-ui/bento-recipes.md +313 -543
  420. package/skills/synap-ui/four-builds.md +5 -0
  421. package/skills/synap-ui/view-types.md +2 -2
  422. package/skills/synap-ui/widget-catalog.md +22 -278
  423. package/templates/automations/bookmark-enrichment.automation.json +290 -13
  424. package/templates/automations/url-bookmark-capture.automation.json +73 -11
  425. package/templates/skills/authoring-playbooks/SKILL.md +6 -3
  426. package/templates/skills/authoring-playbooks/reference/stages-contract.md +15 -0
  427. package/templates/skills/authoring-playbooks/reference/worked-example.md +3 -0
  428. package/dist/commands/infra.d.ts +0 -21
  429. package/dist/commands/infra.js +0 -262
  430. package/dist/commands/infra.js.map +0 -1
  431. package/dist/commands/template.d.ts +0 -42
  432. package/dist/commands/template.js +0 -191
  433. package/dist/commands/template.js.map +0 -1
  434. package/dist/lib/browser-auth.d.ts +0 -35
  435. package/dist/lib/browser-auth.js +0 -170
  436. package/dist/lib/browser-auth.js.map +0 -1
  437. package/dist/lib/openclaw.d.ts +0 -32
  438. package/dist/lib/openclaw.js +0 -164
  439. package/dist/lib/openclaw.js.map +0 -1
  440. package/dist/lib/seed.d.ts +0 -13
  441. package/dist/lib/seed.js +0 -135
  442. package/dist/lib/seed.js.map +0 -1
  443. package/node_modules/@synap/hub-rest-client/dist/index.cjs +0 -1261
  444. package/node_modules/@synap/hub-rest-client/dist/index.d.cts +0 -1647
  445. package/node_modules/@synap/hub-rest-client/dist/index.d.ts +0 -1647
  446. package/node_modules/@synap/hub-rest-client/dist/index.js +0 -1231
  447. package/node_modules/@synap/hub-rest-client/package.json +0 -45
  448. package/node_modules/@synap/hub-rest-client/src/client.ts +0 -1631
  449. package/node_modules/@synap/hub-rest-client/src/errors.ts +0 -30
  450. package/node_modules/@synap/hub-rest-client/src/index.ts +0 -153
  451. package/node_modules/@synap/hub-rest-client/src/setup.ts +0 -133
  452. package/node_modules/@synap/hub-rest-client/src/types.ts +0 -1299
@@ -0,0 +1,117 @@
1
+ /**
2
+ * Waiting for a pending agent key to be approved — and resuming that wait.
3
+ *
4
+ * Two rules, both learnt from the 2026-10-12 incident:
5
+ *
6
+ * 1. The wait asks about the PENDING key, presenting the pending key itself
7
+ * (`/auth/key-state`). The old poll authenticated with the person's own
8
+ * key — which, mid-incident, was the very key the approval had just
9
+ * revoked, so the poll could never see the approval land.
10
+ * 2. A request is never filed twice. A minted-but-unapproved key is recorded
11
+ * (`pendingAgentKeys`); the next connect / `doctor --fix` resumes it. Three
12
+ * orphaned requests accumulated in one evening before this.
13
+ */
14
+ import chalk from "chalk";
15
+ import { log } from "../utils/logger.js";
16
+ import { fetchKeyState } from "./key-state.js";
17
+ import { openPodPage } from "./safe-open.js";
18
+ /** The approval did not land in time. The request stays filed and resumable. */
19
+ export class AgentKeyAwaitingApprovalError extends Error {
20
+ agentType;
21
+ approvalUrl;
22
+ constructor(agentType, approvalUrl) {
23
+ super(`${agentType} is waiting for your approval — nothing was changed on this computer.\n` +
24
+ ` Approve it: ${approvalUrl}\n` +
25
+ ` Then finish with: synap doctor --fix`);
26
+ this.agentType = agentType;
27
+ this.approvalUrl = approvalUrl;
28
+ this.name = "AgentKeyAwaitingApprovalError";
29
+ }
30
+ }
31
+ /**
32
+ * Wait until the pod says the key is live (`approved`), refused
33
+ * (`rejected`: revoked / expired / unknown), or the deadline passes.
34
+ * Transient failures never end the wait early.
35
+ */
36
+ export async function waitForKeyLive(opts) {
37
+ const f = opts.fetch ?? fetch;
38
+ const sleep = opts.sleep ?? ((ms) => new Promise((r) => setTimeout(r, ms)));
39
+ // SYNAP_APPROVAL_TIMEOUT_MS / SYNAP_APPROVAL_POLL_MS: wait longer for an
40
+ // approval that needs a walk to the phone (and short in tests).
41
+ const envMs = (name) => {
42
+ const n = Number(process.env[name]);
43
+ return Number.isFinite(n) && n > 0 ? n : undefined;
44
+ };
45
+ const interval = opts.intervalMs ?? envMs("SYNAP_APPROVAL_POLL_MS") ?? 2000;
46
+ const deadline = Date.now() + (opts.timeoutMs ?? envMs("SYNAP_APPROVAL_TIMEOUT_MS") ?? 120_000);
47
+ const base = opts.podUrl.replace(/\/+$/, "");
48
+ while (Date.now() < deadline) {
49
+ const s = await fetchKeyState(opts.podUrl, opts.pendingKey, { fetch: f });
50
+ if (s.state === "active")
51
+ return "approved";
52
+ if (s.state === "revoked" || s.state === "expired" || s.state === "unknown")
53
+ return "rejected";
54
+ // A current pod refusing to even describe the key (403: a guest's key) is a no.
55
+ if (s.state === "inactive" && !s.legacy)
56
+ return "rejected";
57
+ if (s.legacy && s.state === "inactive" && opts.pendingToken && opts.humanApiKey) {
58
+ // Older pod: it cannot describe the pending key — ask the pending door.
59
+ const res = await f(`${base}/api/hub/setup/agent/pending/${opts.pendingToken}`, {
60
+ headers: { Authorization: `Bearer ${opts.humanApiKey}` },
61
+ signal: AbortSignal.timeout(15_000),
62
+ }).catch(() => null);
63
+ const status = res?.ok ? (await res.json().catch(() => ({}))).status : undefined;
64
+ if (status === "active")
65
+ return "approved";
66
+ if (status === "rejected")
67
+ return "rejected";
68
+ }
69
+ await sleep(interval);
70
+ }
71
+ return "timeout";
72
+ }
73
+ /**
74
+ * What a recorded pending key is now: still waiting (resume it), live
75
+ * (approved while we were away — promote it), or dead (forget it, file anew).
76
+ * An unreachable pod keeps it recorded and says so (`unknown`).
77
+ */
78
+ export async function classifyRecordedPending(pending, deps = {}) {
79
+ const state = await fetchKeyState(pending.podUrl, pending.hubApiKey, deps);
80
+ switch (state.state) {
81
+ case "awaiting_approval":
82
+ return { kind: "pending", state };
83
+ case "active":
84
+ return { kind: "active", state };
85
+ case "revoked":
86
+ case "expired":
87
+ case "unknown":
88
+ return { kind: "dead", state };
89
+ case "inactive":
90
+ // Older pod: inactive is either still pending or refused; resuming the
91
+ // wait is safe (the pending door settles it), minting another is not.
92
+ // A current pod refusing the key outright: keep it recorded, mint nothing.
93
+ return { kind: state.legacy ? "pending" : "unknown", state };
94
+ case "unreachable":
95
+ return { kind: "unknown", state };
96
+ }
97
+ }
98
+ /**
99
+ * Print the approval link, open it, and wait — the one interactive wait.
100
+ * The link came from the pod: it is opened only when it is on that pod's own
101
+ * origin or its pod-admin origin (`openPodPage`), never anywhere else.
102
+ */
103
+ export async function openAndWait(agentType, approvalUrl, podUrl, wait, openUrl) {
104
+ log.info(`\n Approve ${agentType} on your pod:`);
105
+ log.dim(` ${approvalUrl}`);
106
+ openPodPage(approvalUrl, podUrl, openUrl);
107
+ process.stdout.write(chalk.dim(" Waiting for approval"));
108
+ const ticker = setInterval(() => process.stdout.write(chalk.dim(".")), 2000);
109
+ try {
110
+ return await wait();
111
+ }
112
+ finally {
113
+ clearInterval(ticker);
114
+ process.stdout.write("\n");
115
+ }
116
+ }
117
+ //# sourceMappingURL=key-approval.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"key-approval.js","sourceRoot":"","sources":["../../src/lib/key-approval.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,56 @@
1
+ /**
2
+ * ONE diagnosis per key problem, from where the keys are and what the pod says
3
+ * about each. Pure: no IO, so every state is unit-tested.
4
+ *
5
+ * Shared by `synap doctor` (and its `--fix`) and `synap whoami`, so the two can
6
+ * never tell the person two different stories about the same key.
7
+ *
8
+ * Each diagnosis carries the ONE right action and the exact command, because
9
+ * the 2026-10-12 incident was a wrong action taken on a wrong story: a key
10
+ * that was only AWAITING APPROVAL was reported "revoked or expired", and every
11
+ * re-run of `init` / `connect` filed another request instead of finishing the
12
+ * first one.
13
+ */
14
+ import { type KeyLocation } from "./key-locations.js";
15
+ import type { KeyState } from "./key-state.js";
16
+ export type DiagnosisCode = "ok" | "awaiting_approval" | "replaced_by_other_computer" | "replaced_on_this_computer" | "revoked" | "expired" | "unknown_key" | "refused" | "unverifiable" | "stale_copies" | "env_shadow" | "person_key_dead";
17
+ /** The single thing `doctor --fix` does for a diagnosis. */
18
+ export type FixAction = "approve_and_wait" | "reprovision" | "rewrite" | "edit_shell_rc" | "login" | "none";
19
+ export interface Diagnosis {
20
+ code: DiagnosisCode;
21
+ severity: "ok" | "warn" | "error";
22
+ /** Agent surface (claude-code, codex, …); absent for the person's own key / env. */
23
+ surface?: string;
24
+ /** The surface's display name. */
25
+ label?: string;
26
+ title: string;
27
+ lines: string[];
28
+ /** The exact command that resolves it (what `--fix` runs, or what the person runs). */
29
+ command?: string;
30
+ action: FixAction;
31
+ /** The key the action works with: the one to approve, or the live one to copy. */
32
+ key?: string;
33
+ agentUserId?: string;
34
+ approvalUrl?: string;
35
+ /** The pod's agent type for the surface, when the pod said. */
36
+ agentType?: string;
37
+ /** The copies the diagnosis is about. */
38
+ locations: KeyLocation[];
39
+ }
40
+ export interface DiagnoseInput {
41
+ locations: KeyLocation[];
42
+ /** The pod's answer per key (by plaintext). A key with no entry reads as unreachable. */
43
+ states: Map<string, KeyState>;
44
+ /** This computer's instance label for a surface. */
45
+ instanceIdFor: (surface: string) => string;
46
+ /** `SYNAP_HUB_API_KEY` as this process sees it. */
47
+ envKey?: string;
48
+ /** A surface's display name (the CLI's target label). Default: the surface id. */
49
+ labelOf?: (surface: string) => string;
50
+ /** This computer's instance ids for a pod agentType (`thisComputerInstanceIds`). */
51
+ instanceIdsForAgentType?: (agentType: string) => Set<string>;
52
+ }
53
+ /** Why one key does not work, in one sentence. */
54
+ export declare function describeKeyState(s: KeyState): string;
55
+ /** Diagnose every key for one pod: the person's own key, each agent surface, the env var. */
56
+ export declare function diagnoseKeys(input: DiagnoseInput): Diagnosis[];
@@ -0,0 +1,227 @@
1
+ /**
2
+ * ONE diagnosis per key problem, from where the keys are and what the pod says
3
+ * about each. Pure: no IO, so every state is unit-tested.
4
+ *
5
+ * Shared by `synap doctor` (and its `--fix`) and `synap whoami`, so the two can
6
+ * never tell the person two different stories about the same key.
7
+ *
8
+ * Each diagnosis carries the ONE right action and the exact command, because
9
+ * the 2026-10-12 incident was a wrong action taken on a wrong story: a key
10
+ * that was only AWAITING APPROVAL was reported "revoked or expired", and every
11
+ * re-run of `init` / `connect` filed another request instead of finishing the
12
+ * first one.
13
+ */
14
+ import { envKeySetBy } from "./key-locations.js";
15
+ const day = (iso) => (iso ? iso.replace("T", " ").slice(0, 16) + " UTC" : "an unknown time");
16
+ function stateOf(input, key) {
17
+ return input.states.get(key) ?? { state: "unreachable", error: "not asked" };
18
+ }
19
+ /** Why one key does not work, in one sentence. */
20
+ export function describeKeyState(s) {
21
+ switch (s.state) {
22
+ case "active":
23
+ return "works";
24
+ case "awaiting_approval":
25
+ return "is waiting for your approval (it was never revoked)";
26
+ case "revoked":
27
+ return s.replacedBy
28
+ ? `was replaced on ${day(s.revokedAt)} by a connection created ${day(s.replacedBy.createdAt)}${s.replacedBy.instanceLabel ? ` on ${s.replacedBy.instanceLabel}` : ""}`
29
+ : `was revoked on ${day(s.revokedAt)}${s.revokedReason ? ` (${s.revokedReason})` : ""}`;
30
+ case "expired":
31
+ return `expired${s.expiresAt ? ` on ${day(s.expiresAt)}` : ""}`;
32
+ case "unknown":
33
+ return "is not a key this pod issued";
34
+ case "inactive":
35
+ return s.legacy ? "is refused, and this pod is too old to say why" : `is refused by this pod${s.error ? ` (${s.error})` : ""}`;
36
+ case "unreachable":
37
+ return `could not be checked (${s.error ?? "pod unreachable"})`;
38
+ }
39
+ }
40
+ const tail = (k) => (k.length <= 8 ? "…" : `…${k.slice(-6)}`);
41
+ function agentDiagnosis(input, surface, group) {
42
+ const label = (input.labelOf ?? ((x) => x))(surface);
43
+ const copies = group.filter((l) => l.kind !== "pending");
44
+ const keys = [...new Set(group.map((l) => l.key))];
45
+ const live = keys.filter((k) => stateOf(input, k).state === "active");
46
+ const primaryLoc = group.find((l) => l.kind === "agent-key-by-pod") ?? copies[0] ?? group[0];
47
+ const agentUserIdOf = (k) => group.find((l) => l.key === k && l.agentUserId)?.agentUserId;
48
+ if (live.length > 0) {
49
+ const liveKey = live.includes(primaryLoc.key) ? primaryLoc.key : live[0];
50
+ const stale = copies.filter((l) => l.key !== liveKey);
51
+ if (stale.length === 0)
52
+ return { code: "ok", severity: "ok", surface, label, title: `${label}: key works`, lines: [], action: "none", key: liveKey, locations: copies };
53
+ return {
54
+ code: "stale_copies",
55
+ severity: "warn",
56
+ surface,
57
+ label,
58
+ title: `${label}: ${stale.length} cop${stale.length === 1 ? "y holds" : "ies hold"} an old key`,
59
+ lines: [
60
+ `The working key (${tail(liveKey)}) is in ${copies.filter((l) => l.key === liveKey).map((l) => l.label).join(", ")}.`,
61
+ ...stale.map((l) => `${l.label} has ${tail(l.key)}, which ${describeKeyState(stateOf(input, l.key))}.`),
62
+ ],
63
+ command: "synap doctor --fix",
64
+ action: "rewrite",
65
+ key: liveKey,
66
+ agentUserId: agentUserIdOf(liveKey),
67
+ locations: stale,
68
+ };
69
+ }
70
+ // Nothing works. A request waiting for approval is the whole story: finish it.
71
+ const awaiting = keys.filter((k) => stateOf(input, k).state === "awaiting_approval");
72
+ if (awaiting.length > 0) {
73
+ const recorded = group.find((l) => l.kind === "pending" && awaiting.includes(l.key))?.key;
74
+ const newest = [...awaiting].sort((a, b) => String(stateOf(input, b).createdAt ?? "").localeCompare(String(stateOf(input, a).createdAt ?? "")))[0];
75
+ const key = recorded ?? newest;
76
+ const s = stateOf(input, key);
77
+ const holding = copies.filter((l) => l.key === key).map((l) => l.label);
78
+ const lines = [
79
+ `Key ${tail(key)} was filed${s.createdAt ? ` on ${day(s.createdAt)}` : ""} and nobody approved it yet — it was never revoked.`,
80
+ ...(holding.length ? [`It is already written into ${holding.join(", ")}, which is why every call says "Invalid or expired API key".`] : []),
81
+ ...(awaiting.length > 1 ? [`${awaiting.length - 1} other unapproved request${awaiting.length > 2 ? "s" : ""} for ${label} ${awaiting.length > 2 ? "are" : "is"} left over; approving this one is enough.`] : []),
82
+ `Approve it: ${s.approvalUrl ?? "(open your pod's agent approvals)"}`,
83
+ ];
84
+ return {
85
+ code: "awaiting_approval",
86
+ severity: "error",
87
+ surface,
88
+ label,
89
+ title: `${label} is waiting for your approval`,
90
+ lines,
91
+ command: "synap doctor --fix (opens the link, waits, then writes the key)",
92
+ action: "approve_and_wait",
93
+ key,
94
+ agentUserId: agentUserIdOf(key),
95
+ approvalUrl: s.approvalUrl,
96
+ agentType: s.agentType ?? undefined,
97
+ locations: copies,
98
+ };
99
+ }
100
+ // Every copy is dead. Explain the primary one.
101
+ const s = stateOf(input, primaryLoc.key);
102
+ const base = { surface, label, locations: copies, agentType: s.agentType ?? undefined, command: "synap doctor --fix (asks the pod for a key for THIS computer, waits for your approval, then writes it everywhere)" };
103
+ const where = copies.map((l) => l.label);
104
+ if (s.state === "revoked" && s.replacedBy !== undefined) {
105
+ const mine = input.instanceIdFor(surface);
106
+ const otherInstance = s.replacedBy?.instanceId ?? null;
107
+ if (otherInstance && otherInstance === mine)
108
+ return {
109
+ ...base,
110
+ code: "replaced_on_this_computer",
111
+ severity: "error",
112
+ title: `${label}: a newer key from this computer replaced it, and was never saved here`,
113
+ lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)} on THIS computer.`, `Stale copies: ${where.join(", ")}.`],
114
+ action: "reprovision",
115
+ };
116
+ return {
117
+ ...base,
118
+ code: "replaced_by_other_computer",
119
+ severity: "error",
120
+ title: `${label}: another computer's connection replaced this computer's key`,
121
+ lines: [
122
+ `Key ${tail(primaryLoc.key)} ${describeKeyState(s)}.`,
123
+ otherInstance
124
+ ? `That connection belongs to another computer (${s.replacedBy?.instanceLabel ?? otherInstance}); approving it switched off every other ${label} key that shared its slot.`
125
+ : `That connection carried no computer label (made by an older CLI), so approving it switched off EVERY ${label} key — this computer's included.`,
126
+ `Give this computer its own connection: keys made now carry this computer's label (${input.instanceIdFor(surface)}), so approving one never switches another computer off.`,
127
+ ],
128
+ action: "reprovision",
129
+ };
130
+ }
131
+ if (s.state === "revoked")
132
+ return { ...base, code: "revoked", severity: "error", title: `${label}: key was revoked`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)}.`, `Copies: ${where.join(", ")}.`], action: "reprovision" };
133
+ if (s.state === "expired")
134
+ return { ...base, code: "expired", severity: "error", title: `${label}: key expired`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)}.`, `Copies: ${where.join(", ")}.`], action: "reprovision" };
135
+ if (s.state === "unknown")
136
+ return { ...base, code: "unknown_key", severity: "error", title: `${label}: this pod does not know the key`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)} — it was made for another pod, or deleted.`, `Copies: ${where.join(", ")}.`], action: "reprovision" };
137
+ if (s.state === "inactive") {
138
+ const recorded = group.find((l) => l.kind === "pending");
139
+ return recorded
140
+ ? { ...base, code: "refused", severity: "error", title: `${label}: key is refused (older pod — likely still awaiting approval)`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)}.`, "A request from this computer is recorded; finishing it is safer than filing another."], action: "approve_and_wait", key: recorded.key, agentUserId: recorded.agentUserId, command: "synap doctor --fix" }
141
+ : { ...base, code: "refused", severity: "error", title: `${label}: key is refused`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)} (awaiting approval or revoked).`, `Copies: ${where.join(", ")}.`], action: "reprovision" };
142
+ }
143
+ return { ...base, key: primaryLoc.key, code: "unverifiable", severity: "warn", title: `${label}: could not check the key`, lines: [`Key ${tail(primaryLoc.key)} ${describeKeyState(s)}.`], action: "none", command: "synap doctor (again, once the pod answers)" };
144
+ }
145
+ /**
146
+ * Why the person's key was switched off by a replacing connection. "This
147
+ * computer" is decided only when the pod named the key's agentType: keys are
148
+ * minted with the SURFACE's hash (`thisComputerInstanceIds`), and hashing ""
149
+ * for a missing type would call every connection "another computer".
150
+ */
151
+ function personKeyReplacedLine(input, s) {
152
+ const other = s.replacedBy?.instanceId ?? null;
153
+ const name = s.replacedBy?.instanceLabel ?? other;
154
+ if (!other)
155
+ return "It was an agent key: approving a connection with no computer label switched off every key of that agent, this one included.";
156
+ if (!s.agentType)
157
+ return `It was an agent key: approving another connection (${name}) switched it off.`;
158
+ const mine = (input.instanceIdsForAgentType ?? ((t) => new Set([input.instanceIdFor(t)])))(s.agentType);
159
+ return mine.has(other)
160
+ ? "It was an agent key: a newer connection from THIS computer replaced it."
161
+ : `It was an agent key: approving another computer's connection (${name}) switched it off.`;
162
+ }
163
+ /** Diagnose every key for one pod: the person's own key, each agent surface, the env var. */
164
+ export function diagnoseKeys(input) {
165
+ const out = [];
166
+ // 1. The person's / this computer's own CLI key (pod profile).
167
+ for (const loc of input.locations.filter((l) => l.kind === "profile")) {
168
+ const s = stateOf(input, loc.key);
169
+ if (s.state === "active" || s.state === "unreachable")
170
+ continue;
171
+ out.push({
172
+ code: "person_key_dead",
173
+ severity: "error",
174
+ title: `Your CLI key for this pod ${describeKeyState(s)}`,
175
+ lines: [
176
+ `${loc.label} holds ${tail(loc.key)}. Agent keys cannot be re-made without it.`,
177
+ ...(s.state === "revoked" && s.replacedBy !== undefined ? [personKeyReplacedLine(input, s)] : []),
178
+ ],
179
+ command: `synap login --reconnect${loc.ref ? ` ${loc.ref}` : ""}`,
180
+ action: "login",
181
+ locations: [loc],
182
+ });
183
+ }
184
+ // 2. One diagnosis per agent surface.
185
+ const bySurface = new Map();
186
+ for (const l of input.locations) {
187
+ if (l.role !== "agent" || !l.surface)
188
+ continue;
189
+ bySurface.set(l.surface, [...(bySurface.get(l.surface) ?? []), l]);
190
+ }
191
+ const surfaceDiags = new Map();
192
+ for (const [surface, group] of bySurface) {
193
+ const d = agentDiagnosis(input, surface, group);
194
+ surfaceDiags.set(surface, d);
195
+ out.push(d);
196
+ }
197
+ // 3. The ambient SYNAP_HUB_API_KEY beats the CLI profile — name who sets it
198
+ // when it is not the working key it is meant to be.
199
+ if (input.envKey) {
200
+ const envState = stateOf(input, input.envKey);
201
+ const setBy = envKeySetBy(input.locations, input.envKey);
202
+ const liveAgentKeys = [...surfaceDiags.values()].filter((d) => d.code === "ok" || d.code === "stale_copies").map((d) => d.key);
203
+ const profileKeys = input.locations.filter((l) => l.kind === "profile").map((l) => l.key);
204
+ const designed = envState.state === "active" && (liveAgentKeys.includes(input.envKey) || profileKeys.includes(input.envKey));
205
+ if (!designed) {
206
+ const shell = setBy.filter((l) => l.kind === "shell-rc");
207
+ const fixedWithSurface = setBy.some((l) => l.kind === "claude-settings-env") && shell.length === 0;
208
+ const who = setBy.length ? setBy.map((l) => l.label).join(" and ") : "something outside the files the doctor reads (your terminal or launcher)";
209
+ out.push({
210
+ code: "env_shadow",
211
+ severity: envState.state === "active" ? "warn" : "error",
212
+ title: `SYNAP_HUB_API_KEY overrides your CLI profile key${envState.state === "active" ? "" : " — and it does not work"}`,
213
+ lines: [
214
+ `It is set by ${who}.`,
215
+ `Its key ${tail(input.envKey)} ${describeKeyState(envState)}; every command run with it set uses it instead of ${profileKeys.length ? "the profile key" : "any profile"}.`,
216
+ ...(shell.length ? [`Edit ${shell.map((l) => l.label).join(", ")}: remove that line, or set it to the working key, then open a new shell.`] : []),
217
+ ...(fixedWithSurface ? ["`synap doctor --fix` rewrites it together with the Claude Code key; restart Claude Code afterwards."] : []),
218
+ ],
219
+ command: shell.length ? `edit ${shell[0].label}` : fixedWithSurface ? "synap doctor --fix" : "unset SYNAP_HUB_API_KEY",
220
+ action: shell.length ? "edit_shell_rc" : "none",
221
+ locations: setBy,
222
+ });
223
+ }
224
+ }
225
+ return out;
226
+ }
227
+ //# sourceMappingURL=key-diagnosis.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"key-diagnosis.js","sourceRoot":"","sources":["../../src/lib/key-diagnosis.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,136 @@
1
+ /**
2
+ * Key health for one pod: read every copy, ask the pod about each key, print
3
+ * one diagnosis per problem — and, with `--fix`, do the one right thing.
4
+ *
5
+ * The fix never writes a key the pod has not confirmed live (`assertKeyWritable`),
6
+ * and it ends with a real MCP `initialize` against `/mcp` using the key it
7
+ * wrote: a fix is only reported ✓ when that call succeeds AND every copy it had
8
+ * to rewrite was rewritten.
9
+ *
10
+ * A key is sent to this pod only when something ties it to this pod
11
+ * (`keysToProbe`); keys are asked about ONE AT A TIME. The pod resolves a key it
12
+ * does not know with a bcrypt scan of every key sharing its prefix (~12s on a
13
+ * 4-thread pool, measured 2026-10-12); asked all at once, four unknown keys
14
+ * starved each other past the timeout and read "no answer".
15
+ */
16
+ import { type ClientKeyFile, type KeyLocation, type UncheckedLocation } from "./key-locations.js";
17
+ import { type Diagnosis } from "./key-diagnosis.js";
18
+ import { type FetchLike, type KeyState } from "./key-state.js";
19
+ /** Per-key wait for `/auth/key-state` — an unknown key costs the pod ~12s of bcrypt. */
20
+ export declare const KEY_STATE_TIMEOUT_MS = 30000;
21
+ export interface KeyHealthReport {
22
+ podUrl: string;
23
+ locations: KeyLocation[];
24
+ states: Map<string, KeyState>;
25
+ diagnoses: Diagnosis[];
26
+ /** True when the pod answered the holder door for at least one key (vs an older pod). */
27
+ podDescribesKeys: boolean;
28
+ /** Files the doctor could not read or parse — "not checked", never ✓. */
29
+ unchecked?: UncheckedLocation[];
30
+ /** Copies whose key nothing ties to this pod: listed, never sent to it. */
31
+ notSent?: KeyLocation[];
32
+ }
33
+ export interface KeyHealthDeps {
34
+ home?: string;
35
+ envKey?: string;
36
+ envPodUrl?: string;
37
+ fetch?: FetchLike;
38
+ instanceIdFor?: (surface: string) => string;
39
+ labelOf?: (surface: string) => string;
40
+ /** Client config files to read. Default: derived from `TARGETS` (`clientKeyFiles`). */
41
+ clients?: ClientKeyFile[];
42
+ timeoutMs?: number;
43
+ /**
44
+ * Only this agent surface: its copies are read and its keys asked about —
45
+ * not the person's key, the env, or another agent's (`confirmSurfaceKey`).
46
+ */
47
+ surface?: string;
48
+ }
49
+ export declare function checkKeyHealth(podUrl: string, deps?: KeyHealthDeps): Promise<KeyHealthReport>;
50
+ /** The problems only — `ok` diagnoses are summarised, not listed. */
51
+ export declare function keyProblems(report: KeyHealthReport): Diagnosis[];
52
+ /** A problem `--fix` can act on (not merely tell you a command). */
53
+ export declare function isFixable(d: Diagnosis): boolean;
54
+ /**
55
+ * What setup may say about one agent after writing its config:
56
+ * active — the pod confirms the key now in its files works
57
+ * not-active — the pod (or the files) SAID it does not: pending, revoked,
58
+ * expired, unknown, stale copies, no key where setup writes it —
59
+ * as the doctor's own diagnosis line + command
60
+ * unconfirmed — the check itself FAILED (pod unreachable, file unreadable,
61
+ * read threw). Not a dead key — the doctor prints it "?"
62
+ * unchecked — the target keeps no key the CLI can read back (`keyStore.none`)
63
+ */
64
+ export type SetupCheck = {
65
+ verdict: "active";
66
+ } | {
67
+ verdict: "not-active";
68
+ title: string;
69
+ command?: string;
70
+ } | {
71
+ verdict: "unconfirmed";
72
+ reason: string;
73
+ } | {
74
+ verdict: "unchecked";
75
+ reason: string;
76
+ };
77
+ /**
78
+ * The check behind every "<Agent> connected" line: read back what setup WROTE
79
+ * for `surface` — the same copies `synap doctor` reads — ask the pod about each
80
+ * key, and pass only when the doctor would say "key works". The 2026-10-15
81
+ * devbox printed "✓ Claude Code connected" over a key the pod held as
82
+ * awaiting approval; a success line now comes from this read, never from
83
+ * having written the file.
84
+ */
85
+ export declare function confirmSurfaceKey(podUrl: string, surface: string, deps?: KeyHealthDeps): Promise<SetupCheck>;
86
+ /**
87
+ * Print what is wrong, and what could not be checked. Working keys are one
88
+ * line (listed with `verbose`); an unverifiable key is "?", never ✓ or ✗.
89
+ */
90
+ export declare function printKeyHealth(report: KeyHealthReport, opts?: {
91
+ fixHint?: boolean;
92
+ verbose?: boolean;
93
+ showOk?: boolean;
94
+ indent?: string;
95
+ }): void;
96
+ export interface RewriteResult {
97
+ /** Every copy that now holds the live key (rewritten or already there). */
98
+ done: string[];
99
+ /** Copies that should hold it and could not be rewritten — with why. */
100
+ failed: string[];
101
+ }
102
+ /**
103
+ * Write `key` into every rewritable copy of `surface` for this pod — ONLY after
104
+ * the pod confirms it is live. A copy that cannot be rewritten is reported in
105
+ * `failed`, never dropped.
106
+ */
107
+ export declare function rewriteSurfaceKey(report: KeyHealthReport, surface: string, key: string, agentUserId: string | undefined, deps?: {
108
+ fetch?: FetchLike;
109
+ home?: string;
110
+ }): Promise<RewriteResult>;
111
+ export interface FixDeps {
112
+ fetch?: FetchLike;
113
+ openUrl?: (url: string) => void;
114
+ /** Wait for a pending key (default `waitForKeyLive`). */
115
+ wait?: (args: {
116
+ podUrl: string;
117
+ pendingKey: string;
118
+ }) => Promise<"approved" | "rejected" | "timeout">;
119
+ /** Make a new key for this computer (default `provisionAgentKey`, which waits for approval). */
120
+ provision?: (podUrl: string, mintingKey: string, agentType: string, surface: string) => Promise<{
121
+ hubApiKey: string;
122
+ agentUserId: string;
123
+ }>;
124
+ verify?: (podUrl: string, key: string) => Promise<{
125
+ ok: boolean;
126
+ toolCount?: number;
127
+ error?: string;
128
+ }>;
129
+ }
130
+ export interface FixOutcome {
131
+ diagnosis: Diagnosis;
132
+ ok: boolean;
133
+ message: string;
134
+ }
135
+ /** Perform each diagnosis's one action, then verify with a real MCP initialize. */
136
+ export declare function fixKeyHealth(report: KeyHealthReport, deps?: FixDeps): Promise<FixOutcome[]>;