@canonical/pragma-cli 0.33.0 → 0.35.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 (892) hide show
  1. package/README.md +153 -30
  2. package/dist/.build-ok +0 -0
  3. package/dist/package.json +83 -0
  4. package/dist/pragma.conf.js +814 -0
  5. package/dist/pragma.conf.js.map +1 -0
  6. package/dist/src/bin.js +356 -0
  7. package/dist/src/bin.js.map +1 -0
  8. package/dist/src/capabilities/capabilities/capabilities.render.js +70 -0
  9. package/dist/src/capabilities/capabilities/capabilities.render.js.map +1 -0
  10. package/dist/src/capabilities/capabilities/capabilities.verb.js +59 -0
  11. package/dist/src/capabilities/capabilities/capabilities.verb.js.map +1 -0
  12. package/dist/src/capabilities/capabilities/catalog.js +130 -0
  13. package/dist/src/capabilities/capabilities/catalog.js.map +1 -0
  14. package/dist/src/capabilities/capabilities/hints.js +195 -0
  15. package/dist/src/capabilities/capabilities/hints.js.map +1 -0
  16. package/dist/src/capabilities/capabilities/index.js +11 -0
  17. package/dist/src/capabilities/capabilities/index.js.map +1 -0
  18. package/dist/src/capabilities/capabilities/types.js +11 -0
  19. package/dist/src/capabilities/capabilities/types.js.map +1 -0
  20. package/dist/src/capabilities/colophon/collectColophon.js +83 -0
  21. package/dist/src/capabilities/colophon/collectColophon.js.map +1 -0
  22. package/dist/src/capabilities/colophon/colophon.render.js +59 -0
  23. package/dist/src/capabilities/colophon/colophon.render.js.map +1 -0
  24. package/dist/src/capabilities/colophon/colophon.verb.js +43 -0
  25. package/dist/src/capabilities/colophon/colophon.verb.js.map +1 -0
  26. package/dist/src/capabilities/colophon/index.js +5 -0
  27. package/dist/src/capabilities/colophon/index.js.map +1 -0
  28. package/dist/src/capabilities/colophon/markdownTerminal.js +90 -0
  29. package/dist/src/capabilities/colophon/markdownTerminal.js.map +1 -0
  30. package/dist/src/capabilities/colophon/types.js +10 -0
  31. package/dist/src/capabilities/colophon/types.js.map +1 -0
  32. package/dist/src/capabilities/config/collectConfigShow.js +59 -0
  33. package/dist/src/capabilities/config/collectConfigShow.js.map +1 -0
  34. package/dist/src/capabilities/config/field.render.js +22 -0
  35. package/dist/src/capabilities/config/field.render.js.map +1 -0
  36. package/dist/src/capabilities/config/fields.js +46 -0
  37. package/dist/src/capabilities/config/fields.js.map +1 -0
  38. package/dist/src/capabilities/config/get.verb.js +61 -0
  39. package/dist/src/capabilities/config/get.verb.js.map +1 -0
  40. package/dist/src/capabilities/config/index.js +5 -0
  41. package/dist/src/capabilities/config/index.js.map +1 -0
  42. package/dist/src/capabilities/config/runField.js +59 -0
  43. package/dist/src/capabilities/config/runField.js.map +1 -0
  44. package/dist/src/capabilities/config/runGet.js +28 -0
  45. package/dist/src/capabilities/config/runGet.js.map +1 -0
  46. package/dist/src/capabilities/config/runSet.js +53 -0
  47. package/dist/src/capabilities/config/runSet.js.map +1 -0
  48. package/dist/src/capabilities/config/set.verb.js +66 -0
  49. package/dist/src/capabilities/config/set.verb.js.map +1 -0
  50. package/dist/src/capabilities/config/show.render.js +84 -0
  51. package/dist/src/capabilities/config/show.render.js.map +1 -0
  52. package/dist/src/capabilities/config/show.verb.js +44 -0
  53. package/dist/src/capabilities/config/show.verb.js.map +1 -0
  54. package/dist/src/capabilities/config/types.js +5 -0
  55. package/dist/src/capabilities/config/types.js.map +1 -0
  56. package/dist/src/capabilities/config/unset.verb.js +49 -0
  57. package/dist/src/capabilities/config/unset.verb.js.map +1 -0
  58. package/dist/src/capabilities/create/cliProjection.js +195 -0
  59. package/dist/src/capabilities/create/cliProjection.js.map +1 -0
  60. package/dist/src/capabilities/create/constants.js +47 -0
  61. package/dist/src/capabilities/create/constants.js.map +1 -0
  62. package/dist/src/capabilities/create/create.render.js +100 -0
  63. package/dist/src/capabilities/create/create.render.js.map +1 -0
  64. package/dist/src/capabilities/create/create.verb.js +438 -0
  65. package/dist/src/capabilities/create/create.verb.js.map +1 -0
  66. package/dist/src/capabilities/create/createHelp.js +47 -0
  67. package/dist/src/capabilities/create/createHelp.js.map +1 -0
  68. package/dist/src/capabilities/create/createSurface.generated.js +394 -0
  69. package/dist/src/capabilities/create/createSurface.generated.js.map +1 -0
  70. package/dist/src/capabilities/create/generatorToVerbSpec.js +106 -0
  71. package/dist/src/capabilities/create/generatorToVerbSpec.js.map +1 -0
  72. package/dist/src/capabilities/create/index.js +18 -0
  73. package/dist/src/capabilities/create/index.js.map +1 -0
  74. package/dist/src/capabilities/create/messages.js +16 -0
  75. package/dist/src/capabilities/create/messages.js.map +1 -0
  76. package/dist/src/capabilities/create/mount.js +293 -0
  77. package/dist/src/capabilities/create/mount.js.map +1 -0
  78. package/dist/src/capabilities/create/pathJail.js +65 -0
  79. package/dist/src/capabilities/create/pathJail.js.map +1 -0
  80. package/dist/src/capabilities/create/pickGenerator.js +53 -0
  81. package/dist/src/capabilities/create/pickGenerator.js.map +1 -0
  82. package/dist/src/capabilities/create/types.js +2 -0
  83. package/dist/src/capabilities/create/types.js.map +1 -0
  84. package/dist/src/capabilities/distribution.js +40 -0
  85. package/dist/src/capabilities/distribution.js.map +1 -0
  86. package/dist/src/capabilities/doctor/checks/checkKeStore.js +40 -0
  87. package/dist/src/capabilities/doctor/checks/checkKeStore.js.map +1 -0
  88. package/dist/src/capabilities/doctor/checks/checkNodeVersion.js +21 -0
  89. package/dist/src/capabilities/doctor/checks/checkNodeVersion.js.map +1 -0
  90. package/dist/src/capabilities/doctor/checks/checkPackageRefs.js +92 -0
  91. package/dist/src/capabilities/doctor/checks/checkPackageRefs.js.map +1 -0
  92. package/dist/src/capabilities/doctor/checks/checkPragmaVersion.js +19 -0
  93. package/dist/src/capabilities/doctor/checks/checkPragmaVersion.js.map +1 -0
  94. package/dist/src/capabilities/doctor/checks/checkShellCompletions.js +199 -0
  95. package/dist/src/capabilities/doctor/checks/checkShellCompletions.js.map +1 -0
  96. package/dist/src/capabilities/doctor/checks/index.js +27 -0
  97. package/dist/src/capabilities/doctor/checks/index.js.map +1 -0
  98. package/dist/src/capabilities/doctor/checks/mcpCommand.js +57 -0
  99. package/dist/src/capabilities/doctor/checks/mcpCommand.js.map +1 -0
  100. package/dist/src/capabilities/doctor/checks/targetHealth.js +205 -0
  101. package/dist/src/capabilities/doctor/checks/targetHealth.js.map +1 -0
  102. package/dist/src/capabilities/doctor/doctor.render.js +185 -0
  103. package/dist/src/capabilities/doctor/doctor.render.js.map +1 -0
  104. package/dist/src/capabilities/doctor/doctor.verb.js +45 -0
  105. package/dist/src/capabilities/doctor/doctor.verb.js.map +1 -0
  106. package/dist/src/capabilities/doctor/index.js +5 -0
  107. package/dist/src/capabilities/doctor/index.js.map +1 -0
  108. package/dist/src/capabilities/doctor/runChecks.js +83 -0
  109. package/dist/src/capabilities/doctor/runChecks.js.map +1 -0
  110. package/dist/src/capabilities/doctor/types.js +5 -0
  111. package/dist/src/capabilities/doctor/types.js.map +1 -0
  112. package/dist/src/capabilities/graph/index.js +19 -0
  113. package/dist/src/capabilities/graph/index.js.map +1 -0
  114. package/dist/src/capabilities/graph/inspect.render.js +76 -0
  115. package/dist/src/capabilities/graph/inspect.render.js.map +1 -0
  116. package/dist/src/capabilities/graph/inspect.verb.js +53 -0
  117. package/dist/src/capabilities/graph/inspect.verb.js.map +1 -0
  118. package/dist/src/capabilities/graph/query.render.js +73 -0
  119. package/dist/src/capabilities/graph/query.render.js.map +1 -0
  120. package/dist/src/capabilities/graph/query.verb.js +49 -0
  121. package/dist/src/capabilities/graph/query.verb.js.map +1 -0
  122. package/dist/src/capabilities/graph/runQuery.js +41 -0
  123. package/dist/src/capabilities/graph/runQuery.js.map +1 -0
  124. package/dist/src/capabilities/index.js +56 -0
  125. package/dist/src/capabilities/index.js.map +1 -0
  126. package/dist/src/capabilities/info/collectInfo.js +66 -0
  127. package/dist/src/capabilities/info/collectInfo.js.map +1 -0
  128. package/dist/src/capabilities/info/index.js +5 -0
  129. package/dist/src/capabilities/info/index.js.map +1 -0
  130. package/dist/src/capabilities/info/info.render.js +53 -0
  131. package/dist/src/capabilities/info/info.render.js.map +1 -0
  132. package/dist/src/capabilities/info/info.verb.js +42 -0
  133. package/dist/src/capabilities/info/info.verb.js.map +1 -0
  134. package/dist/src/capabilities/info/types.js +5 -0
  135. package/dist/src/capabilities/info/types.js.map +1 -0
  136. package/dist/src/capabilities/meta/complete.verb.js +43 -0
  137. package/dist/src/capabilities/meta/complete.verb.js.map +1 -0
  138. package/dist/src/capabilities/meta/index.js +13 -0
  139. package/dist/src/capabilities/meta/index.js.map +1 -0
  140. package/dist/src/capabilities/meta/mcp.verb.js +34 -0
  141. package/dist/src/capabilities/meta/mcp.verb.js.map +1 -0
  142. package/dist/src/capabilities/ontology/index.js +21 -0
  143. package/dist/src/capabilities/ontology/index.js.map +1 -0
  144. package/dist/src/capabilities/ontology/queries.js +123 -0
  145. package/dist/src/capabilities/ontology/queries.js.map +1 -0
  146. package/dist/src/capabilities/ontology/render.js +66 -0
  147. package/dist/src/capabilities/ontology/render.js.map +1 -0
  148. package/dist/src/capabilities/ontology/verbs.js +181 -0
  149. package/dist/src/capabilities/ontology/verbs.js.map +1 -0
  150. package/dist/src/capabilities/prompt/index.js +16 -0
  151. package/dist/src/capabilities/prompt/index.js.map +1 -0
  152. package/dist/src/capabilities/prompt/prompt.render.js +78 -0
  153. package/dist/src/capabilities/prompt/prompt.render.js.map +1 -0
  154. package/dist/src/capabilities/prompt/types.js +10 -0
  155. package/dist/src/capabilities/prompt/types.js.map +1 -0
  156. package/dist/src/capabilities/prompt/verbs.js +93 -0
  157. package/dist/src/capabilities/prompt/verbs.js.map +1 -0
  158. package/dist/src/capabilities/resources/index.js +10 -0
  159. package/dist/src/capabilities/resources/index.js.map +1 -0
  160. package/dist/src/capabilities/resources/provider.js +423 -0
  161. package/dist/src/capabilities/resources/provider.js.map +1 -0
  162. package/dist/src/capabilities/setup/buildPlan.js +168 -0
  163. package/dist/src/capabilities/setup/buildPlan.js.map +1 -0
  164. package/dist/src/capabilities/setup/index.js +5 -0
  165. package/dist/src/capabilities/setup/index.js.map +1 -0
  166. package/dist/src/capabilities/setup/mode.js +53 -0
  167. package/dist/src/capabilities/setup/mode.js.map +1 -0
  168. package/dist/src/capabilities/setup/operations/index.js +39 -0
  169. package/dist/src/capabilities/setup/operations/index.js.map +1 -0
  170. package/dist/src/capabilities/setup/operations/setupCompletions.js +160 -0
  171. package/dist/src/capabilities/setup/operations/setupCompletions.js.map +1 -0
  172. package/dist/src/capabilities/setup/operations/setupConfig.js +101 -0
  173. package/dist/src/capabilities/setup/operations/setupConfig.js.map +1 -0
  174. package/dist/src/capabilities/setup/operations/setupGenerator.js +343 -0
  175. package/dist/src/capabilities/setup/operations/setupGenerator.js.map +1 -0
  176. package/dist/src/capabilities/setup/operations/setupLsp.js +277 -0
  177. package/dist/src/capabilities/setup/operations/setupLsp.js.map +1 -0
  178. package/dist/src/capabilities/setup/operations/setupMcp.js +207 -0
  179. package/dist/src/capabilities/setup/operations/setupMcp.js.map +1 -0
  180. package/dist/src/capabilities/setup/operations/setupSkills.js +316 -0
  181. package/dist/src/capabilities/setup/operations/setupSkills.js.map +1 -0
  182. package/dist/src/capabilities/setup/plan.js +128 -0
  183. package/dist/src/capabilities/setup/plan.js.map +1 -0
  184. package/dist/src/capabilities/setup/plan.render.js +193 -0
  185. package/dist/src/capabilities/setup/plan.render.js.map +1 -0
  186. package/dist/src/capabilities/setup/setup.render.js +54 -0
  187. package/dist/src/capabilities/setup/setup.render.js.map +1 -0
  188. package/dist/src/capabilities/setup/setup.verb.js +334 -0
  189. package/dist/src/capabilities/setup/setup.verb.js.map +1 -0
  190. package/dist/src/capabilities/setup/shell.js +196 -0
  191. package/dist/src/capabilities/setup/shell.js.map +1 -0
  192. package/dist/src/capabilities/setup/targets.js +263 -0
  193. package/dist/src/capabilities/setup/targets.js.map +1 -0
  194. package/dist/src/capabilities/setup/types.js +5 -0
  195. package/dist/src/capabilities/setup/types.js.map +1 -0
  196. package/dist/src/capabilities/shared/assertExecOk.js +137 -0
  197. package/dist/src/capabilities/shared/assertExecOk.js.map +1 -0
  198. package/dist/src/capabilities/shared/bands.js +16 -0
  199. package/dist/src/capabilities/shared/bands.js.map +1 -0
  200. package/dist/src/capabilities/shared/index.js +26 -0
  201. package/dist/src/capabilities/shared/index.js.map +1 -0
  202. package/dist/src/capabilities/shared/packageManager.js +103 -0
  203. package/dist/src/capabilities/shared/packageManager.js.map +1 -0
  204. package/dist/src/capabilities/shared/registry.js +55 -0
  205. package/dist/src/capabilities/shared/registry.js.map +1 -0
  206. package/dist/src/capabilities/skill/discover.js +195 -0
  207. package/dist/src/capabilities/skill/discover.js.map +1 -0
  208. package/dist/src/capabilities/skill/index.js +10 -0
  209. package/dist/src/capabilities/skill/index.js.map +1 -0
  210. package/dist/src/capabilities/skill/render.js +49 -0
  211. package/dist/src/capabilities/skill/render.js.map +1 -0
  212. package/dist/src/capabilities/skill/verbs.js +83 -0
  213. package/dist/src/capabilities/skill/verbs.js.map +1 -0
  214. package/dist/src/capabilities/sources/collectStatus.js +103 -0
  215. package/dist/src/capabilities/sources/collectStatus.js.map +1 -0
  216. package/dist/src/capabilities/sources/index.js +13 -0
  217. package/dist/src/capabilities/sources/index.js.map +1 -0
  218. package/dist/src/capabilities/sources/installSkills.js +167 -0
  219. package/dist/src/capabilities/sources/installSkills.js.map +1 -0
  220. package/dist/src/capabilities/sources/runUpdate.js +394 -0
  221. package/dist/src/capabilities/sources/runUpdate.js.map +1 -0
  222. package/dist/src/capabilities/sources/status.render.js +64 -0
  223. package/dist/src/capabilities/sources/status.render.js.map +1 -0
  224. package/dist/src/capabilities/sources/status.verb.js +40 -0
  225. package/dist/src/capabilities/sources/status.verb.js.map +1 -0
  226. package/dist/src/capabilities/sources/types.js +6 -0
  227. package/dist/src/capabilities/sources/types.js.map +1 -0
  228. package/dist/src/capabilities/sources/update.render.js +34 -0
  229. package/dist/src/capabilities/sources/update.render.js.map +1 -0
  230. package/dist/src/capabilities/sources/update.verb.js +55 -0
  231. package/dist/src/capabilities/sources/update.verb.js.map +1 -0
  232. package/dist/src/capabilities/upgrade/index.js +5 -0
  233. package/dist/src/capabilities/upgrade/index.js.map +1 -0
  234. package/dist/src/capabilities/upgrade/runUpgrade.js +99 -0
  235. package/dist/src/capabilities/upgrade/runUpgrade.js.map +1 -0
  236. package/dist/src/capabilities/upgrade/types.js +5 -0
  237. package/dist/src/capabilities/upgrade/types.js.map +1 -0
  238. package/dist/src/capabilities/upgrade/upgrade.render.js +44 -0
  239. package/dist/src/capabilities/upgrade/upgrade.render.js.map +1 -0
  240. package/dist/src/capabilities/upgrade/upgrade.verb.js +52 -0
  241. package/dist/src/capabilities/upgrade/upgrade.verb.js.map +1 -0
  242. package/dist/src/capabilities/version/index.js +10 -0
  243. package/dist/src/capabilities/version/index.js.map +1 -0
  244. package/dist/src/capabilities/version/version.verb.js +36 -0
  245. package/dist/src/capabilities/version/version.verb.js.map +1 -0
  246. package/dist/src/constants.js +82 -0
  247. package/dist/src/constants.js.map +1 -0
  248. package/dist/src/index.js +12 -0
  249. package/dist/src/index.js.map +1 -0
  250. package/dist/src/kernel/completion/complete.js +66 -0
  251. package/dist/src/kernel/completion/complete.js.map +1 -0
  252. package/dist/src/kernel/completion/emitScripts.js +92 -0
  253. package/dist/src/kernel/completion/emitScripts.js.map +1 -0
  254. package/dist/src/kernel/completion/entitySource.js +285 -0
  255. package/dist/src/kernel/completion/entitySource.js.map +1 -0
  256. package/dist/src/kernel/completion/index.js +14 -0
  257. package/dist/src/kernel/completion/index.js.map +1 -0
  258. package/dist/src/kernel/completion/model.js +301 -0
  259. package/dist/src/kernel/completion/model.js.map +1 -0
  260. package/dist/src/kernel/completion/parse.js +253 -0
  261. package/dist/src/kernel/completion/parse.js.map +1 -0
  262. package/dist/src/kernel/completion/rank.js +101 -0
  263. package/dist/src/kernel/completion/rank.js.map +1 -0
  264. package/dist/src/kernel/completion/resolve.js +100 -0
  265. package/dist/src/kernel/completion/resolve.js.map +1 -0
  266. package/dist/src/kernel/completion/templates/bash.js +209 -0
  267. package/dist/src/kernel/completion/templates/bash.js.map +1 -0
  268. package/dist/src/kernel/completion/templates/fish.js +214 -0
  269. package/dist/src/kernel/completion/templates/fish.js.map +1 -0
  270. package/dist/src/kernel/completion/templates/index.js +23 -0
  271. package/dist/src/kernel/completion/templates/index.js.map +1 -0
  272. package/dist/src/kernel/completion/templates/shared.js +98 -0
  273. package/dist/src/kernel/completion/templates/shared.js.map +1 -0
  274. package/dist/src/kernel/completion/templates/zsh.js +201 -0
  275. package/dist/src/kernel/completion/templates/zsh.js.map +1 -0
  276. package/dist/src/kernel/completion/types.js +13 -0
  277. package/dist/src/kernel/completion/types.js.map +1 -0
  278. package/dist/src/kernel/config/defaults.js +17 -0
  279. package/dist/src/kernel/config/defaults.js.map +1 -0
  280. package/dist/src/kernel/config/evaluateProjectConfig.js +126 -0
  281. package/dist/src/kernel/config/evaluateProjectConfig.js.map +1 -0
  282. package/dist/src/kernel/config/findProjectConfig.js +43 -0
  283. package/dist/src/kernel/config/findProjectConfig.js.map +1 -0
  284. package/dist/src/kernel/config/firstRun.js +34 -0
  285. package/dist/src/kernel/config/firstRun.js.map +1 -0
  286. package/dist/src/kernel/config/globalConfig.js +79 -0
  287. package/dist/src/kernel/config/globalConfig.js.map +1 -0
  288. package/dist/src/kernel/config/index.js +16 -0
  289. package/dist/src/kernel/config/index.js.map +1 -0
  290. package/dist/src/kernel/config/paths.js +35 -0
  291. package/dist/src/kernel/config/paths.js.map +1 -0
  292. package/dist/src/kernel/config/readConfig.js +78 -0
  293. package/dist/src/kernel/config/readConfig.js.map +1 -0
  294. package/dist/src/kernel/config/schema.js +130 -0
  295. package/dist/src/kernel/config/schema.js.map +1 -0
  296. package/dist/src/kernel/config/types.js +19 -0
  297. package/dist/src/kernel/config/types.js.map +1 -0
  298. package/dist/src/kernel/config/writeConfigField.js +59 -0
  299. package/dist/src/kernel/config/writeConfigField.js.map +1 -0
  300. package/dist/src/kernel/copy.js +43 -0
  301. package/dist/src/kernel/copy.js.map +1 -0
  302. package/dist/src/kernel/error/PragmaError.js +149 -0
  303. package/dist/src/kernel/error/PragmaError.js.map +1 -0
  304. package/dist/src/kernel/error/constants.js +40 -0
  305. package/dist/src/kernel/error/constants.js.map +1 -0
  306. package/dist/src/kernel/error/fromTaskError.js +96 -0
  307. package/dist/src/kernel/error/fromTaskError.js.map +1 -0
  308. package/dist/src/kernel/error/index.js +13 -0
  309. package/dist/src/kernel/error/index.js.map +1 -0
  310. package/dist/src/kernel/error/recovery.js +52 -0
  311. package/dist/src/kernel/error/recovery.js.map +1 -0
  312. package/dist/src/kernel/error/renderError.js +115 -0
  313. package/dist/src/kernel/error/renderError.js.map +1 -0
  314. package/dist/src/kernel/error/serialize.js +25 -0
  315. package/dist/src/kernel/error/serialize.js.map +1 -0
  316. package/dist/src/kernel/error/types.js +9 -0
  317. package/dist/src/kernel/error/types.js.map +1 -0
  318. package/dist/src/kernel/index.js +25 -0
  319. package/dist/src/kernel/index.js.map +1 -0
  320. package/dist/src/kernel/packs/collect.js +187 -0
  321. package/dist/src/kernel/packs/collect.js.map +1 -0
  322. package/dist/src/kernel/packs/compile.js +304 -0
  323. package/dist/src/kernel/packs/compile.js.map +1 -0
  324. package/dist/src/kernel/packs/disclosure.js +76 -0
  325. package/dist/src/kernel/packs/disclosure.js.map +1 -0
  326. package/dist/src/kernel/packs/glob.js +38 -0
  327. package/dist/src/kernel/packs/glob.js.map +1 -0
  328. package/dist/src/kernel/packs/graphql/buildLookupDocument.js +258 -0
  329. package/dist/src/kernel/packs/graphql/buildLookupDocument.js.map +1 -0
  330. package/dist/src/kernel/packs/graphql/fetchGraphqlLookup.js +157 -0
  331. package/dist/src/kernel/packs/graphql/fetchGraphqlLookup.js.map +1 -0
  332. package/dist/src/kernel/packs/graphql/index.js +20 -0
  333. package/dist/src/kernel/packs/graphql/index.js.map +1 -0
  334. package/dist/src/kernel/packs/graphql/nameMap.js +63 -0
  335. package/dist/src/kernel/packs/graphql/nameMap.js.map +1 -0
  336. package/dist/src/kernel/packs/index.js +34 -0
  337. package/dist/src/kernel/packs/index.js.map +1 -0
  338. package/dist/src/kernel/packs/iri.js +110 -0
  339. package/dist/src/kernel/packs/iri.js.map +1 -0
  340. package/dist/src/kernel/packs/renderPack.js +129 -0
  341. package/dist/src/kernel/packs/renderPack.js.map +1 -0
  342. package/dist/src/kernel/packs/resolveEntity.js +223 -0
  343. package/dist/src/kernel/packs/resolveEntity.js.map +1 -0
  344. package/dist/src/kernel/packs/runBodies.js +87 -0
  345. package/dist/src/kernel/packs/runBodies.js.map +1 -0
  346. package/dist/src/kernel/packs/sample.js +56 -0
  347. package/dist/src/kernel/packs/sample.js.map +1 -0
  348. package/dist/src/kernel/packs/schema.js +369 -0
  349. package/dist/src/kernel/packs/schema.js.map +1 -0
  350. package/dist/src/kernel/packs/sparql/applyFilters.js +68 -0
  351. package/dist/src/kernel/packs/sparql/applyFilters.js.map +1 -0
  352. package/dist/src/kernel/packs/sparql/applySearch.js +25 -0
  353. package/dist/src/kernel/packs/sparql/applySearch.js.map +1 -0
  354. package/dist/src/kernel/packs/sparql/buildLookupQuery.js +217 -0
  355. package/dist/src/kernel/packs/sparql/buildLookupQuery.js.map +1 -0
  356. package/dist/src/kernel/packs/sparql/escape.js +21 -0
  357. package/dist/src/kernel/packs/sparql/escape.js.map +1 -0
  358. package/dist/src/kernel/packs/sparql/index.js +31 -0
  359. package/dist/src/kernel/packs/sparql/index.js.map +1 -0
  360. package/dist/src/kernel/packs/sparql/runSelect.js +101 -0
  361. package/dist/src/kernel/packs/sparql/runSelect.js.map +1 -0
  362. package/dist/src/kernel/packs/types.js +30 -0
  363. package/dist/src/kernel/packs/types.js.map +1 -0
  364. package/dist/src/kernel/packs/uniqueness.js +30 -0
  365. package/dist/src/kernel/packs/uniqueness.js.map +1 -0
  366. package/dist/src/kernel/project/cli/buildProgram.js +263 -0
  367. package/dist/src/kernel/project/cli/buildProgram.js.map +1 -0
  368. package/dist/src/kernel/project/cli/constants.js +27 -0
  369. package/dist/src/kernel/project/cli/constants.js.map +1 -0
  370. package/dist/src/kernel/project/cli/dispatch.js +420 -0
  371. package/dist/src/kernel/project/cli/dispatch.js.map +1 -0
  372. package/dist/src/kernel/project/cli/exitCodes.js +66 -0
  373. package/dist/src/kernel/project/cli/exitCodes.js.map +1 -0
  374. package/dist/src/kernel/project/cli/globalFlags.js +216 -0
  375. package/dist/src/kernel/project/cli/globalFlags.js.map +1 -0
  376. package/dist/src/kernel/project/cli/helpFormat.js +59 -0
  377. package/dist/src/kernel/project/cli/helpFormat.js.map +1 -0
  378. package/dist/src/kernel/project/cli/index.js +14 -0
  379. package/dist/src/kernel/project/cli/index.js.map +1 -0
  380. package/dist/src/kernel/project/cli/rootHelp.js +197 -0
  381. package/dist/src/kernel/project/cli/rootHelp.js.map +1 -0
  382. package/dist/src/kernel/project/cli/suggest.js +75 -0
  383. package/dist/src/kernel/project/cli/suggest.js.map +1 -0
  384. package/dist/src/kernel/project/cli/suggestNames.js +96 -0
  385. package/dist/src/kernel/project/cli/suggestNames.js.map +1 -0
  386. package/dist/src/kernel/project/cli/verbHelp.js +131 -0
  387. package/dist/src/kernel/project/cli/verbHelp.js.map +1 -0
  388. package/dist/src/kernel/project/mcp/buildServer.js +67 -0
  389. package/dist/src/kernel/project/mcp/buildServer.js.map +1 -0
  390. package/dist/src/kernel/project/mcp/envelope.js +37 -0
  391. package/dist/src/kernel/project/mcp/envelope.js.map +1 -0
  392. package/dist/src/kernel/project/mcp/index.js +8 -0
  393. package/dist/src/kernel/project/mcp/index.js.map +1 -0
  394. package/dist/src/kernel/project/mcp/instructions.js +44 -0
  395. package/dist/src/kernel/project/mcp/instructions.js.map +1 -0
  396. package/dist/src/kernel/project/mcp/mcpError.js +42 -0
  397. package/dist/src/kernel/project/mcp/mcpError.js.map +1 -0
  398. package/dist/src/kernel/project/mcp/prompts/index.js +36 -0
  399. package/dist/src/kernel/project/mcp/prompts/index.js.map +1 -0
  400. package/dist/src/kernel/project/mcp/prompts/provider.js +98 -0
  401. package/dist/src/kernel/project/mcp/prompts/provider.js.map +1 -0
  402. package/dist/src/kernel/project/mcp/prompts/source.js +154 -0
  403. package/dist/src/kernel/project/mcp/prompts/source.js.map +1 -0
  404. package/dist/src/kernel/project/mcp/registerVerb.js +300 -0
  405. package/dist/src/kernel/project/mcp/registerVerb.js.map +1 -0
  406. package/dist/src/kernel/project/mcp/serve.js +35 -0
  407. package/dist/src/kernel/project/mcp/serve.js.map +1 -0
  408. package/dist/src/kernel/render/compactUri.js +24 -0
  409. package/dist/src/kernel/render/compactUri.js.map +1 -0
  410. package/dist/src/kernel/render/contracts.js +10 -0
  411. package/dist/src/kernel/render/contracts.js.map +1 -0
  412. package/dist/src/kernel/render/disclosure.js +34 -0
  413. package/dist/src/kernel/render/disclosure.js.map +1 -0
  414. package/dist/src/kernel/render/envelope.js +30 -0
  415. package/dist/src/kernel/render/envelope.js.map +1 -0
  416. package/dist/src/kernel/render/formatters.js +27 -0
  417. package/dist/src/kernel/render/formatters.js.map +1 -0
  418. package/dist/src/kernel/render/index.js +15 -0
  419. package/dist/src/kernel/render/index.js.map +1 -0
  420. package/dist/src/kernel/render/prefixes.js +46 -0
  421. package/dist/src/kernel/render/prefixes.js.map +1 -0
  422. package/dist/src/kernel/render/renderers.js +468 -0
  423. package/dist/src/kernel/render/renderers.js.map +1 -0
  424. package/dist/src/kernel/render/style.js +85 -0
  425. package/dist/src/kernel/render/style.js.map +1 -0
  426. package/dist/src/kernel/render/turtle.js +194 -0
  427. package/dist/src/kernel/render/turtle.js.map +1 -0
  428. package/dist/src/kernel/render/writeStdout.js +43 -0
  429. package/dist/src/kernel/render/writeStdout.js.map +1 -0
  430. package/dist/src/kernel/runtime/boot.js +49 -0
  431. package/dist/src/kernel/runtime/boot.js.map +1 -0
  432. package/dist/src/kernel/runtime/facade.js +39 -0
  433. package/dist/src/kernel/runtime/facade.js.map +1 -0
  434. package/dist/src/kernel/runtime/graphpack/build.js +122 -0
  435. package/dist/src/kernel/runtime/graphpack/build.js.map +1 -0
  436. package/dist/src/kernel/runtime/graphpack/buildIndex.js +303 -0
  437. package/dist/src/kernel/runtime/graphpack/buildIndex.js.map +1 -0
  438. package/dist/src/kernel/runtime/graphpack/embedded/pack.generated.js +6 -0
  439. package/dist/src/kernel/runtime/graphpack/embedded/pack.generated.js.map +1 -0
  440. package/dist/src/kernel/runtime/graphpack/embedded/pack.index.generated.js +4 -0
  441. package/dist/src/kernel/runtime/graphpack/embedded/pack.index.generated.js.map +1 -0
  442. package/dist/src/kernel/runtime/graphpack/embedded/pack.stories.generated.js +4 -0
  443. package/dist/src/kernel/runtime/graphpack/embedded/pack.stories.generated.js.map +1 -0
  444. package/dist/src/kernel/runtime/graphpack/embedded.js +82 -0
  445. package/dist/src/kernel/runtime/graphpack/embedded.js.map +1 -0
  446. package/dist/src/kernel/runtime/graphpack/hash.js +38 -0
  447. package/dist/src/kernel/runtime/graphpack/hash.js.map +1 -0
  448. package/dist/src/kernel/runtime/graphpack/index.js +11 -0
  449. package/dist/src/kernel/runtime/graphpack/index.js.map +1 -0
  450. package/dist/src/kernel/runtime/graphpack/manifest.js +145 -0
  451. package/dist/src/kernel/runtime/graphpack/manifest.js.map +1 -0
  452. package/dist/src/kernel/runtime/graphpack/read.js +92 -0
  453. package/dist/src/kernel/runtime/graphpack/read.js.map +1 -0
  454. package/dist/src/kernel/runtime/graphpack/schemas.js +70 -0
  455. package/dist/src/kernel/runtime/graphpack/schemas.js.map +1 -0
  456. package/dist/src/kernel/runtime/graphpack/stories.js +68 -0
  457. package/dist/src/kernel/runtime/graphpack/stories.js.map +1 -0
  458. package/dist/src/kernel/runtime/graphpack/types.js +55 -0
  459. package/dist/src/kernel/runtime/graphpack/types.js.map +1 -0
  460. package/dist/src/kernel/runtime/index.js +8 -0
  461. package/dist/src/kernel/runtime/index.js.map +1 -0
  462. package/dist/src/kernel/runtime/loadSession.js +34 -0
  463. package/dist/src/kernel/runtime/loadSession.js.map +1 -0
  464. package/dist/src/kernel/runtime/paths.js +78 -0
  465. package/dist/src/kernel/runtime/paths.js.map +1 -0
  466. package/dist/src/kernel/runtime/probe.js +37 -0
  467. package/dist/src/kernel/runtime/probe.js.map +1 -0
  468. package/dist/src/kernel/runtime/readEntity.js +363 -0
  469. package/dist/src/kernel/runtime/readEntity.js.map +1 -0
  470. package/dist/src/kernel/runtime/refs/gitOps.js +65 -0
  471. package/dist/src/kernel/runtime/refs/gitOps.js.map +1 -0
  472. package/dist/src/kernel/runtime/refs/index.js +29 -0
  473. package/dist/src/kernel/runtime/refs/index.js.map +1 -0
  474. package/dist/src/kernel/runtime/refs/parseRef.js +70 -0
  475. package/dist/src/kernel/runtime/refs/parseRef.js.map +1 -0
  476. package/dist/src/kernel/runtime/refs/resolve.js +332 -0
  477. package/dist/src/kernel/runtime/refs/resolve.js.map +1 -0
  478. package/dist/src/kernel/runtime/resolveSources.js +62 -0
  479. package/dist/src/kernel/runtime/resolveSources.js.map +1 -0
  480. package/dist/src/kernel/runtime/store.js +75 -0
  481. package/dist/src/kernel/runtime/store.js.map +1 -0
  482. package/dist/src/kernel/runtime/storeReadiness.js +51 -0
  483. package/dist/src/kernel/runtime/storeReadiness.js.map +1 -0
  484. package/dist/src/kernel/runtime/types.js +11 -0
  485. package/dist/src/kernel/runtime/types.js.map +1 -0
  486. package/dist/src/kernel/spec/asVerb.js +21 -0
  487. package/dist/src/kernel/spec/asVerb.js.map +1 -0
  488. package/dist/src/kernel/spec/emitReference.js +578 -0
  489. package/dist/src/kernel/spec/emitReference.js.map +1 -0
  490. package/dist/src/kernel/spec/emitSurface.js +202 -0
  491. package/dist/src/kernel/spec/emitSurface.js.map +1 -0
  492. package/dist/src/kernel/spec/index.js +11 -0
  493. package/dist/src/kernel/spec/index.js.map +1 -0
  494. package/dist/src/kernel/spec/surfaceConformance.js +103 -0
  495. package/dist/src/kernel/spec/surfaceConformance.js.map +1 -0
  496. package/dist/src/kernel/spec/types.js +14 -0
  497. package/dist/src/kernel/spec/types.js.map +1 -0
  498. package/dist/src/kernel/spec/validate.js +110 -0
  499. package/dist/src/kernel/spec/validate.js.map +1 -0
  500. package/dist/src/kernel/vocabulary.js +97 -0
  501. package/dist/src/kernel/vocabulary.js.map +1 -0
  502. package/dist/src/types.js +11 -0
  503. package/dist/src/types.js.map +1 -0
  504. package/package.json +25 -24
  505. package/pragma.conf.ts +853 -0
  506. package/src/bin.ts +276 -82
  507. package/src/capabilities/block.parity.test.ts +253 -0
  508. package/src/capabilities/capabilities/capabilities.render.ts +4 -3
  509. package/src/capabilities/capabilities/capabilities.verb.ts +32 -14
  510. package/src/capabilities/capabilities/catalog.ts +20 -12
  511. package/src/capabilities/capabilities/hints.ts +43 -24
  512. package/src/capabilities/capabilities/index.ts +1 -1
  513. package/src/capabilities/colophon/collectColophon.ts +50 -24
  514. package/src/capabilities/colophon/colophon.render.ts +25 -1
  515. package/src/capabilities/colophon/colophon.test.ts +42 -21
  516. package/src/capabilities/colophon/colophon.verb.ts +9 -5
  517. package/src/capabilities/colophon/types.ts +16 -7
  518. package/src/capabilities/config/collectConfigShow.test.ts +58 -0
  519. package/src/capabilities/config/collectConfigShow.ts +43 -6
  520. package/src/capabilities/config/field.render.ts +4 -5
  521. package/src/capabilities/config/fields.ts +17 -37
  522. package/src/capabilities/config/get.verb.ts +70 -0
  523. package/src/capabilities/config/getUnset.test.ts +264 -0
  524. package/src/capabilities/config/index.ts +5 -1
  525. package/src/capabilities/config/runField.ts +40 -22
  526. package/src/capabilities/config/runGet.ts +34 -0
  527. package/src/capabilities/config/runSet.ts +35 -9
  528. package/src/capabilities/config/set.test.ts +48 -14
  529. package/src/capabilities/config/set.verb.ts +14 -9
  530. package/src/capabilities/config/show.render.test.ts +77 -5
  531. package/src/capabilities/config/show.render.ts +8 -13
  532. package/src/capabilities/config/show.verb.ts +13 -9
  533. package/src/capabilities/config/types.ts +26 -4
  534. package/src/capabilities/config/unset.verb.ts +58 -0
  535. package/src/capabilities/create/byteEquality.subprocess.test.ts +2 -3
  536. package/src/capabilities/create/byteEquality.test.ts +95 -103
  537. package/src/capabilities/create/cliProjection.ts +227 -0
  538. package/src/capabilities/create/constants.ts +50 -0
  539. package/src/capabilities/create/create.mcp.test.ts +91 -7
  540. package/src/capabilities/create/create.render.ts +71 -7
  541. package/src/capabilities/create/create.test.ts +523 -162
  542. package/src/capabilities/create/create.verb.ts +361 -321
  543. package/src/capabilities/create/createGrammar.test.ts +865 -0
  544. package/src/capabilities/create/createHelp.ts +71 -0
  545. package/src/capabilities/create/createSurface.generated.ts +400 -0
  546. package/src/capabilities/create/crossCli.subprocess.test.ts +745 -0
  547. package/src/capabilities/create/cwdJail.test.ts +24 -5
  548. package/src/capabilities/create/generatorToVerbSpec.test.ts +186 -0
  549. package/src/capabilities/create/generatorToVerbSpec.ts +13 -11
  550. package/src/capabilities/create/index.ts +9 -14
  551. package/src/capabilities/create/messages.ts +18 -0
  552. package/src/capabilities/create/mount.ts +391 -0
  553. package/src/capabilities/create/pathJail.test.ts +90 -0
  554. package/src/capabilities/create/pathJail.ts +8 -5
  555. package/src/capabilities/create/pickGenerator.ts +40 -46
  556. package/src/capabilities/create/shippedCreate.subprocess.test.ts +164 -0
  557. package/src/capabilities/create/types.ts +29 -5
  558. package/src/capabilities/{standard/parity.test.ts → distribution.parity.test.ts} +24 -14
  559. package/src/capabilities/distribution.test.ts +122 -0
  560. package/src/capabilities/distribution.ts +54 -0
  561. package/src/capabilities/doctor/checks/checkKeStore.ts +9 -7
  562. package/src/capabilities/doctor/checks/checkPackageRefs.ts +82 -46
  563. package/src/capabilities/doctor/checks/checkPragmaVersion.ts +5 -4
  564. package/src/capabilities/doctor/checks/checkShellCompletions.test.ts +125 -30
  565. package/src/capabilities/doctor/checks/checkShellCompletions.ts +113 -27
  566. package/src/capabilities/doctor/checks/index.ts +27 -0
  567. package/src/capabilities/doctor/checks/mcpCommand.test.ts +100 -0
  568. package/src/capabilities/doctor/checks/mcpCommand.ts +69 -0
  569. package/src/capabilities/doctor/checks/targetHealth.ts +274 -0
  570. package/src/capabilities/doctor/doctor.render.test.ts +24 -13
  571. package/src/capabilities/doctor/doctor.render.ts +45 -20
  572. package/src/capabilities/doctor/doctor.test.ts +158 -40
  573. package/src/capabilities/doctor/doctor.verb.ts +9 -5
  574. package/src/capabilities/doctor/runChecks.ts +65 -66
  575. package/src/capabilities/doctor/types.ts +21 -5
  576. package/src/capabilities/emptyRecovery.test.ts +44 -22
  577. package/src/capabilities/graph/examples.exec.test.ts +107 -0
  578. package/src/capabilities/graph/index.ts +1 -1
  579. package/src/capabilities/graph/inspect.render.ts +70 -22
  580. package/src/capabilities/graph/inspect.test.ts +260 -5
  581. package/src/capabilities/graph/inspect.verb.ts +18 -5
  582. package/src/capabilities/graph/query.render.ts +15 -3
  583. package/src/capabilities/graph/query.verb.ts +5 -4
  584. package/src/capabilities/graph/runQuery.ts +9 -7
  585. package/src/capabilities/index.ts +25 -19
  586. package/src/capabilities/info/collectInfo.ts +15 -10
  587. package/src/capabilities/info/info.render.ts +4 -3
  588. package/src/capabilities/info/info.verb.ts +4 -3
  589. package/src/capabilities/lazy.test.ts +125 -2
  590. package/src/capabilities/meta/complete.verb.ts +1 -1
  591. package/src/capabilities/meta/index.ts +1 -1
  592. package/src/capabilities/meta/mcp.verb.ts +10 -8
  593. package/src/capabilities/ontology/index.ts +15 -11
  594. package/src/capabilities/ontology/ontology.test.ts +6 -55
  595. package/src/capabilities/ontology/queries.ts +2 -2
  596. package/src/capabilities/ontology/render.ts +3 -4
  597. package/src/capabilities/ontology/verbs.ts +42 -83
  598. package/src/capabilities/prompt/index.ts +2 -2
  599. package/src/capabilities/prompt/prompt.render.ts +6 -2
  600. package/src/capabilities/prompt/prompt.test.ts +12 -6
  601. package/src/capabilities/prompt/types.ts +1 -1
  602. package/src/capabilities/prompt/verbs.ts +26 -14
  603. package/src/capabilities/reference.test.ts +63 -0
  604. package/src/capabilities/resources/provider.ts +367 -91
  605. package/src/capabilities/resources/resources.test.ts +411 -59
  606. package/src/capabilities/setup/buildPlan.ts +236 -0
  607. package/src/capabilities/setup/index.ts +7 -7
  608. package/src/capabilities/setup/mode.ts +74 -0
  609. package/src/capabilities/setup/operations/index.ts +74 -0
  610. package/src/capabilities/setup/operations/setupCompletions.ts +97 -24
  611. package/src/capabilities/setup/operations/setupConfig.ts +124 -0
  612. package/src/capabilities/setup/operations/setupGenerator.ts +397 -320
  613. package/src/capabilities/setup/operations/setupLsp.ts +329 -68
  614. package/src/capabilities/setup/operations/setupMcp.ts +137 -97
  615. package/src/capabilities/setup/operations/setupSkills.ts +336 -108
  616. package/src/capabilities/setup/plan.render.ts +241 -0
  617. package/src/capabilities/setup/plan.ts +236 -0
  618. package/src/capabilities/setup/setup.mcp.correctness.test.ts +432 -0
  619. package/src/capabilities/setup/setup.render.test.ts +281 -73
  620. package/src/capabilities/setup/setup.render.ts +45 -77
  621. package/src/capabilities/setup/setup.test.ts +972 -209
  622. package/src/capabilities/setup/setup.verb.ts +233 -74
  623. package/src/capabilities/setup/shell.test.ts +86 -0
  624. package/src/capabilities/setup/shell.ts +166 -14
  625. package/src/capabilities/setup/targets.ts +367 -0
  626. package/src/capabilities/setup/types.ts +18 -57
  627. package/src/capabilities/shared/assertExecOk.ts +68 -10
  628. package/src/capabilities/shared/index.ts +32 -0
  629. package/src/capabilities/shared/packageManager.test.ts +55 -0
  630. package/src/capabilities/shared/packageManager.ts +62 -6
  631. package/src/capabilities/skill/discover.ts +47 -9
  632. package/src/capabilities/skill/index.ts +1 -1
  633. package/src/capabilities/skill/render.ts +14 -14
  634. package/src/capabilities/skill/skill.test.ts +7 -5
  635. package/src/capabilities/skill/verbs.ts +9 -10
  636. package/src/capabilities/sources/collectStatus.ts +61 -51
  637. package/src/capabilities/sources/index.ts +2 -2
  638. package/src/capabilities/sources/installSkills.ts +86 -9
  639. package/src/capabilities/sources/runUpdate.ts +164 -141
  640. package/src/capabilities/sources/sources.test.ts +265 -119
  641. package/src/capabilities/sources/status.render.test.ts +53 -24
  642. package/src/capabilities/sources/status.render.ts +25 -30
  643. package/src/capabilities/sources/status.verb.ts +16 -9
  644. package/src/capabilities/sources/types.ts +18 -25
  645. package/src/capabilities/sources/update.render.ts +10 -3
  646. package/src/capabilities/sources/update.verb.ts +13 -24
  647. package/src/capabilities/surface.test.ts +165 -25
  648. package/src/capabilities/tier.parity.test.ts +144 -0
  649. package/src/capabilities/upgrade/runUpgrade.ts +8 -8
  650. package/src/capabilities/upgrade/upgrade.render.ts +4 -5
  651. package/src/capabilities/upgrade/upgrade.test.ts +3 -3
  652. package/src/capabilities/upgrade/upgrade.verb.ts +8 -4
  653. package/src/capabilities/version/index.ts +12 -0
  654. package/src/capabilities/version/version.test.ts +66 -0
  655. package/src/capabilities/version/version.verb.ts +39 -0
  656. package/src/constants.test.ts +8 -6
  657. package/src/constants.ts +78 -22
  658. package/src/identity.test.ts +348 -0
  659. package/src/index.ts +2 -2
  660. package/src/kernel/completion/__snapshots__/emitScripts.test.ts.snap +20 -15
  661. package/src/kernel/completion/complete.test.ts +12 -2
  662. package/src/kernel/completion/complete.ts +1 -1
  663. package/src/kernel/completion/emitScripts.test.ts +1 -1
  664. package/src/kernel/completion/emitScripts.ts +5 -3
  665. package/src/kernel/completion/entitySource.test.ts +185 -41
  666. package/src/kernel/completion/entitySource.ts +133 -110
  667. package/src/kernel/completion/model.test.ts +165 -13
  668. package/src/kernel/completion/model.ts +105 -14
  669. package/src/kernel/completion/parse.test.ts +4 -7
  670. package/src/kernel/completion/parse.ts +15 -0
  671. package/src/kernel/completion/resolve.test.ts +0 -1
  672. package/src/kernel/completion/safety.test.ts +104 -50
  673. package/src/kernel/completion/shellDrive.test.ts +611 -0
  674. package/src/kernel/completion/templates/bash.ts +7 -2
  675. package/src/kernel/completion/templates/fish.ts +28 -6
  676. package/src/kernel/completion/templates/index.ts +23 -0
  677. package/src/kernel/completion/types.ts +10 -3
  678. package/src/kernel/config/defaults.test.ts +108 -0
  679. package/src/kernel/config/defaults.ts +13 -23
  680. package/src/kernel/config/evaluateProjectConfig.ts +33 -11
  681. package/src/kernel/config/findProjectConfig.ts +4 -3
  682. package/src/kernel/config/firstRun.test.ts +44 -38
  683. package/src/kernel/config/firstRun.ts +24 -81
  684. package/src/kernel/config/globalConfig.ts +2 -2
  685. package/src/kernel/config/index.ts +5 -6
  686. package/src/kernel/config/paths.ts +17 -17
  687. package/src/kernel/config/readConfig.test.ts +246 -7
  688. package/src/kernel/config/readConfig.ts +8 -8
  689. package/src/kernel/config/schema.test.ts +50 -0
  690. package/src/kernel/config/schema.ts +100 -11
  691. package/src/kernel/config/types.ts +75 -19
  692. package/src/kernel/copy.test.ts +483 -0
  693. package/src/kernel/copy.ts +54 -0
  694. package/src/kernel/error/PragmaError.test.ts +6 -3
  695. package/src/kernel/error/PragmaError.ts +4 -2
  696. package/src/kernel/error/constants.ts +7 -4
  697. package/src/kernel/error/fromTaskError.ts +28 -6
  698. package/src/kernel/error/index.ts +1 -1
  699. package/src/kernel/error/recovery.test.ts +22 -45
  700. package/src/kernel/error/recovery.ts +36 -27
  701. package/src/kernel/error/renderError.ts +42 -1
  702. package/src/kernel/error/types.ts +25 -4
  703. package/src/kernel/index.ts +26 -0
  704. package/src/kernel/packs/collect.test.ts +195 -11
  705. package/src/kernel/packs/collect.ts +212 -61
  706. package/src/kernel/packs/compile.test.ts +293 -8
  707. package/src/kernel/packs/compile.ts +108 -15
  708. package/src/kernel/packs/disclosure.test.ts +5 -2
  709. package/src/kernel/packs/disclosure.ts +2 -2
  710. package/src/kernel/packs/graphql/buildLookupDocument.ts +1 -1
  711. package/src/kernel/packs/graphql/fetchGraphqlLookup.ts +13 -13
  712. package/src/kernel/packs/graphql/index.ts +20 -0
  713. package/src/kernel/packs/graphqlSource.test.ts +6 -3
  714. package/src/kernel/packs/index.ts +40 -0
  715. package/src/kernel/packs/iri.test.ts +73 -0
  716. package/src/kernel/packs/iri.ts +70 -20
  717. package/src/kernel/packs/renderPack.ts +28 -7
  718. package/src/kernel/packs/resolveEntity.test.ts +213 -0
  719. package/src/kernel/packs/resolveEntity.ts +132 -34
  720. package/src/kernel/packs/runBodies.ts +16 -16
  721. package/src/kernel/packs/sample.ts +1 -1
  722. package/src/kernel/packs/schema.ts +114 -11
  723. package/src/kernel/packs/sparql/applyFilters.ts +16 -17
  724. package/src/kernel/packs/sparql/buildLookupQuery.ts +75 -3
  725. package/src/kernel/packs/sparql/index.ts +37 -0
  726. package/src/kernel/packs/sparql/runSelect.test.ts +104 -10
  727. package/src/kernel/packs/sparql/runSelect.ts +75 -37
  728. package/src/kernel/packs/toolDescription.test.ts +52 -5
  729. package/src/kernel/packs/types.ts +52 -4
  730. package/src/kernel/packs/uniqueness.ts +5 -5
  731. package/src/kernel/project/cli/buildProgram.test.ts +157 -17
  732. package/src/kernel/project/cli/buildProgram.ts +77 -18
  733. package/src/kernel/project/cli/constants.ts +34 -0
  734. package/src/kernel/project/cli/dispatch.test.ts +227 -3
  735. package/src/kernel/project/cli/dispatch.ts +250 -48
  736. package/src/kernel/project/cli/exitCodes.ts +1 -1
  737. package/src/kernel/project/cli/globalFlags.test.ts +117 -1
  738. package/src/kernel/project/cli/globalFlags.ts +130 -30
  739. package/src/kernel/project/cli/helpFormat.ts +14 -1
  740. package/src/kernel/project/cli/rootHelp.ts +140 -111
  741. package/src/kernel/project/cli/suggest.test.ts +33 -1
  742. package/src/kernel/project/cli/suggest.ts +25 -1
  743. package/src/kernel/project/cli/verbHelp.test.ts +30 -0
  744. package/src/kernel/project/cli/verbHelp.ts +23 -7
  745. package/src/kernel/project/mcp/buildServer.ts +18 -10
  746. package/src/kernel/project/mcp/envelope.ts +2 -2
  747. package/src/kernel/project/mcp/instructions.ts +12 -7
  748. package/src/kernel/project/mcp/mcpError.ts +1 -1
  749. package/src/kernel/project/mcp/parity.test.ts +42 -1
  750. package/src/kernel/project/mcp/prompts/index.ts +37 -0
  751. package/src/kernel/project/mcp/prompts/prompts.test.ts +120 -5
  752. package/src/kernel/project/mcp/prompts/provider.ts +22 -8
  753. package/src/kernel/project/mcp/prompts/source.ts +69 -68
  754. package/src/kernel/project/mcp/registerVerb.ts +56 -11
  755. package/src/kernel/project/mcp/serve.ts +13 -5
  756. package/src/kernel/project/mcp/toolDescriptions.test.ts +6 -2
  757. package/src/kernel/render/__snapshots__/renderers.test.ts.snap +7 -4
  758. package/src/kernel/render/contracts.ts +21 -0
  759. package/src/kernel/render/disclosure.ts +4 -2
  760. package/src/kernel/render/envelope.ts +2 -3
  761. package/src/kernel/render/formatters.ts +1 -1
  762. package/src/kernel/render/prefixes.test.ts +36 -0
  763. package/src/kernel/render/prefixes.ts +40 -13
  764. package/src/kernel/render/renderers.test.ts +244 -7
  765. package/src/kernel/render/renderers.ts +222 -20
  766. package/src/kernel/render/style.test.ts +75 -24
  767. package/src/kernel/render/style.ts +31 -1
  768. package/src/kernel/render/turtle.ts +222 -0
  769. package/src/kernel/runtime/graphpack/build.ts +29 -3
  770. package/src/kernel/runtime/graphpack/buildIndex.test.ts +46 -0
  771. package/src/kernel/runtime/graphpack/buildIndex.ts +53 -18
  772. package/src/kernel/runtime/graphpack/embedded/pack.generated.ts +5 -5
  773. package/src/kernel/runtime/graphpack/embedded/pack.index.generated.ts +3 -3
  774. package/src/kernel/runtime/graphpack/embedded/pack.stories.generated.ts +3 -0
  775. package/src/kernel/runtime/graphpack/embedded.ts +39 -13
  776. package/src/kernel/runtime/graphpack/graphpack.test.ts +205 -5
  777. package/src/kernel/runtime/graphpack/hash.ts +3 -2
  778. package/src/kernel/runtime/graphpack/index.ts +1 -1
  779. package/src/kernel/runtime/graphpack/manifest.ts +114 -12
  780. package/src/kernel/runtime/graphpack/read.ts +5 -11
  781. package/src/kernel/runtime/graphpack/schemas.ts +74 -0
  782. package/src/kernel/runtime/graphpack/stories.ts +84 -0
  783. package/src/kernel/runtime/graphpack/types.ts +61 -48
  784. package/src/kernel/runtime/loadSession.ts +1 -1
  785. package/src/kernel/runtime/paths.ts +64 -15
  786. package/src/kernel/runtime/probe.test.ts +8 -4
  787. package/src/kernel/runtime/probe.ts +6 -6
  788. package/src/kernel/runtime/readEntity.ts +477 -32
  789. package/src/kernel/runtime/refs/gitOps.ts +1 -19
  790. package/src/kernel/runtime/refs/index.ts +39 -0
  791. package/src/kernel/runtime/refs/parseRef.ts +8 -8
  792. package/src/kernel/runtime/refs/resolve.ts +82 -66
  793. package/src/kernel/runtime/resolveSources.test.ts +63 -24
  794. package/src/kernel/runtime/resolveSources.ts +36 -25
  795. package/src/kernel/runtime/storeReadiness.ts +10 -10
  796. package/src/kernel/runtime/storeless.test.ts +1 -1
  797. package/src/kernel/runtime/types.ts +15 -1
  798. package/src/kernel/runtime/wasmEmbed.test.ts +56 -55
  799. package/src/kernel/spec/emitReference.test.ts +3 -3
  800. package/src/kernel/spec/emitReference.ts +242 -34
  801. package/src/kernel/spec/emitSurface.ts +57 -11
  802. package/src/kernel/spec/surfaceConformance.test.ts +4 -2
  803. package/src/kernel/spec/surfaceConformance.ts +8 -0
  804. package/src/kernel/spec/types.ts +277 -13
  805. package/src/kernel/spec/validate.ts +2 -1
  806. package/src/kernel/vocabulary.test.ts +164 -0
  807. package/src/kernel/vocabulary.ts +146 -0
  808. package/src/testing/PARITY_GAPS.ts +8 -2
  809. package/src/testing/behavioral/README.md +3 -3
  810. package/src/testing/behavioral/completion.test.ts +19 -6
  811. package/src/testing/behavioral/docExamples.test.ts +14 -0
  812. package/src/testing/behavioral/errorMatrix.mcp.test.ts +6 -5
  813. package/src/testing/behavioral/errorMatrix.storeless.test.ts +1 -1
  814. package/src/testing/behavioral/exitCodes.e2e.test.ts +6 -5
  815. package/src/testing/behavioral/firstRun.e2e.test.ts +24 -24
  816. package/src/testing/behavioral/harness.foundation.test.ts +14 -5
  817. package/src/testing/behavioral/journeys.cli.test.ts +117 -76
  818. package/src/testing/behavioral/journeys.defaultPack.test.ts +88 -182
  819. package/src/testing/behavioral/journeys.firstInstall.test.ts +167 -0
  820. package/src/testing/behavioral/journeys.implementation.test.ts +206 -0
  821. package/src/testing/behavioral/journeys.interactiveTty.e2e.test.ts +2 -2
  822. package/src/testing/behavioral/journeys.mcpLifecycle.mcp.test.ts +9 -6
  823. package/src/testing/behavioral/journeys.packageStories.test.ts +188 -0
  824. package/src/testing/behavioral/liveReadSurface.ts +4 -3
  825. package/src/testing/behavioral/mcpServe.e2e.test.ts +57 -2
  826. package/src/testing/behavioral/mcpSurface.test.ts +10 -5
  827. package/src/testing/behavioral/rootCli.e2e.test.ts +26 -2
  828. package/src/testing/behavioral/staleCommands.test.ts +10 -0
  829. package/src/testing/eval/__snapshots__/eval.test.ts.snap +7 -7
  830. package/src/testing/eval/cases/assembly.ts +13 -6
  831. package/src/testing/eval/cases/effectful.ts +28 -15
  832. package/src/testing/eval/cases/readNouns.ts +22 -20
  833. package/src/testing/eval/cases/stable.ts +5 -1
  834. package/src/testing/eval/eval.test.ts +7 -1
  835. package/src/testing/fixtures/blockGraph.ts +79 -0
  836. package/src/testing/fixtures/fixtureCapability.ts +45 -1
  837. package/src/testing/fixtures/graph/canonical.ts +94 -5
  838. package/src/testing/fixtures/graph/defaultPack.ts +7 -6
  839. package/src/testing/fixtures/graph/owlExport.ts +7 -5
  840. package/src/testing/helpers/blankCanonicalRanges.ts +36 -0
  841. package/src/testing/helpers/fixtureGraph.ts +33 -16
  842. package/src/testing/helpers/packRuntime.ts +2 -3
  843. package/src/testing/helpers/projectCli.ts +2 -1
  844. package/src/testing/helpers/projectMcp.ts +38 -6
  845. package/src/testing/helpers/runCli.ts +35 -18
  846. package/src/testing/perf/budgets.test.ts +24 -9
  847. package/src/testing/perf/budgets.ts +76 -12
  848. package/src/testing/perf/codegen.test.ts +126 -0
  849. package/src/testing/perf/globalSetup.test.ts +286 -0
  850. package/src/testing/perf/globalSetup.ts +611 -14
  851. package/src/testing/perf/measure.test.ts +38 -0
  852. package/src/testing/perf/measure.ts +23 -4
  853. package/src/testing/setupXdgIsolation.ts +81 -21
  854. package/src/testing/tempRoot.globalSetup.ts +122 -0
  855. package/src/types.ts +2 -2
  856. package/dist/pragma +0 -0
  857. package/src/capabilities/block/blockList.test.ts +0 -79
  858. package/src/capabilities/block/blockList.verb.ts +0 -163
  859. package/src/capabilities/block/index.ts +0 -25
  860. package/src/capabilities/block/pack.ts +0 -166
  861. package/src/capabilities/block/parity.test.ts +0 -187
  862. package/src/capabilities/block/tierChain.ts +0 -78
  863. package/src/capabilities/colophon/pragmaColophon.ts +0 -66
  864. package/src/capabilities/create/compiledCreate.subprocess.test.ts +0 -152
  865. package/src/capabilities/create/templates.embedded.generated.ts +0 -53
  866. package/src/capabilities/doctor/checks/checkConfigFile.ts +0 -41
  867. package/src/capabilities/doctor/checks/checkMcpCommands.ts +0 -114
  868. package/src/capabilities/doctor/checks/checkMcpConfigured.ts +0 -67
  869. package/src/capabilities/doctor/checks/checkSkillsSymlinked.ts +0 -60
  870. package/src/capabilities/doctor/checks/deriveBand.test.ts +0 -42
  871. package/src/capabilities/doctor/checks/deriveBand.ts +0 -28
  872. package/src/capabilities/modifier/index.ts +0 -15
  873. package/src/capabilities/modifier/pack.ts +0 -64
  874. package/src/capabilities/standard/index.ts +0 -18
  875. package/src/capabilities/standard/pack.ts +0 -128
  876. package/src/capabilities/tier/index.ts +0 -19
  877. package/src/capabilities/tier/lookup.render.test.ts +0 -72
  878. package/src/capabilities/tier/lookup.render.ts +0 -59
  879. package/src/capabilities/tier/lookup.test.ts +0 -83
  880. package/src/capabilities/tier/lookup.verb.ts +0 -44
  881. package/src/capabilities/tier/pack.ts +0 -28
  882. package/src/capabilities/tier/runLookup.ts +0 -87
  883. package/src/capabilities/token/addConfig.render.ts +0 -27
  884. package/src/capabilities/token/addConfig.test.ts +0 -62
  885. package/src/capabilities/token/addConfig.verb.ts +0 -40
  886. package/src/capabilities/token/index.ts +0 -19
  887. package/src/capabilities/token/pack.ts +0 -58
  888. package/src/capabilities/token/runAddConfig.ts +0 -95
  889. package/src/kernel/completion/bashDrive.test.ts +0 -73
  890. package/src/kernel/config/__snapshots__/firstRun.test.ts.snap +0 -11
  891. package/src/kernel/runtime/graphpack/embedded/sample.ttl +0 -39
  892. package/src/kernel/runtime/lock.ts +0 -90
@@ -1,125 +1,323 @@
1
1
  /**
2
- * `setup skills` — symlink discovered skills into each harness skill directory
3
- * and the cross-client `.agents/skills`.
4
- *
5
- * Split into `detectSkills` (skill discovery, harness detection, and the
6
- * per-link create/skip/replace DECISION all run against REAL fs up front, so the
7
- * wizard recap and a `--dry-run` plan reflect true state) and `composeSkills` (a
8
- * pure, re-runnable body performing only the symlink/delete effects the dry-run
9
- * interpreter mocks). Idempotent by construction.
2
+ * `setup skills` — symlink discovered skills into harness skill directories.
3
+ *
4
+ * BAND-MATCHED: the band picks the source root AND the link destination, and
5
+ * the two always match.
6
+ *
7
+ * - global (the default): INSTALLED skills (`$XDG_DATA_HOME/<bin>/skills`, where
8
+ * `sources update` puts package skills) link into user-level harness skill
9
+ * directories — the cross-client `~/.agents/skills`, plus the user-level
10
+ * directory of each detected harness whose user-level location is verified.
11
+ * - project (`--local`): PROJECT skills (`<cwd>/.<bin>/skills`) link into the
12
+ * project's harness directories — the checked-in, team-shared arrangement.
13
+ *
14
+ * Cross-band linking is what this replaces: linking installed skills into a
15
+ * repository's directories leaks machine state into a checkout, and linking a
16
+ * repository's skills into the home directory applies one project's skills
17
+ * machine-wide. Neither is ever what the user asked for.
18
+ *
19
+ * Split into `detectSkills` (discovery, harness detection, and the per-link
20
+ * create/skip/replace DECISION, all against the real filesystem up front, so
21
+ * the plan and the recap reflect true state) and pure compose bodies performing
22
+ * only the symlink/delete effects the dry-run interpreter mocks.
10
23
  */
11
24
 
12
- import { existsSync, readlinkSync } from "node:fs";
13
- import { resolve } from "node:path";
25
+ import { lstatSync, readdirSync, readlinkSync } from "node:fs";
26
+ import { dirname, isAbsolute, relative, resolve, sep } from "node:path";
14
27
  import {
15
28
  deleteFile,
16
- info,
17
29
  mkdir,
18
30
  sequence_,
19
31
  symlink,
20
32
  type Task,
21
33
  } from "@canonical/task";
22
- import { RECOVERY_CLI_PREFIX } from "../../../constants.js";
23
- import { PragmaError } from "../../../kernel/error/PragmaError.js";
24
- import { cliRecovery } from "../../../kernel/error/recovery.js";
25
- import type { PragmaRuntime } from "../../../kernel/runtime/types.js";
26
- import type { SetupSkillsResult, SymlinkAction } from "../types.js";
34
+ import type { PragmaRuntime } from "../../../kernel/runtime/index.js";
35
+ import type { ScopeBand } from "../types.js";
27
36
 
28
37
  /** Cross-client skill directory, shared across all harnesses. */
29
38
  const CROSS_CLIENT_DIR = ".agents/skills";
30
39
 
31
40
  /**
32
- * The detected skill-linking plan: the target directories, the decided per-link
33
- * actions, and the counts/warnings the result surface reports. `available` is
34
- * false when no skills were discovered.
41
+ * The harnesses whose USER-LEVEL skills directory is verified against the
42
+ * harness's own documentation, and therefore safe to link into on the global
43
+ * band. A harness absent from this set simply contributes no global link
44
+ * directory: an invented `~/.<something>/skills` would be a directory nothing
45
+ * reads, and creating it would be litter dressed up as configuration.
46
+ *
47
+ * The path itself is still the registry's — `skillsPath` is a function of a
48
+ * root, so a user-level location is `skillsPath(home)`. What lives here is only
49
+ * the JUDGEMENT that the location has been confirmed.
50
+ */
51
+ const VERIFIED_GLOBAL_SKILL_HARNESSES: ReadonlySet<string> = new Set([
52
+ "claude-code",
53
+ ]);
54
+
55
+ /** One symlink create/skip/replace action decided during detection. */
56
+ export interface SymlinkAction {
57
+ readonly skillName: string;
58
+ readonly target: string;
59
+ readonly linkPath: string;
60
+ readonly action: "created" | "skipped" | "replaced";
61
+ readonly harnessName: string;
62
+ /**
63
+ * Whether this link path currently holds a symlink INTO the band's skill
64
+ * root — the ownership test removal turns on. A link pointing anywhere else
65
+ * is the user's and is never this command's to delete, and a real (non-link)
66
+ * entry is never touched at all.
67
+ */
68
+ readonly owned: boolean;
69
+ /**
70
+ * Whether a REAL (non-symlink) entry occupies the link path. Such a path is
71
+ * `skipped` for the same reason an already-correct link is — neither is
72
+ * anything to do — but they are not the same state: one is a link this
73
+ * command maintains, the other is a hand-placed directory it will never
74
+ * touch, and reporting both as "current" told the user a link exists where
75
+ * none does.
76
+ */
77
+ readonly blocked: boolean;
78
+ }
79
+
80
+ /**
81
+ * The detected skill-linking plan for ONE band: the source root, the target
82
+ * directories, the decided per-link actions, and the counts the plan row
83
+ * reports. `available` is false when the band's root holds no skills.
35
84
  */
36
85
  export interface SkillsDetection {
86
+ readonly band: ScopeBand;
87
+ /** The band's source root — the directory skills are discovered from. */
88
+ readonly sourceRoot: string;
37
89
  readonly available: boolean;
38
90
  readonly targets: readonly { readonly dir: string; readonly name: string }[];
39
91
  readonly actions: readonly SymlinkAction[];
92
+ /**
93
+ * Links this band OWNS that no CURRENT skill accounts for: the source root
94
+ * emptied, or one skill removed upstream. They are not part of the forward
95
+ * plan — there is nothing left to link them to — but they are exactly what
96
+ * removal exists to clear, and deriving removal from the per-skill actions
97
+ * alone left them on disk while `--undo` reported zero work.
98
+ */
99
+ readonly orphans: readonly SymlinkAction[];
40
100
  readonly skillCount: number;
41
101
  readonly harnessCount: number;
42
102
  readonly warnings: readonly string[];
43
103
  }
44
104
 
45
- /** The current target of a symlink, or `null` when absent / not a symlink. */
46
- function currentLink(linkPath: string): string | null {
47
- if (!existsSync(linkPath)) return null;
105
+ /** What currently occupies a candidate link path. */
106
+ type LinkState =
107
+ | { readonly kind: "absent" }
108
+ | { readonly kind: "symlink"; readonly target: string }
109
+ | { readonly kind: "other" };
110
+
111
+ /**
112
+ * Whether a link's destination lives INSIDE the band's skill root — the
113
+ * ownership test, and the one that decides what `--undo` deletes.
114
+ *
115
+ * A raw `readlink` target may be relative, so it is resolved against the link's
116
+ * own directory first; then containment is tested by PATH SEGMENT. A string
117
+ * prefix answered yes for `<root>-backup/foo`, so a user's own link into a
118
+ * sibling directory was classified as ours and removed by `--undo` — a file we
119
+ * never created and had no business deleting.
120
+ *
121
+ * The root itself is not "inside" it: a link pointing AT the root is not one of
122
+ * the per-skill links this command writes.
123
+ *
124
+ * @param root - The band's skill source root, absolute.
125
+ * @param linkPath - The absolute path of the link being classified.
126
+ * @param rawTarget - The link's destination exactly as `readlink` reported it.
127
+ * @returns Whether the destination is a path under the root.
128
+ * @note Pure — it resolves and compares strings, and reads nothing.
129
+ */
130
+ function withinRoot(
131
+ root: string,
132
+ linkPath: string,
133
+ rawTarget: string,
134
+ ): boolean {
135
+ const destination = resolve(dirname(linkPath), rawTarget);
136
+ const rel = relative(root, destination);
137
+ return (
138
+ rel.length > 0 &&
139
+ rel !== ".." &&
140
+ !rel.startsWith(`..${sep}`) &&
141
+ !isAbsolute(rel)
142
+ );
143
+ }
144
+
145
+ /**
146
+ * Classify a link path WITHOUT following it: absent, a symlink (with its raw
147
+ * target, resolving or not), or a real (non-symlink) entry. `lstat`-based, the
148
+ * same classification `sources/installSkills.ts`'s `linkState` uses — probing
149
+ * with `existsSync` FOLLOWS the link, so a DANGLING symlink read as "absent",
150
+ * the plan said `created`, and the real `symlink()` crashed EEXIST while the
151
+ * dry-run previewed a clean create.
152
+ */
153
+ function linkState(linkPath: string): LinkState {
154
+ let stat: ReturnType<typeof lstatSync>;
48
155
  try {
49
- return readlinkSync(linkPath);
156
+ stat = lstatSync(linkPath);
50
157
  } catch {
51
- return "";
158
+ return { kind: "absent" };
159
+ }
160
+ if (stat.isSymbolicLink()) {
161
+ try {
162
+ return { kind: "symlink", target: readlinkSync(linkPath) };
163
+ } catch {
164
+ return { kind: "other" };
165
+ }
52
166
  }
167
+ return { kind: "other" };
53
168
  }
54
169
 
55
170
  /**
56
- * Discover skills, detect harnesses, and decide each link action (real fs, up
57
- * front). Returns `available: false` (empty plan) when no skills exist — the
58
- * run-all omits the step; the direct sub-verb turns it into {@link skillsEmptyError}.
171
+ * The link directories for a band. Project: every detected harness's
172
+ * project-rooted skills directory plus the cross-client one, exactly as
173
+ * before. Global: the same construction rooted at the user's home directory,
174
+ * but only for the harnesses in {@link VERIFIED_GLOBAL_SKILL_HARNESSES} —
175
+ * plus the cross-client directory, which every client reads by convention.
176
+ *
177
+ * @param detected - The detected harnesses.
178
+ * @param band - The band being set up.
179
+ * @param root - The band's link root (`cwd` for project, home for global).
180
+ * @returns The deduplicated target directories, first-seen wins.
181
+ */
182
+ function linkTargets(
183
+ detected: readonly {
184
+ harness: { id: string; name: string; skillsPath: (root: string) => string };
185
+ }[],
186
+ band: ScopeBand,
187
+ root: string,
188
+ ): { dir: string; name: string }[] {
189
+ const seen = new Set<string>();
190
+ const targets: { dir: string; name: string }[] = [];
191
+ for (const d of detected) {
192
+ if (
193
+ band === "global" &&
194
+ !VERIFIED_GLOBAL_SKILL_HARNESSES.has(d.harness.id)
195
+ ) {
196
+ continue;
197
+ }
198
+ const dir = d.harness.skillsPath(root);
199
+ if (seen.has(dir)) continue;
200
+ seen.add(dir);
201
+ targets.push({ dir, name: d.harness.name });
202
+ }
203
+ const crossDir = resolve(root, CROSS_CLIENT_DIR);
204
+ if (!seen.has(crossDir))
205
+ targets.push({ dir: crossDir, name: CROSS_CLIENT_DIR });
206
+ return targets;
207
+ }
208
+
209
+ /**
210
+ * Every owned link sitting in the target directories that the per-skill pass
211
+ * did not already visit.
212
+ *
213
+ * The forward pass enumerates CURRENT skills, so it can only ever see links a
214
+ * skill still exists for. Once the source root is emptied — or one skill is
215
+ * removed upstream — the link it left behind is invisible to that pass, and
216
+ * removal derived from it found nothing to do. Ownership is the same
217
+ * containment test the forward pass applies, so a user's own link is no more
218
+ * removable here than it is there.
219
+ *
220
+ * @param targets - The band's link directories.
221
+ * @param sourceRoot - The band's skill source root.
222
+ * @param covered - Link paths the per-skill pass already decided.
223
+ * @returns The owned links no current skill accounts for.
224
+ * @note Impure — reads each target directory and lstats its entries.
225
+ */
226
+ function orphanedLinks(
227
+ targets: readonly { dir: string; name: string }[],
228
+ sourceRoot: string,
229
+ covered: ReadonlySet<string>,
230
+ ): SymlinkAction[] {
231
+ const orphans: SymlinkAction[] = [];
232
+ for (const { dir, name } of targets) {
233
+ let entries: string[];
234
+ try {
235
+ entries = readdirSync(dir);
236
+ } catch {
237
+ continue; // The directory does not exist — it holds no links.
238
+ }
239
+ for (const entry of entries) {
240
+ const linkPath = resolve(dir, entry);
241
+ if (covered.has(linkPath)) continue;
242
+ const state = linkState(linkPath);
243
+ if (state.kind !== "symlink") continue;
244
+ if (!withinRoot(sourceRoot, linkPath, state.target)) continue;
245
+ orphans.push({
246
+ skillName: entry,
247
+ target: resolve(dirname(linkPath), state.target),
248
+ linkPath,
249
+ action: "skipped",
250
+ harnessName: name,
251
+ blocked: false,
252
+ owned: true,
253
+ });
254
+ }
255
+ }
256
+ return orphans;
257
+ }
258
+
259
+ /**
260
+ * Discover the band's skills, detect harnesses, and decide each link action
261
+ * (real filesystem, up front).
262
+ *
263
+ * Target discovery runs even when the band holds NO skills: the directories are
264
+ * where this command's own links live, and a removal has to be able to find
265
+ * them after the source root has been emptied.
59
266
  *
60
267
  * @param rt - The per-invocation runtime.
61
- * @returns The link plan.
268
+ * @param band - Which band to plan: global (installed skills) or project.
269
+ * @returns The band's link plan.
62
270
  * @note Impure — reads the filesystem (skills + harnesses + existing links).
63
271
  */
64
272
  export async function detectSkills(
65
273
  rt: PragmaRuntime,
274
+ band: ScopeBand,
66
275
  ): Promise<SkillsDetection> {
67
276
  const cwd = rt.cwd;
68
- const [{ discoverSkills }, { detectHarnesses }, { runTask }] =
69
- await Promise.all([
70
- import("../../skill/discover.js"),
71
- import("@canonical/harnesses"),
72
- import("@canonical/task/node"),
73
- ]);
74
-
75
- const skills = discoverSkills(cwd);
76
- if (skills.length === 0) {
77
- return {
78
- available: false,
79
- targets: [],
80
- actions: [],
81
- skillCount: 0,
82
- harnessCount: 0,
83
- warnings: [],
84
- };
85
- }
277
+ const [
278
+ { discoverSkillsFrom, installedSkillsDir, projectSkillsDir },
279
+ { detectHarnesses, readPlatformEnv, userHome },
280
+ { runTask },
281
+ ] = await Promise.all([
282
+ import("../../skill/discover.js"),
283
+ import("@canonical/harnesses"),
284
+ import("@canonical/task/node"),
285
+ ]);
86
286
 
287
+ const sourceRoot =
288
+ band === "project" ? projectSkillsDir(cwd) : installedSkillsDir();
289
+ const linkRoot = band === "project" ? cwd : userHome(readPlatformEnv());
290
+ const skills = discoverSkillsFrom([sourceRoot]);
87
291
  const detected = await runTask(detectHarnesses(cwd));
292
+ const targets = linkTargets(detected, band, linkRoot);
88
293
 
89
- // Target dirs (harness skill dirs + the cross-client dir), first-seen wins.
90
- const seen = new Set<string>();
91
- const targets: { dir: string; name: string }[] = [];
92
- for (const d of detected) {
93
- const dir = d.harness.skillsPath(cwd);
94
- if (!seen.has(dir)) {
95
- seen.add(dir);
96
- targets.push({ dir, name: d.harness.name });
97
- }
98
- }
99
- const crossDir = resolve(cwd, CROSS_CLIENT_DIR);
100
- if (!seen.has(crossDir)) {
101
- seen.add(crossDir);
102
- targets.push({ dir: crossDir, name: CROSS_CLIENT_DIR });
103
- }
104
-
105
- // Decide each action against REAL fs (so the preview is accurate).
294
+ // Decide each action against REAL fs (so the preview is accurate). Dangling
295
+ // or wrong-target symlinks are `replaced` (delete + relink); a real
296
+ // (non-symlink) file or directory at the path is `skipped` — a hand-placed
297
+ // skill is never this command's to delete.
106
298
  const actions: SymlinkAction[] = [];
107
299
  for (const { dir, name } of targets) {
108
300
  for (const skill of skills) {
109
301
  const linkPath = resolve(dir, skill.folderName);
110
- const current = currentLink(linkPath);
302
+ const state = linkState(linkPath);
111
303
  const action: SymlinkAction["action"] =
112
- current === null
304
+ state.kind === "absent"
113
305
  ? "created"
114
- : current === skill.sourcePath
306
+ : state.kind === "symlink" && state.target === skill.sourcePath
115
307
  ? "skipped"
116
- : "replaced";
308
+ : state.kind === "symlink"
309
+ ? "replaced"
310
+ : "skipped";
117
311
  actions.push({
118
312
  skillName: skill.name,
119
313
  target: skill.sourcePath,
120
314
  linkPath,
121
315
  action,
122
316
  harnessName: name,
317
+ blocked: state.kind === "other",
318
+ owned:
319
+ state.kind === "symlink" &&
320
+ withinRoot(sourceRoot, linkPath, state.target),
123
321
  });
124
322
  }
125
323
  }
@@ -127,15 +325,22 @@ export async function detectSkills(
127
325
  const warnings = actions
128
326
  .filter((a) => a.action === "replaced")
129
327
  .map(
130
- (a) => `Replaced stale symlink for ${a.skillName} in ${a.harnessName}`,
328
+ (a) => `Replaced a stale symlink for ${a.skillName} in ${a.harnessName}`,
131
329
  );
132
330
 
133
331
  return {
134
- available: true,
332
+ band,
333
+ sourceRoot,
334
+ available: skills.length > 0,
135
335
  targets,
136
336
  actions,
337
+ orphans: orphanedLinks(
338
+ targets,
339
+ sourceRoot,
340
+ new Set(actions.map((a) => a.linkPath)),
341
+ ),
137
342
  skillCount: skills.length,
138
- harnessCount: detected.length,
343
+ harnessCount: targets.length,
139
344
  warnings,
140
345
  };
141
346
  }
@@ -146,60 +351,83 @@ export async function detectSkills(
146
351
  *
147
352
  * Built from re-runnable combinators (NOT a single-use `gen`) because `execute`
148
353
  * interprets the task twice (preview + perform). `created` links carry an undo;
149
- * a `replaced` link is delete-then-relink (idempotent); `skipped` is a no-op.
150
- *
151
- * FOLLOW-UP(AV-284): global-band skills — skills only link into per-project
152
- * harness dirs today; a `--scope global` machine-band skills location is
153
- * deferred. The manifest line is `[project]`-prefixed to make that explicit.
354
+ * a `replaced` link is delete-then-relink (idempotent); `skipped` is a no-op —
355
+ * and a detection where every action is `skipped` composes NOTHING, so a
356
+ * converged re-run performs zero filesystem mutations.
154
357
  *
155
358
  * @param d - The detection gathered up front.
156
- * @returns A Task that mkdirs each target and creates/replaces each symlink.
359
+ * @returns A Task that mkdirs each needed target and creates/replaces links.
157
360
  */
158
361
  export function composeSkills(d: SkillsDetection): Task<void> {
159
- if (!d.available) return sequence_([]);
160
- const tasks: Task<unknown>[] = [];
161
- for (const { dir } of d.targets) {
162
- tasks.push(mkdir(dir, true));
163
- }
164
- for (const a of d.actions) {
362
+ const pending = d.actions.filter((a) => a.action !== "skipped");
363
+ if (!d.available || pending.length === 0) return sequence_([]);
364
+ const dirs = new Set(pending.map((a) => dirname(a.linkPath)));
365
+ const tasks: Task<unknown>[] = [...dirs]
366
+ .sort()
367
+ .map((dir) => mkdir(dir, true));
368
+ for (const a of pending) {
165
369
  if (a.action === "created") {
166
370
  tasks.push(
167
371
  symlink(a.target, a.linkPath, { undo: deleteFile(a.linkPath) }),
168
372
  );
169
- } else if (a.action === "replaced") {
373
+ } else {
170
374
  tasks.push(deleteFile(a.linkPath));
171
- tasks.push(symlink(a.target, a.linkPath));
375
+ tasks.push(
376
+ symlink(a.target, a.linkPath, { undo: deleteFile(a.linkPath) }),
377
+ );
172
378
  }
173
379
  }
174
- tasks.push(
175
- info(
176
- `[project] Linked ${d.skillCount} skill(s) into ${d.targets.length} dir(s).`,
177
- ),
178
- );
179
380
  return sequence_(tasks);
180
381
  }
181
382
 
182
- /** Project a detection onto the {@link SetupSkillsResult} output shape. */
183
- export function toSkillsResult(d: SkillsDetection): SetupSkillsResult {
184
- return {
185
- actions: d.actions,
186
- harnessCount: d.harnessCount,
187
- skillCount: d.skillCount,
188
- warnings: d.warnings,
189
- };
190
- }
383
+ /**
384
+ * The links this band OWNS right now — every existing symlink pointing into the
385
+ * band's skill root, including dangling ones, ones already correct, and the
386
+ * ones no current skill accounts for. This is what removal acts on, and it is
387
+ * deliberately NOT the forward plan: undoing a freshly composed forward plan on
388
+ * an already-linked tree reversed the mkdirs and removed nothing, while
389
+ * reporting a step count.
390
+ */
391
+ /**
392
+ * The named reason a skills row skips, shared by the setup plan and the doctor
393
+ * row so the two surfaces cannot word the same finding differently. Two strings
394
+ * for one condition is how a user ends up unsure whether they are looking at one
395
+ * problem or two.
396
+ *
397
+ * @param sourceRoot - The band's skill source root, already root-relative.
398
+ * @param band - The band being reported.
399
+ * @returns The reason line.
400
+ */
401
+ export const skillsSkipReason = (
402
+ sourceRoot: string,
403
+ band: ScopeBand,
404
+ ): string =>
405
+ band === "project"
406
+ ? `no project skills (${sourceRoot} is absent)`
407
+ : "no skills installed";
408
+
409
+ export const ownedSkillLinks = (
410
+ d: SkillsDetection,
411
+ ): readonly SymlinkAction[] => [
412
+ ...d.actions.filter((a) => a.owned),
413
+ ...d.orphans,
414
+ ];
191
415
 
192
416
  /**
193
- * The EMPTY_RESULTS error the DIRECT `setup skills` sub-verb raises when no
194
- * skills are discoverable (the run-all instead omits the step). Recovery points
195
- * at where skills COME FROM (U8): package skills install on `sources update`.
417
+ * Compose the removal of every owned link. Each forward effect re-asserts the
418
+ * link (idempotent) and carries its deletion as `undo`, which is what the undo
419
+ * interpreter executes — so the reversal is composed from what detection says
420
+ * this command owns, never from what a fresh forward plan would create.
421
+ *
422
+ * @param d - The detection gathered up front.
423
+ * @returns A Task whose undo removes every owned link.
196
424
  */
197
- export function skillsEmptyError(): PragmaError {
198
- return PragmaError.emptyResults("skill", {
199
- message: "No skills found to link.",
200
- recovery: cliRecovery(
201
- `${RECOVERY_CLI_PREFIX}sources update`,
202
- "Add a design-system package that ships skills to your config, then run `pragma sources update` to install them.",
425
+ export function composeSkillsRemoval(d: SkillsDetection): Task<void> {
426
+ const owned = ownedSkillLinks(d);
427
+ if (owned.length === 0) return sequence_([]);
428
+ return sequence_(
429
+ owned.map((a) =>
430
+ symlink(a.target, a.linkPath, { undo: deleteFile(a.linkPath) }),
203
431
  ),
204
- });
432
+ );
205
433
  }