@canonical/pragma-cli 0.34.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 (798) 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 +20 -22
  505. package/pragma.conf.ts +249 -60
  506. package/src/bin.ts +267 -82
  507. package/src/capabilities/block.parity.test.ts +6 -3
  508. package/src/capabilities/capabilities/capabilities.render.ts +1 -1
  509. package/src/capabilities/capabilities/capabilities.verb.ts +1 -1
  510. package/src/capabilities/capabilities/catalog.ts +3 -3
  511. package/src/capabilities/capabilities/hints.ts +32 -7
  512. package/src/capabilities/capabilities/index.ts +1 -1
  513. package/src/capabilities/colophon/collectColophon.ts +35 -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 +4 -4
  517. package/src/capabilities/config/collectConfigShow.test.ts +1 -0
  518. package/src/capabilities/config/collectConfigShow.ts +3 -3
  519. package/src/capabilities/config/field.render.ts +4 -5
  520. package/src/capabilities/config/fields.ts +17 -10
  521. package/src/capabilities/config/get.verb.ts +70 -0
  522. package/src/capabilities/config/getUnset.test.ts +264 -0
  523. package/src/capabilities/config/index.ts +5 -1
  524. package/src/capabilities/config/runField.ts +40 -22
  525. package/src/capabilities/config/runGet.ts +34 -0
  526. package/src/capabilities/config/runSet.ts +35 -9
  527. package/src/capabilities/config/set.test.ts +48 -14
  528. package/src/capabilities/config/set.verb.ts +8 -7
  529. package/src/capabilities/config/show.render.ts +1 -1
  530. package/src/capabilities/config/show.verb.ts +9 -6
  531. package/src/capabilities/config/types.ts +18 -4
  532. package/src/capabilities/config/unset.verb.ts +58 -0
  533. package/src/capabilities/create/byteEquality.subprocess.test.ts +2 -3
  534. package/src/capabilities/create/byteEquality.test.ts +25 -11
  535. package/src/capabilities/create/cliProjection.ts +227 -0
  536. package/src/capabilities/create/constants.ts +36 -61
  537. package/src/capabilities/create/create.mcp.test.ts +89 -5
  538. package/src/capabilities/create/create.render.ts +71 -7
  539. package/src/capabilities/create/create.test.ts +433 -219
  540. package/src/capabilities/create/create.verb.ts +297 -328
  541. package/src/capabilities/create/createGrammar.test.ts +865 -0
  542. package/src/capabilities/create/createHelp.ts +71 -0
  543. package/src/capabilities/create/createSurface.generated.ts +400 -0
  544. package/src/capabilities/create/crossCli.subprocess.test.ts +745 -0
  545. package/src/capabilities/create/cwdJail.test.ts +24 -5
  546. package/src/capabilities/create/generatorToVerbSpec.test.ts +186 -0
  547. package/src/capabilities/create/generatorToVerbSpec.ts +13 -11
  548. package/src/capabilities/create/index.ts +7 -4
  549. package/src/capabilities/create/messages.ts +18 -0
  550. package/src/capabilities/create/mount.ts +391 -0
  551. package/src/capabilities/create/pathJail.test.ts +90 -0
  552. package/src/capabilities/create/pathJail.ts +8 -5
  553. package/src/capabilities/create/pickGenerator.ts +23 -35
  554. package/src/capabilities/create/shippedCreate.subprocess.test.ts +164 -0
  555. package/src/capabilities/create/types.ts +20 -0
  556. package/src/capabilities/distribution.test.ts +3 -1
  557. package/src/capabilities/distribution.ts +10 -15
  558. package/src/capabilities/doctor/checks/checkKeStore.ts +7 -5
  559. package/src/capabilities/doctor/checks/checkPackageRefs.ts +6 -4
  560. package/src/capabilities/doctor/checks/checkPragmaVersion.ts +2 -2
  561. package/src/capabilities/doctor/checks/checkShellCompletions.test.ts +72 -27
  562. package/src/capabilities/doctor/checks/checkShellCompletions.ts +59 -13
  563. package/src/capabilities/doctor/checks/index.ts +27 -0
  564. package/src/capabilities/doctor/checks/mcpCommand.test.ts +100 -0
  565. package/src/capabilities/doctor/checks/mcpCommand.ts +69 -0
  566. package/src/capabilities/doctor/checks/targetHealth.ts +274 -0
  567. package/src/capabilities/doctor/doctor.render.test.ts +18 -7
  568. package/src/capabilities/doctor/doctor.render.ts +43 -19
  569. package/src/capabilities/doctor/doctor.test.ts +123 -34
  570. package/src/capabilities/doctor/doctor.verb.ts +3 -3
  571. package/src/capabilities/doctor/runChecks.ts +62 -63
  572. package/src/capabilities/doctor/types.ts +20 -4
  573. package/src/capabilities/emptyRecovery.test.ts +13 -8
  574. package/src/capabilities/graph/examples.exec.test.ts +107 -0
  575. package/src/capabilities/graph/index.ts +1 -1
  576. package/src/capabilities/graph/inspect.render.ts +70 -22
  577. package/src/capabilities/graph/inspect.test.ts +260 -5
  578. package/src/capabilities/graph/inspect.verb.ts +18 -6
  579. package/src/capabilities/graph/query.render.ts +15 -3
  580. package/src/capabilities/graph/query.verb.ts +3 -3
  581. package/src/capabilities/graph/runQuery.ts +2 -3
  582. package/src/capabilities/index.ts +3 -1
  583. package/src/capabilities/info/collectInfo.ts +5 -4
  584. package/src/capabilities/info/info.render.ts +1 -1
  585. package/src/capabilities/info/info.verb.ts +1 -1
  586. package/src/capabilities/lazy.test.ts +32 -0
  587. package/src/capabilities/meta/complete.verb.ts +1 -1
  588. package/src/capabilities/meta/index.ts +1 -1
  589. package/src/capabilities/meta/mcp.verb.ts +10 -8
  590. package/src/capabilities/ontology/index.ts +15 -11
  591. package/src/capabilities/ontology/ontology.test.ts +6 -55
  592. package/src/capabilities/ontology/queries.ts +2 -2
  593. package/src/capabilities/ontology/render.ts +3 -4
  594. package/src/capabilities/ontology/verbs.ts +27 -68
  595. package/src/capabilities/prompt/index.ts +2 -2
  596. package/src/capabilities/prompt/prompt.render.ts +6 -2
  597. package/src/capabilities/prompt/types.ts +1 -1
  598. package/src/capabilities/prompt/verbs.ts +4 -5
  599. package/src/capabilities/reference.test.ts +63 -0
  600. package/src/capabilities/resources/provider.ts +342 -85
  601. package/src/capabilities/resources/resources.test.ts +355 -59
  602. package/src/capabilities/setup/buildPlan.ts +236 -0
  603. package/src/capabilities/setup/index.ts +7 -7
  604. package/src/capabilities/setup/mode.ts +74 -0
  605. package/src/capabilities/setup/operations/index.ts +74 -0
  606. package/src/capabilities/setup/operations/setupCompletions.ts +97 -24
  607. package/src/capabilities/setup/operations/setupConfig.ts +124 -0
  608. package/src/capabilities/setup/operations/setupGenerator.ts +396 -326
  609. package/src/capabilities/setup/operations/setupLsp.ts +329 -68
  610. package/src/capabilities/setup/operations/setupMcp.ts +137 -97
  611. package/src/capabilities/setup/operations/setupSkills.ts +336 -108
  612. package/src/capabilities/setup/plan.render.ts +241 -0
  613. package/src/capabilities/setup/plan.ts +236 -0
  614. package/src/capabilities/setup/setup.mcp.correctness.test.ts +432 -0
  615. package/src/capabilities/setup/setup.render.test.ts +281 -73
  616. package/src/capabilities/setup/setup.render.ts +45 -77
  617. package/src/capabilities/setup/setup.test.ts +972 -209
  618. package/src/capabilities/setup/setup.verb.ts +223 -71
  619. package/src/capabilities/setup/shell.test.ts +86 -0
  620. package/src/capabilities/setup/shell.ts +137 -11
  621. package/src/capabilities/setup/targets.ts +367 -0
  622. package/src/capabilities/setup/types.ts +18 -57
  623. package/src/capabilities/shared/assertExecOk.ts +68 -10
  624. package/src/capabilities/shared/index.ts +32 -0
  625. package/src/capabilities/shared/packageManager.test.ts +55 -0
  626. package/src/capabilities/shared/packageManager.ts +62 -6
  627. package/src/capabilities/skill/discover.ts +37 -5
  628. package/src/capabilities/skill/index.ts +1 -1
  629. package/src/capabilities/skill/render.ts +10 -9
  630. package/src/capabilities/skill/skill.test.ts +7 -5
  631. package/src/capabilities/skill/verbs.ts +3 -4
  632. package/src/capabilities/sources/collectStatus.ts +7 -2
  633. package/src/capabilities/sources/index.ts +1 -1
  634. package/src/capabilities/sources/installSkills.ts +84 -7
  635. package/src/capabilities/sources/runUpdate.ts +53 -21
  636. package/src/capabilities/sources/sources.test.ts +154 -2
  637. package/src/capabilities/sources/status.render.ts +1 -1
  638. package/src/capabilities/sources/status.verb.ts +1 -1
  639. package/src/capabilities/sources/update.render.ts +1 -1
  640. package/src/capabilities/sources/update.verb.ts +1 -1
  641. package/src/capabilities/surface.test.ts +134 -17
  642. package/src/capabilities/upgrade/runUpgrade.ts +8 -8
  643. package/src/capabilities/upgrade/upgrade.render.ts +4 -5
  644. package/src/capabilities/upgrade/upgrade.test.ts +3 -3
  645. package/src/capabilities/upgrade/upgrade.verb.ts +1 -1
  646. package/src/capabilities/version/index.ts +12 -0
  647. package/src/capabilities/version/version.test.ts +66 -0
  648. package/src/capabilities/version/version.verb.ts +39 -0
  649. package/src/constants.ts +31 -1
  650. package/src/identity.test.ts +40 -25
  651. package/src/kernel/completion/__snapshots__/emitScripts.test.ts.snap +15 -13
  652. package/src/kernel/completion/complete.test.ts +12 -2
  653. package/src/kernel/completion/complete.ts +1 -1
  654. package/src/kernel/completion/emitScripts.ts +1 -1
  655. package/src/kernel/completion/entitySource.test.ts +1 -1
  656. package/src/kernel/completion/entitySource.ts +21 -8
  657. package/src/kernel/completion/model.test.ts +164 -12
  658. package/src/kernel/completion/model.ts +94 -14
  659. package/src/kernel/completion/parse.test.ts +4 -7
  660. package/src/kernel/completion/parse.ts +15 -0
  661. package/src/kernel/completion/resolve.test.ts +0 -1
  662. package/src/kernel/completion/safety.test.ts +34 -26
  663. package/src/kernel/completion/shellDrive.test.ts +28 -9
  664. package/src/kernel/completion/templates/bash.ts +7 -2
  665. package/src/kernel/completion/templates/index.ts +23 -0
  666. package/src/kernel/completion/types.ts +7 -0
  667. package/src/kernel/config/defaults.test.ts +25 -2
  668. package/src/kernel/config/defaults.ts +4 -3
  669. package/src/kernel/config/evaluateProjectConfig.ts +31 -8
  670. package/src/kernel/config/firstRun.test.ts +44 -38
  671. package/src/kernel/config/firstRun.ts +24 -88
  672. package/src/kernel/config/index.ts +1 -1
  673. package/src/kernel/config/readConfig.test.ts +6 -3
  674. package/src/kernel/config/readConfig.ts +1 -1
  675. package/src/kernel/config/schema.ts +3 -1
  676. package/src/kernel/config/types.ts +3 -1
  677. package/src/kernel/copy.test.ts +34 -4
  678. package/src/kernel/copy.ts +54 -0
  679. package/src/kernel/error/PragmaError.test.ts +5 -2
  680. package/src/kernel/error/PragmaError.ts +4 -2
  681. package/src/kernel/error/constants.ts +7 -5
  682. package/src/kernel/error/fromTaskError.ts +28 -6
  683. package/src/kernel/error/recovery.ts +14 -0
  684. package/src/kernel/error/renderError.ts +42 -1
  685. package/src/kernel/error/types.ts +21 -1
  686. package/src/kernel/index.ts +26 -0
  687. package/src/kernel/packs/collect.ts +12 -16
  688. package/src/kernel/packs/compile.test.ts +130 -1
  689. package/src/kernel/packs/compile.ts +93 -3
  690. package/src/kernel/packs/disclosure.ts +2 -2
  691. package/src/kernel/packs/graphql/buildLookupDocument.ts +1 -1
  692. package/src/kernel/packs/graphql/fetchGraphqlLookup.ts +3 -4
  693. package/src/kernel/packs/graphql/index.ts +20 -0
  694. package/src/kernel/packs/index.ts +40 -0
  695. package/src/kernel/packs/iri.test.ts +73 -0
  696. package/src/kernel/packs/iri.ts +66 -14
  697. package/src/kernel/packs/renderPack.ts +24 -5
  698. package/src/kernel/packs/resolveEntity.test.ts +213 -0
  699. package/src/kernel/packs/resolveEntity.ts +112 -18
  700. package/src/kernel/packs/runBodies.ts +2 -3
  701. package/src/kernel/packs/sample.ts +1 -1
  702. package/src/kernel/packs/schema.ts +18 -1
  703. package/src/kernel/packs/sparql/applyFilters.ts +16 -17
  704. package/src/kernel/packs/sparql/buildLookupQuery.ts +75 -3
  705. package/src/kernel/packs/sparql/index.ts +37 -0
  706. package/src/kernel/packs/sparql/runSelect.test.ts +1 -1
  707. package/src/kernel/packs/sparql/runSelect.ts +3 -4
  708. package/src/kernel/packs/toolDescription.test.ts +42 -3
  709. package/src/kernel/packs/types.ts +13 -0
  710. package/src/kernel/packs/uniqueness.ts +1 -1
  711. package/src/kernel/project/cli/buildProgram.test.ts +147 -12
  712. package/src/kernel/project/cli/buildProgram.ts +77 -18
  713. package/src/kernel/project/cli/constants.ts +34 -0
  714. package/src/kernel/project/cli/dispatch.test.ts +160 -3
  715. package/src/kernel/project/cli/dispatch.ts +222 -42
  716. package/src/kernel/project/cli/exitCodes.ts +1 -1
  717. package/src/kernel/project/cli/globalFlags.test.ts +117 -1
  718. package/src/kernel/project/cli/globalFlags.ts +130 -30
  719. package/src/kernel/project/cli/helpFormat.ts +13 -0
  720. package/src/kernel/project/cli/rootHelp.ts +41 -12
  721. package/src/kernel/project/cli/suggest.test.ts +33 -1
  722. package/src/kernel/project/cli/suggest.ts +25 -1
  723. package/src/kernel/project/cli/verbHelp.test.ts +30 -0
  724. package/src/kernel/project/cli/verbHelp.ts +23 -7
  725. package/src/kernel/project/mcp/buildServer.ts +7 -4
  726. package/src/kernel/project/mcp/envelope.ts +2 -2
  727. package/src/kernel/project/mcp/instructions.ts +2 -2
  728. package/src/kernel/project/mcp/mcpError.ts +1 -1
  729. package/src/kernel/project/mcp/parity.test.ts +5 -2
  730. package/src/kernel/project/mcp/prompts/index.ts +37 -0
  731. package/src/kernel/project/mcp/prompts/source.ts +2 -2
  732. package/src/kernel/project/mcp/registerVerb.ts +35 -9
  733. package/src/kernel/project/mcp/serve.ts +2 -2
  734. package/src/kernel/render/__snapshots__/renderers.test.ts.snap +7 -4
  735. package/src/kernel/render/contracts.ts +21 -0
  736. package/src/kernel/render/envelope.ts +2 -3
  737. package/src/kernel/render/formatters.ts +1 -1
  738. package/src/kernel/render/renderers.test.ts +243 -6
  739. package/src/kernel/render/renderers.ts +222 -20
  740. package/src/kernel/render/style.test.ts +75 -24
  741. package/src/kernel/render/style.ts +31 -1
  742. package/src/kernel/render/turtle.ts +222 -0
  743. package/src/kernel/runtime/graphpack/buildIndex.ts +1 -1
  744. package/src/kernel/runtime/graphpack/embedded/pack.generated.ts +3 -3
  745. package/src/kernel/runtime/graphpack/embedded/pack.index.generated.ts +1 -1
  746. package/src/kernel/runtime/graphpack/embedded.ts +3 -3
  747. package/src/kernel/runtime/graphpack/manifest.ts +1 -1
  748. package/src/kernel/runtime/graphpack/read.ts +1 -2
  749. package/src/kernel/runtime/loadSession.ts +1 -1
  750. package/src/kernel/runtime/probe.ts +6 -6
  751. package/src/kernel/runtime/readEntity.ts +472 -28
  752. package/src/kernel/runtime/refs/index.ts +39 -0
  753. package/src/kernel/runtime/refs/parseRef.ts +2 -2
  754. package/src/kernel/runtime/refs/resolve.ts +4 -4
  755. package/src/kernel/runtime/storeReadiness.ts +1 -2
  756. package/src/kernel/runtime/types.ts +15 -1
  757. package/src/kernel/runtime/wasmEmbed.test.ts +37 -39
  758. package/src/kernel/spec/emitReference.ts +105 -30
  759. package/src/kernel/spec/emitSurface.ts +48 -6
  760. package/src/kernel/spec/surfaceConformance.test.ts +4 -2
  761. package/src/kernel/spec/types.ts +248 -4
  762. package/src/testing/behavioral/docExamples.test.ts +14 -0
  763. package/src/testing/behavioral/errorMatrix.mcp.test.ts +2 -2
  764. package/src/testing/behavioral/firstRun.e2e.test.ts +24 -24
  765. package/src/testing/behavioral/journeys.cli.test.ts +1 -1
  766. package/src/testing/behavioral/journeys.defaultPack.test.ts +7 -7
  767. package/src/testing/behavioral/journeys.implementation.test.ts +206 -0
  768. package/src/testing/behavioral/journeys.interactiveTty.e2e.test.ts +2 -2
  769. package/src/testing/behavioral/journeys.packageStories.test.ts +4 -4
  770. package/src/testing/behavioral/mcpServe.e2e.test.ts +57 -2
  771. package/src/testing/behavioral/mcpSurface.test.ts +1 -1
  772. package/src/testing/behavioral/rootCli.e2e.test.ts +26 -2
  773. package/src/testing/eval/cases/effectful.ts +3 -2
  774. package/src/testing/fixtures/blockGraph.ts +79 -0
  775. package/src/testing/fixtures/graph/canonical.ts +88 -2
  776. package/src/testing/fixtures/graph/defaultPack.ts +1 -1
  777. package/src/testing/helpers/blankCanonicalRanges.ts +36 -0
  778. package/src/testing/helpers/projectMcp.ts +32 -6
  779. package/src/testing/helpers/runCli.ts +35 -18
  780. package/src/testing/perf/budgets.test.ts +20 -9
  781. package/src/testing/perf/budgets.ts +58 -9
  782. package/src/testing/perf/codegen.test.ts +126 -0
  783. package/src/testing/perf/globalSetup.test.ts +286 -0
  784. package/src/testing/perf/globalSetup.ts +505 -23
  785. package/src/testing/perf/measure.test.ts +38 -0
  786. package/src/testing/perf/measure.ts +23 -4
  787. package/src/testing/setupXdgIsolation.ts +81 -21
  788. package/src/testing/tempRoot.globalSetup.ts +122 -0
  789. package/dist/pragma +0 -0
  790. package/src/capabilities/create/compiledCreate.subprocess.test.ts +0 -189
  791. package/src/capabilities/create/templates.embedded.generated.ts +0 -28
  792. package/src/capabilities/doctor/checks/checkConfigFile.ts +0 -42
  793. package/src/capabilities/doctor/checks/checkMcpCommands.ts +0 -114
  794. package/src/capabilities/doctor/checks/checkMcpConfigured.ts +0 -68
  795. package/src/capabilities/doctor/checks/checkSkillsSymlinked.ts +0 -61
  796. package/src/capabilities/doctor/checks/deriveBand.test.ts +0 -42
  797. package/src/capabilities/doctor/checks/deriveBand.ts +0 -28
  798. package/src/kernel/config/__snapshots__/firstRun.test.ts.snap +0 -11
@@ -0,0 +1,100 @@
1
+ /**
2
+ * `commandOf` reads BOTH registered entry shapes.
3
+ *
4
+ * A harness whose schema requires `command` to be an argv array (OpenCode)
5
+ * carries the executable in the first element; a string-valued `command` IS the
6
+ * executable. Reading only the string form made doctor skip an entry `setup`
7
+ * had just written correctly — and report no command-based servers on a fully
8
+ * configured machine. The two shapes must resolve to the same executable, which
9
+ * is what these cases pin.
10
+ */
11
+
12
+ import { mkdtempSync, rmSync, writeFileSync } from "node:fs";
13
+ import { tmpdir } from "node:os";
14
+ import { join } from "node:path";
15
+ import type { PlatformEnv } from "@canonical/harnesses";
16
+ import { afterAll, describe, expect, it } from "vitest";
17
+ import { commandOf, commandResolves } from "./mcpCommand.js";
18
+
19
+ describe("commandOf — one executable, either entry shape", () => {
20
+ it("reads a string command", () => {
21
+ expect(commandOf({ command: "pragma", args: ["mcp", "serve"] })).toBe(
22
+ "pragma",
23
+ );
24
+ });
25
+
26
+ it("reads the executable out of an argv array", () => {
27
+ expect(commandOf({ command: ["pragma", "mcp", "serve"] })).toBe("pragma");
28
+ });
29
+
30
+ it("skips the leading empty element rather than returning it", () => {
31
+ expect(commandOf({ command: ["", "pragma"] })).toBe("pragma");
32
+ });
33
+
34
+ it("has no command for an HTTP entry", () => {
35
+ expect(commandOf({ type: "http", url: "https://example.test" })).toBe(
36
+ undefined,
37
+ );
38
+ });
39
+
40
+ it("has no command for an empty string, an empty array, or a non-entry", () => {
41
+ expect(commandOf({ command: "" })).toBe(undefined);
42
+ expect(commandOf({ command: [] })).toBe(undefined);
43
+ expect(commandOf(null)).toBe(undefined);
44
+ expect(commandOf("pragma")).toBe(undefined);
45
+ });
46
+ });
47
+
48
+ describe("commandResolves — the host's own resolution rules", () => {
49
+ const dirs: string[] = [];
50
+ const tmp = (): string => {
51
+ const dir = mkdtempSync(join(tmpdir(), "pragma-mcp-path-"));
52
+ dirs.push(dir);
53
+ return dir;
54
+ };
55
+ afterAll(() => {
56
+ for (const dir of dirs) rmSync(dir, { recursive: true, force: true });
57
+ });
58
+
59
+ const hostOf = (
60
+ platform: PlatformEnv["platform"],
61
+ dir: string,
62
+ ): PlatformEnv => ({
63
+ platform,
64
+ env: { PATH: dir },
65
+ home: dir,
66
+ isWsl: false,
67
+ });
68
+
69
+ it("resolves a Windows shim, which a bare-name PATH join cannot see", async () => {
70
+ // npm installs the CLI as `pragma.cmd` on Windows. Joining the bare name
71
+ // onto each PATH directory found nothing, so a registration `setup` had
72
+ // just written correctly was reported as a dead command. (The file is
73
+ // spelled to match a default `PATHEXT` entry exactly, because this test
74
+ // runs on a case-sensitive filesystem.)
75
+ const dir = tmp();
76
+ writeFileSync(join(dir, "pragma.CMD"), "");
77
+ expect(await commandResolves("pragma", dir, hostOf("win32", dir))).toBe(
78
+ true,
79
+ );
80
+ });
81
+
82
+ it("resolves a bare name off PATH elsewhere, and says no when it is absent", async () => {
83
+ const dir = tmp();
84
+ writeFileSync(join(dir, "pragma"), "");
85
+ expect(await commandResolves("pragma", dir, hostOf("linux", dir))).toBe(
86
+ true,
87
+ );
88
+ expect(await commandResolves("absent", dir, hostOf("linux", dir))).toBe(
89
+ false,
90
+ );
91
+ });
92
+
93
+ it("checks a path-bearing command as a file, relative to the project root", async () => {
94
+ const dir = tmp();
95
+ writeFileSync(join(dir, "local-bin"), "");
96
+ expect(
97
+ await commandResolves("./local-bin", dir, hostOf("linux", dir)),
98
+ ).toBe(true);
99
+ });
100
+ });
@@ -0,0 +1,69 @@
1
+ /**
2
+ * Command resolution for MCP server entries.
3
+ *
4
+ * A dead `command` makes every agent session try and fail to boot the server,
5
+ * so the `mcp` doctor row reports whether the entry it owns resolves. The row
6
+ * judges ONLY the entry this CLI writes: an aggregate check over every server
7
+ * in the file failed the row whenever some FOREIGN server had a dead command,
8
+ * which is a fact about someone else's tool reported as this one's fault.
9
+ */
10
+
11
+ import { existsSync } from "node:fs";
12
+ import { isAbsolute, join } from "node:path";
13
+ import type { PlatformEnv } from "@canonical/harnesses";
14
+
15
+ /**
16
+ * Extract the stdio command from an MCP server config entry, if any. HTTP/SSE
17
+ * entries (`{ type: "http", url }`) have no command and are not checked.
18
+ *
19
+ * Both entry shapes resolve to the same executable. A harness whose schema
20
+ * requires `command` to be an argv array (OpenCode) carries the executable in
21
+ * its first element; a string-valued `command` IS the executable. Reading only
22
+ * the string form made this check skip an entry `setup` had just written
23
+ * correctly, and report no command-based servers on a configured machine.
24
+ */
25
+ export function commandOf(entry: unknown): string | undefined {
26
+ if (typeof entry !== "object" || entry === null) return undefined;
27
+ const command = (entry as { command?: unknown }).command;
28
+ if (typeof command === "string") {
29
+ return command.length > 0 ? command : undefined;
30
+ }
31
+ if (Array.isArray(command)) {
32
+ return command.find(
33
+ (part): part is string => typeof part === "string" && part.length > 0,
34
+ );
35
+ }
36
+ return undefined;
37
+ }
38
+
39
+ /**
40
+ * Resolve a command the way the host would: a path-bearing entry is checked as
41
+ * a file (relative to the project root), a bare name is searched across `PATH`
42
+ * through `@canonical/harnesses`' `executableCandidates`, which owns the PATH
43
+ * split and the win32 `PATHEXT` rules in one place.
44
+ *
45
+ * The bare-name arm used to join the name onto each PATH directory, which
46
+ * cannot see the `.cmd` shim npm installs on Windows: a registration this CLI
47
+ * had just written correctly was reported as a dead command.
48
+ *
49
+ * @param command - The executable the entry names.
50
+ * @param cwd - The project root a relative command is resolved against.
51
+ * @param platform - The captured host to use instead of this one (tests).
52
+ * @returns Whether the command resolves on this machine.
53
+ * @note Impure — tests candidate paths on the filesystem.
54
+ */
55
+ export async function commandResolves(
56
+ command: string,
57
+ cwd: string,
58
+ platform?: PlatformEnv,
59
+ ): Promise<boolean> {
60
+ if (command.includes("/") || command.includes("\\")) {
61
+ return existsSync(isAbsolute(command) ? command : join(cwd, command));
62
+ }
63
+ const { executableCandidates, readPlatformEnv } = await import(
64
+ "@canonical/harnesses"
65
+ );
66
+ return executableCandidates(command, platform ?? readPlatformEnv()).some(
67
+ (candidate) => existsSync(candidate),
68
+ );
69
+ }
@@ -0,0 +1,274 @@
1
+ /**
2
+ * The banded doctor rows, derived from the setup target table.
3
+ *
4
+ * `doctor` and `setup` are the SAME LIST. Every banded row here carries a
5
+ * target id verbatim — `completions`, not "Shell completions"; `mcp`, not "MCP
6
+ * configured" — because the row name IS the fix command's argument, and a user
7
+ * who reads `✗ mcp` beside `fix: pragma setup mcp` can see that they are the
8
+ * same thing. Two checks reporting on one target under two different names, one
9
+ * of which no command accepts, is how a report ends up describing a machine
10
+ * nobody can repair.
11
+ *
12
+ * Every row's detection comes from the target table's own `detect`, so the two
13
+ * surfaces cannot disagree about what they looked at, and every `fix:` is
14
+ * derived from the row's id and band rather than authored per check.
15
+ *
16
+ * Doctor's UNBANDED environment checks (Node version, the CLI's own version,
17
+ * pack refs, the store) diagnose things setup cannot install and stay outside
18
+ * this list.
19
+ */
20
+
21
+ import { MCP_SERVER_NAME } from "../../../constants.js";
22
+ import type { PragmaRuntime } from "../../../kernel/runtime/index.js";
23
+ import {
24
+ type DetectedRow,
25
+ detectionFailure,
26
+ detectTargets,
27
+ resolveRoots,
28
+ } from "../../setup/buildPlan.js";
29
+ import type {
30
+ CompletionsDetection,
31
+ ConfigDetection,
32
+ } from "../../setup/operations/index.js";
33
+ import {
34
+ type LspDetection,
35
+ lspEditorNames,
36
+ lspSkipReason,
37
+ type McpDetection,
38
+ mcpGroupState,
39
+ type SkillsDetection,
40
+ skillsSkipReason,
41
+ } from "../../setup/operations/index.js";
42
+ import { shortenPath, TARGET_IDS } from "../../setup/plan.js";
43
+ import type { CheckItem, CheckResult, ScopeBand } from "../types.js";
44
+ import { checkShellCompletions } from "./checkShellCompletions.js";
45
+ import { commandResolves } from "./mcpCommand.js";
46
+
47
+ /** What a row reports before its name, band and `fix:` line are attached. */
48
+ interface Health {
49
+ readonly status: CheckResult["status"];
50
+ readonly detail: string;
51
+ readonly items?: readonly CheckItem[];
52
+ /**
53
+ * A remedy that is NOT the derived setup command — the zsh activation line,
54
+ * for instance, which setup cannot perform for the user. Absent means "the
55
+ * fix is to run the target's own setup command", which is the default and the
56
+ * reason the bijection holds without anyone authoring it.
57
+ */
58
+ readonly remedy?: string;
59
+ }
60
+
61
+ /** The `config` row: the global config file exists and parses. */
62
+ const configHealth = (
63
+ d: ConfigDetection,
64
+ roots: { global: string; project: string },
65
+ ): Health => {
66
+ const path = shortenPath(d.path, roots);
67
+ if (!d.exists) return { status: "available", detail: `${path} not created` };
68
+ if (!d.parses) {
69
+ return { status: "fail", detail: `${path} cannot be parsed as JSON` };
70
+ }
71
+ return { status: "pass", detail: `${path} — valid` };
72
+ };
73
+
74
+ /** The `lsp` row — the first this report has ever had. */
75
+ const lspHealth = (d: LspDetection): Health => {
76
+ if (d.state === "unknown") {
77
+ return { status: "skip", detail: lspSkipReason(d) };
78
+ }
79
+ const editors = lspEditorNames(d).join(", ");
80
+ return d.state === "installed"
81
+ ? { status: "pass", detail: `installed (${editors})` }
82
+ : { status: "available", detail: `not installed (${editors})` };
83
+ };
84
+
85
+ /**
86
+ * The `mcp` row: one sub-item per file, each saying whether the entry is
87
+ * present, current, and bootable. Two separate checks used to report this —
88
+ * one for presence, one for command resolution — and the second judged every
89
+ * server in the file, so a foreign server's dead command failed this CLI's row.
90
+ */
91
+ async function mcpHealth(
92
+ d: McpDetection,
93
+ band: ScopeBand,
94
+ cwd: string,
95
+ roots: { global: string; project: string },
96
+ ): Promise<Health> {
97
+ if (d.groups.length === 0) {
98
+ return {
99
+ status: "skip",
100
+ detail: "no harness config location in this band",
101
+ };
102
+ }
103
+ const resolves = await commandResolves(MCP_SERVER_NAME, cwd);
104
+ const items: CheckItem[] = d.groups.map((group) => {
105
+ const state = mcpGroupState(d, group.path);
106
+ const label = shortenPath(group.path, roots);
107
+ if (state === "absent") {
108
+ return { label, status: "available", detail: "not configured" };
109
+ }
110
+ if (state === "drifted") {
111
+ return { label, status: "fail", detail: "entry differs from current" };
112
+ }
113
+ return {
114
+ label,
115
+ status: resolves ? "pass" : "fail",
116
+ detail: resolves
117
+ ? `entry current, \`${MCP_SERVER_NAME}\` resolves`
118
+ : `entry current, \`${MCP_SERVER_NAME}\` is not on PATH`,
119
+ };
120
+ });
121
+ const configured = items.filter((item) => item.status === "pass").length;
122
+ const failing = items.filter((item) => item.status === "fail").length;
123
+ if (failing > 0) {
124
+ return {
125
+ status: "fail",
126
+ detail: `${failing} of ${items.length} need attention`,
127
+ items,
128
+ };
129
+ }
130
+ if (configured === 0) {
131
+ // Project-band absence is not a failure: the band is opt-in, so a
132
+ // repository with no checked-in MCP config is a healthy repository.
133
+ return band === "project"
134
+ ? { status: "skip", detail: "not configured for this project (opt-in)" }
135
+ : {
136
+ status: "available",
137
+ detail: `${items.length} not configured`,
138
+ items,
139
+ };
140
+ }
141
+ return {
142
+ status: configured === items.length ? "pass" : "available",
143
+ detail: `${configured} of ${items.length} current`,
144
+ items,
145
+ };
146
+ }
147
+
148
+ /** The `skills` row: every expected link present, lstat-verified, none stale. */
149
+ function skillsHealth(
150
+ d: SkillsDetection,
151
+ band: ScopeBand,
152
+ roots: { global: string; project: string },
153
+ ): Health {
154
+ if (!d.available) {
155
+ return {
156
+ status: "skip",
157
+ detail: skillsSkipReason(shortenPath(d.sourceRoot, roots), band),
158
+ };
159
+ }
160
+ const stale = d.actions.filter((a) => a.action === "replaced").length;
161
+ const missing = d.actions.filter((a) => a.action === "created").length;
162
+ if (stale > 0) {
163
+ return {
164
+ status: "fail",
165
+ detail: `${stale} of ${d.actions.length} links point elsewhere`,
166
+ };
167
+ }
168
+ // A hand-placed real directory is `skipped` like an already-correct link is,
169
+ // and reporting the two the same way made this row say "links current" where
170
+ // no link exists at all. Setup will never clear such a path — it is not this
171
+ // command's to delete — so the row carries the only remedy that settles it.
172
+ const blocked = d.actions.filter((a) => a.blocked).length;
173
+ if (blocked > 0) {
174
+ return {
175
+ status: "available",
176
+ detail: `${blocked} of ${d.actions.length} link paths hold a real directory`,
177
+ remedy:
178
+ "Move or delete the directory at that path, then link the skills again.",
179
+ };
180
+ }
181
+ if (missing > 0) {
182
+ return {
183
+ status: "available",
184
+ detail: `${missing} of ${d.actions.length} links not created`,
185
+ };
186
+ }
187
+ return { status: "pass", detail: `${d.actions.length} links current` };
188
+ }
189
+
190
+ /**
191
+ * Map one detected row onto its health. The `completions` row delegates to the
192
+ * check that owns the three gates the script depends on — the resolver answers,
193
+ * the installed bytes are current, and zsh has the directory on its `fpath`.
194
+ */
195
+ async function healthOf(
196
+ row: DetectedRow,
197
+ rt: PragmaRuntime,
198
+ roots: { global: string; project: string },
199
+ ): Promise<Health> {
200
+ // A detection that threw is reported as ITS OWN failing row. Letting the
201
+ // rejection escape took the whole banded section of the report with it, so a
202
+ // single unreadable config file left the user with no rows at all — the one
203
+ // moment the report is most worth having.
204
+ const failure = detectionFailure(row);
205
+ if (failure !== undefined) return { status: "fail", detail: failure };
206
+ switch (row.target.id) {
207
+ case "config":
208
+ return configHealth(row.detection as ConfigDetection, roots);
209
+ case "completions": {
210
+ const result = await checkShellCompletions(
211
+ rt.cwd,
212
+ row.detection as CompletionsDetection,
213
+ );
214
+ return {
215
+ status: result.status,
216
+ detail: result.detail,
217
+ ...(result.remedy === undefined ? {} : { remedy: result.remedy }),
218
+ };
219
+ }
220
+ case "lsp":
221
+ return lspHealth(row.detection as LspDetection);
222
+ case "mcp":
223
+ return mcpHealth(row.detection as McpDetection, row.band, rt.cwd, roots);
224
+ default:
225
+ return skillsHealth(row.detection as SkillsDetection, row.band, roots);
226
+ }
227
+ }
228
+
229
+ /**
230
+ * The command that repairs a row — derived from its id and band, never
231
+ * authored. This is the bijection made mechanical: a row exists because a
232
+ * target exists, and its fix is that target's own invocation.
233
+ */
234
+ export const fixCommandFor = (
235
+ id: string,
236
+ band: ScopeBand,
237
+ bin: string,
238
+ ): string => `${bin} setup ${id}${band === "project" ? " --local" : ""}`;
239
+
240
+ /**
241
+ * Run every banded check: the target table, both bands, in table order.
242
+ *
243
+ * @param rt - The per-invocation runtime.
244
+ * @param bin - The binary name the `fix:` lines are derived from.
245
+ * @returns One {@link CheckResult} per (target, band) the machine can hold.
246
+ * @note Impure — every target's detection reads the real filesystem.
247
+ */
248
+ export async function bandedChecks(
249
+ rt: PragmaRuntime,
250
+ bin: string,
251
+ ): Promise<CheckResult[]> {
252
+ const roots = await resolveRoots(rt);
253
+ const detected = await detectTargets(rt, [...TARGET_IDS], "both");
254
+ return Promise.all(
255
+ detected.map(async (row): Promise<CheckResult> => {
256
+ const health = await healthOf(row, rt, roots);
257
+ const needsFix =
258
+ health.status === "fail" || health.status === "available";
259
+ return {
260
+ name: row.target.id,
261
+ status: health.status,
262
+ detail: health.detail,
263
+ band: row.band,
264
+ ...(health.items === undefined ? {} : { items: health.items }),
265
+ ...(needsFix
266
+ ? {
267
+ remedy:
268
+ health.remedy ?? fixCommandFor(row.target.id, row.band, bin),
269
+ }
270
+ : {}),
271
+ };
272
+ }),
273
+ );
274
+ }
@@ -29,8 +29,8 @@ const BANDED_DATA: DoctorData = {
29
29
  },
30
30
  {
31
31
  name: "MCP configured",
32
- status: "fail",
33
- detail: "detected Windsurf but pragma not configured",
32
+ status: "available",
33
+ detail: "not set up for Windsurf",
34
34
  remedy: "pragma setup mcp",
35
35
  band: "global",
36
36
  },
@@ -42,11 +42,12 @@ const BANDED_DATA: DoctorData = {
42
42
  },
43
43
  ],
44
44
  passed: 2,
45
- failed: 1,
45
+ failed: 0,
46
+ available: 1,
46
47
  skipped: 1,
47
48
  };
48
49
 
49
- /** A fixture spanning pass/fail/skip, sub-items, and a remedy — every color path. */
50
+ /** A fixture spanning every status tier, sub-items, and remedies — every color path. */
50
51
  const COLOR_DATA: DoctorData = {
51
52
  checks: [
52
53
  { name: "Node version", status: "pass", detail: "v24" },
@@ -60,10 +61,17 @@ const COLOR_DATA: DoctorData = {
60
61
  ],
61
62
  remedy: "pragma sources update",
62
63
  },
64
+ {
65
+ name: "Shell completions",
66
+ status: "available",
67
+ detail: "resolver OK; zsh script not installed",
68
+ remedy: "pragma setup completions",
69
+ },
63
70
  { name: "Skills symlinked", status: "skip", detail: "no harness" },
64
71
  ],
65
72
  passed: 1,
66
73
  failed: 1,
74
+ available: 1,
67
75
  skipped: 1,
68
76
  };
69
77
 
@@ -112,7 +120,7 @@ describe("doctor render — banded plain report", () => {
112
120
  expect(at("Global")).toBeLessThan(at("Shell completions"));
113
121
  expect(at("MCP configured")).toBeLessThan(at("Project"));
114
122
  expect(at("Project")).toBeLessThan(at("Skills symlinked"));
115
- // A failing banded check keeps its inline remedy under its band.
123
+ // An available banded check keeps its inline setup command under its band.
116
124
  expect(out).toContain("fix: pragma setup mcp");
117
125
  // The tally closes the report.
118
126
  expect(out).toContain("2 passed");
@@ -131,7 +139,7 @@ describe("doctor render — banded llm report", () => {
131
139
  expect(at("### Global")).toBeLessThan(at("Shell completions"));
132
140
  expect(at("Shell completions")).toBeLessThan(at("### Project"));
133
141
  expect(at("### Project")).toBeLessThan(at("Skills symlinked"));
134
- expect(out).toContain("_2 passed, 1 failed, 1 skipped_");
142
+ expect(out).toContain("_2 passed, 0 failed, 1 available, 1 skipped_");
135
143
  });
136
144
  });
137
145
 
@@ -152,9 +160,12 @@ describe("doctor render — piped output is ANSI-free (F1)", () => {
152
160
  expect(out).toContain("pragma doctor");
153
161
  expect(out).toContain("✓ Node version");
154
162
  expect(out).toContain("✗ pack refs");
163
+ expect(out).toContain("◇ Shell completions");
155
164
  expect(out).toContain("○ Skills symlinked");
156
165
  expect(out).toContain("↳ fix: pragma sources update");
157
- expect(out).toContain(" 1 passed · 1 failed · 1 skipped");
166
+ // The available tier keeps its setup command inline, like a fail's fix.
167
+ expect(out).toContain("↳ fix: pragma setup completions");
168
+ expect(out).toContain(" 1 passed · 1 failed · 1 available · 1 skipped");
158
169
  });
159
170
  });
160
171
  });
@@ -13,14 +13,21 @@
13
13
  import chalk from "chalk";
14
14
  import { BIN_NAME } from "../../constants.js";
15
15
  import { defaultStyle, type RenderStyle } from "../../kernel/render/style.js";
16
- import type { Formatters } from "../../kernel/spec/types.js";
17
- import { BAND_LABELS } from "../shared/bands.js";
16
+ import type { Formatters } from "../../kernel/spec/index.js";
17
+ import { BAND_LABELS } from "../shared/index.js";
18
18
  import type { CheckResult, CheckStatus, DoctorData } from "./types.js";
19
19
 
20
- /** Uncolored status glyphs — tinted at render time (never baked at module load). */
20
+ /**
21
+ * Uncolored status glyphs — tinted at render time (never baked at module load).
22
+ * `available` gets its own glyph, distinct from ✗: an opt-in integration that
23
+ * is not set up is not a fault, and rendering it as one would train users to
24
+ * ignore the failure count. The glyph pairs with the word in the tally, so the
25
+ * distinction survives with color stripped.
26
+ */
21
27
  const STATUS_GLYPHS: Record<CheckStatus, string> = {
22
28
  pass: "✓",
23
29
  fail: "✗",
30
+ available: "◇",
24
31
  skip: "○",
25
32
  };
26
33
 
@@ -48,11 +55,16 @@ function doctorStyle(): DoctorStyle {
48
55
  };
49
56
  }
50
57
 
51
- /** Tint a status glyph by meaning — green pass, red fail, yellow skip. */
58
+ /**
59
+ * Tint a status glyph by meaning — green pass, red fail, cyan available
60
+ * (actionable-but-optional, the same tint as the `fix:` arrow it points at),
61
+ * yellow skip.
62
+ */
52
63
  function paintGlyph(status: CheckStatus, style: DoctorStyle): string {
53
64
  const glyph = STATUS_GLYPHS[status];
54
65
  if (status === "pass") return style.green(glyph);
55
66
  if (status === "fail") return style.red(glyph);
67
+ if (status === "available") return style.cyan(glyph);
56
68
  return style.yellow(glyph);
57
69
  }
58
70
 
@@ -89,7 +101,12 @@ function formatCheckPlain(
89
101
  }
90
102
  }
91
103
 
92
- if (check.status === "fail" && check.remedy) {
104
+ // Both actionable tiers keep their inline instruction: a fail's remedy is
105
+ // the repair, an available's remedy is the setup command that enables it.
106
+ if (
107
+ (check.status === "fail" || check.status === "available") &&
108
+ check.remedy
109
+ ) {
93
110
  lines.push(
94
111
  `${INDENT}${style.cyan(FIX_ARROW)} ${style.cyan("fix:")} ${check.remedy}`,
95
112
  );
@@ -98,7 +115,11 @@ function formatCheckPlain(
98
115
  return lines;
99
116
  }
100
117
 
101
- /** Render the pass/fail/skip tally, coloring non-zero fail/skip. */
118
+ /**
119
+ * Render the pass/fail/available/skip tally, coloring the non-zero counts.
120
+ * `available` is counted apart from `failed` so a healthy install with
121
+ * integrations left to opt into never reports failures it does not have.
122
+ */
102
123
  function formatSummary(data: DoctorData, style: DoctorStyle): string {
103
124
  const parts = [style.green(`${data.passed} passed`)];
104
125
  parts.push(
@@ -106,6 +127,11 @@ function formatSummary(data: DoctorData, style: DoctorStyle): string {
106
127
  ? style.red(`${data.failed} failed`)
107
128
  : style.dim(`${data.failed} failed`),
108
129
  );
130
+ parts.push(
131
+ data.available > 0
132
+ ? style.cyan(`${data.available} available`)
133
+ : style.dim(`${data.available} available`),
134
+ );
109
135
  parts.push(
110
136
  data.skipped > 0
111
137
  ? style.yellow(`${data.skipped} skipped`)
@@ -155,22 +181,20 @@ export const doctorFormatters: Formatters<DoctorData> = {
155
181
 
156
182
  llm(data) {
157
183
  const renderCheck = (check: CheckResult): string[] => {
158
- const icon =
159
- check.status === "pass" ? "✓" : check.status === "fail" ? "✗" : "○";
160
- const out = [`- ${icon} **${check.name}**: ${check.detail}`];
184
+ const out = [
185
+ `- ${STATUS_GLYPHS[check.status]} **${check.name}**: ${check.detail}`,
186
+ ];
161
187
  for (const item of check.items ?? []) {
162
- const itemIcon =
163
- item.status === "pass"
164
- ? "✓ "
165
- : item.status === "fail"
166
- ? "✗ "
167
- : item.status === "skip"
168
- ? "○ "
169
- : "";
188
+ const itemIcon = item.status ? `${STATUS_GLYPHS[item.status]} ` : "";
170
189
  const detail = item.detail ? `: ${item.detail}` : "";
171
190
  out.push(` - ${itemIcon}${item.label}${detail}`);
172
191
  }
173
- if (check.status === "fail" && check.remedy) {
192
+ // Same rule as the plain path: fail and available both carry their
193
+ // inline instruction (the repair, or the setup command).
194
+ if (
195
+ (check.status === "fail" || check.status === "available") &&
196
+ check.remedy
197
+ ) {
174
198
  out.push(` - _fix:_ \`${check.remedy}\``);
175
199
  }
176
200
  return out;
@@ -188,7 +212,7 @@ export const doctorFormatters: Formatters<DoctorData> = {
188
212
  section(BAND_LABELS.project, project);
189
213
  lines.push(
190
214
  "",
191
- `_${data.passed} passed, ${data.failed} failed, ${data.skipped} skipped_`,
215
+ `_${data.passed} passed, ${data.failed} failed, ${data.available} available, ${data.skipped} skipped_`,
192
216
  );
193
217
  return lines.join("\n");
194
218
  },