@joekytc/dsh-swarm 0.1.2 → 0.2.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 (567) hide show
  1. package/README.md +3 -3
  2. package/README.zh-CN.md +3 -3
  3. package/client/BoardCard.tsx +24 -2
  4. package/client/ConfigSection.tsx +71 -0
  5. package/client/ConfigSelect.tsx +69 -0
  6. package/client/KanbanBoard.tsx +3 -0
  7. package/client/KanbanTab.tsx +4 -3
  8. package/client/TaskDrawer.tsx +2 -26
  9. package/client/WorkflowRail.tsx +3 -1
  10. package/client/config-store.ts +51 -0
  11. package/client/config.css +110 -0
  12. package/client/index.ts +39 -4
  13. package/client/kanban.css +19 -2
  14. package/client/session-bridge.ts +39 -0
  15. package/client/timeline-model.ts +10 -1
  16. package/client/workflow-model.ts +3 -1
  17. package/lib/client.js +358 -53
  18. package/lib/config.d.ts +8 -1
  19. package/lib/config.js +6 -1
  20. package/lib/dispatcher/agent-runner.d.ts +28 -6
  21. package/lib/dispatcher/agent-runner.js +175 -62
  22. package/lib/dispatcher/chain-auditor.js +4 -1
  23. package/lib/dispatcher/dispatcher.d.ts +62 -3
  24. package/lib/dispatcher/dispatcher.js +243 -20
  25. package/lib/dispatcher/session-events.d.ts +11 -15
  26. package/lib/dispatcher/session-events.js +17 -5
  27. package/lib/dispatcher/v-orchestrator.d.ts +42 -9
  28. package/lib/dispatcher/v-orchestrator.js +236 -28
  29. package/lib/domain/config-override.d.ts +38 -0
  30. package/lib/domain/config-override.js +101 -0
  31. package/lib/domain/delivery-contract.d.ts +3 -2
  32. package/lib/domain/delivery-contract.js +28 -16
  33. package/lib/domain/gate-policy.d.ts +26 -0
  34. package/lib/domain/gate-policy.js +44 -0
  35. package/lib/domain/kanban-service.d.ts +16 -3
  36. package/lib/domain/kanban-service.js +41 -6
  37. package/lib/domain/permissions.js +1 -1
  38. package/lib/domain/planning-checklist.d.ts +5 -0
  39. package/lib/domain/planning-checklist.js +80 -6
  40. package/lib/domain/projection.js +2 -1
  41. package/lib/domain/review-evidence.js +1 -1
  42. package/lib/domain/state-machine.js +2 -1
  43. package/lib/domain/types.d.ts +2 -2
  44. package/lib/index.js +19 -21
  45. package/lib/roles/clean-fs-tools.d.ts +22 -0
  46. package/lib/roles/clean-fs-tools.js +118 -0
  47. package/lib/roles/skill-installer.d.ts +6 -0
  48. package/lib/roles/skill-installer.js +32 -0
  49. package/lib/roles/toolsets.d.ts +13 -1
  50. package/lib/roles/toolsets.js +163 -31
  51. package/lib/roles/wiki-worker.d.ts +1 -0
  52. package/lib/roles/wiki-worker.js +10 -2
  53. package/lib/routes/kanban-http.d.ts +5 -2
  54. package/lib/routes/kanban-http.js +36 -3
  55. package/lib/routes/planning-driver.d.ts +3 -1
  56. package/lib/routes/planning-driver.js +10 -6
  57. package/lib/routes/prefix-router.d.ts +16 -0
  58. package/lib/routes/prefix-router.js +37 -2
  59. package/lib/services/config-provider.d.ts +42 -0
  60. package/lib/services/config-provider.js +94 -0
  61. package/lib/services/gate-runner.d.ts +24 -0
  62. package/lib/services/gate-runner.js +87 -0
  63. package/lib/services/kanban-provider.d.ts +5 -1
  64. package/lib/services/kanban-provider.js +40 -2
  65. package/lib/services/llm-catalog.d.ts +35 -0
  66. package/lib/services/llm-catalog.js +19 -0
  67. package/lib/tools/kanban-tools.js +1 -0
  68. package/lib/tools/main-session-tools.d.ts +17 -2
  69. package/lib/tools/main-session-tools.js +88 -21
  70. package/lib/tools/planning-tools.d.ts +4 -0
  71. package/lib/tools/planning-tools.js +39 -12
  72. package/lib/tools/prefetch-tools.js +1 -0
  73. package/lib/tools/spec-card-tools.js +1 -0
  74. package/lib/tools/wiki-tools.js +5 -4
  75. package/lib/wiki/kb-linkage.d.ts +9 -2
  76. package/lib/wiki/kb-linkage.js +3 -3
  77. package/lib/wiki/local-kb-client.d.ts +14 -0
  78. package/lib/wiki/local-kb-client.js +101 -0
  79. package/lib/wiki/local-kb.d.ts +6 -0
  80. package/lib/wiki/local-kb.js +25 -0
  81. package/lib/wiki/memory-recall.d.ts +14 -6
  82. package/lib/wiki/memory-recall.js +17 -13
  83. package/lib/wiki/page-path.d.ts +9 -3
  84. package/lib/wiki/page-path.js +29 -11
  85. package/lib/wiki/wiki-vault-client.d.ts +3 -3
  86. package/lib/wiki/wiki-vault-client.js +6 -6
  87. package/package.json +16 -11
  88. package/personas/kanban-d/preset.yml +1 -1
  89. package/personas/kanban-dt/agent.cordis.yml +2 -2
  90. package/personas/kanban-dt/preset.yml +1 -1
  91. package/personas/kanban-p/agent.cordis.yml +16 -0
  92. package/personas/kanban-p/preset.yml +1 -1
  93. package/personas/kanban-pt/agent.cordis.yml +38 -8
  94. package/personas/kanban-pt/preset.yml +1 -1
  95. package/personas/kanban-w/agent.cordis.yml +35 -16
  96. package/personas/kanban-w/preset.yml +1 -1
  97. package/personas/persona-dt.md +1 -1
  98. package/personas/persona-p.md +4 -1
  99. package/personas/persona-pt.md +13 -6
  100. package/personas/persona-w.md +11 -9
  101. package/skills/grill-me/SKILL.md +71 -0
  102. package/skills/llm-wiki-skill/.mise.toml +2 -0
  103. package/skills/llm-wiki-skill/.nvmrc +1 -0
  104. package/skills/llm-wiki-skill/AGENTS.md +173 -0
  105. package/skills/llm-wiki-skill/CHANGELOG.md +548 -0
  106. package/skills/llm-wiki-skill/CLAUDE.md +152 -0
  107. package/skills/llm-wiki-skill/HERMES.md +44 -0
  108. package/skills/llm-wiki-skill/README.en.md +261 -0
  109. package/skills/llm-wiki-skill/README.md +291 -0
  110. package/skills/llm-wiki-skill/SKILL.md +1133 -0
  111. package/skills/llm-wiki-skill/assets/graph-demo.gif +0 -0
  112. package/skills/llm-wiki-skill/assets/graph-preview.png +0 -0
  113. package/skills/llm-wiki-skill/deps/LICENSE-d3.txt +13 -0
  114. package/skills/llm-wiki-skill/deps/LICENSE-marked.txt +44 -0
  115. package/skills/llm-wiki-skill/deps/LICENSE-purify.txt +568 -0
  116. package/skills/llm-wiki-skill/deps/LICENSE-roughjs.txt +21 -0
  117. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/SKILL.md +261 -0
  118. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/references/config/first-time-setup.md +106 -0
  119. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/cdp.ts +179 -0
  120. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/constants.ts +13 -0
  121. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/defuddle-converter.ts +58 -0
  122. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/html-to-markdown.ts +135 -0
  123. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/legacy-converter.ts +629 -0
  124. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/main.ts +314 -0
  125. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/markdown-conversion-shared.ts +305 -0
  126. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/media-localizer.ts +317 -0
  127. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/package.json +14 -0
  128. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/paths.ts +29 -0
  129. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/vendor/baoyu-chrome-cdp/package.json +9 -0
  130. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/vendor/baoyu-chrome-cdp/src/index.test.ts +307 -0
  131. package/skills/llm-wiki-skill/deps/baoyu-url-to-markdown/scripts/vendor/baoyu-chrome-cdp/src/index.ts +523 -0
  132. package/skills/llm-wiki-skill/deps/d3.min.js +2 -0
  133. package/skills/llm-wiki-skill/deps/marked.min.js +6 -0
  134. package/skills/llm-wiki-skill/deps/purify.min.js +3 -0
  135. package/skills/llm-wiki-skill/deps/rough.min.js +7 -0
  136. package/skills/llm-wiki-skill/deps/youtube-transcript/SKILL.md +47 -0
  137. package/skills/llm-wiki-skill/deps/youtube-transcript/scripts/get_transcript.py +72 -0
  138. package/skills/llm-wiki-skill/designs/graph-edge-legibility/graph-edge-treatments.html +480 -0
  139. package/skills/llm-wiki-skill/docs/design/oriental-atlas/DESIGN.md +183 -0
  140. package/skills/llm-wiki-skill/docs/design/oriental-atlas/README.md +10 -0
  141. package/skills/llm-wiki-skill/docs/design/oriental-atlas/design-brief.md +170 -0
  142. package/skills/llm-wiki-skill/docs/design/oriental-atlas/oriental-editorial-atlas.html +1908 -0
  143. package/skills/llm-wiki-skill/docs/design/oriental-atlas/reviews/result-review.md +68 -0
  144. package/skills/llm-wiki-skill/docs/graph/2026-06-16-interaction-risk-audit.md +88 -0
  145. package/skills/llm-wiki-skill/docs/graph/2026-06-16-interaction-test-coverage-map.md +212 -0
  146. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-18-phase-0-2-baseline.md +86 -0
  147. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-18-phase-1-3-dom-svg-large-baseline.md +85 -0
  148. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-18-phase-1-4-disposable-validation-gate.md +97 -0
  149. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-18-phase-2-4-global-renderer-trial-matrix.md +168 -0
  150. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-19-phase-6-1-sigma-graphology-trial.md +71 -0
  151. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-19-phase-6-2-vis-network-trial.md +78 -0
  152. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-19-phase-6-3-aggregation-fallback-trial.md +72 -0
  153. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-19-phase-6-4-global-renderer-route-decision.md +94 -0
  154. package/skills/llm-wiki-skill/docs/graph/performance/2026-06-19-sigma-global-production-integration-result.md +102 -0
  155. package/skills/llm-wiki-skill/docs/graph/performance/artifacts/2026-06-18-phase-0-2/stage-4.5-offline-dense-wheel.json +9 -0
  156. package/skills/llm-wiki-skill/docs/graph/performance/artifacts/2026-06-18-phase-0-2/stage-4.5-offline-dense-wheel.png +0 -0
  157. package/skills/llm-wiki-skill/docs/graph/performance/artifacts/2026-06-18-phase-0-2/stage-4.5-offline-navigation.png +0 -0
  158. package/skills/llm-wiki-skill/docs/spark/2026-06-15-omp-tool-status-events-design.md +174 -0
  159. package/skills/llm-wiki-skill/docs/spark/2026-06-16-graph-interaction-geometry-design.md +832 -0
  160. package/skills/llm-wiki-skill/docs/spark/2026-06-16-graph-six-layer-architecture-design.md +577 -0
  161. package/skills/llm-wiki-skill/docs/spark/2026-06-17-static-renderer-coordination-split-design.md +172 -0
  162. package/skills/llm-wiki-skill/docs/spark/2026-06-18-large-graph-global-community-design.md +909 -0
  163. package/skills/llm-wiki-skill/docs/spark/2026-06-19-sigma-global-graph-renderer-design.md +360 -0
  164. package/skills/llm-wiki-skill/docs/spark/2026-06-20-paper-ui-port-design.md +162 -0
  165. package/skills/llm-wiki-skill/docs/spark/2026-06-20-paper-ui-v2-shell-alignment-design.md +384 -0
  166. package/skills/llm-wiki-skill/docs/spark/2026-06-21-graph-experience-completion-design.md +534 -0
  167. package/skills/llm-wiki-skill/docs/spark/2026-06-22-chat-auto-scroll-design.md +185 -0
  168. package/skills/llm-wiki-skill/docs/spark/2026-06-22-graph-community-node-visual-design.md +266 -0
  169. package/skills/llm-wiki-skill/docs/spark/2026-06-25-sigma-overlay-refactor-perf-design.md +170 -0
  170. package/skills/llm-wiki-skill/docs/spark/2026-06-26-global-sigma-community-spotlight-design.md +393 -0
  171. package/skills/llm-wiki-skill/docs/spark/mockups/2026-06-18-large-graph-global-community-flow.html +746 -0
  172. package/skills/llm-wiki-skill/install.ps1 +87 -0
  173. package/skills/llm-wiki-skill/install.sh +722 -0
  174. package/skills/llm-wiki-skill/package-lock.json +11171 -0
  175. package/skills/llm-wiki-skill/package.json +24 -0
  176. package/skills/llm-wiki-skill/packages/graph-engine/package.json +37 -0
  177. package/skills/llm-wiki-skill/packages/graph-engine/src/anim/.gitkeep +1 -0
  178. package/skills/llm-wiki-skill/packages/graph-engine/src/anim/index.ts +179 -0
  179. package/skills/llm-wiki-skill/packages/graph-engine/src/architecture.ts +79 -0
  180. package/skills/llm-wiki-skill/packages/graph-engine/src/diff.ts +121 -0
  181. package/skills/llm-wiki-skill/packages/graph-engine/src/facade.ts +1406 -0
  182. package/skills/llm-wiki-skill/packages/graph-engine/src/graph-node.ts +37 -0
  183. package/skills/llm-wiki-skill/packages/graph-engine/src/index.ts +25 -0
  184. package/skills/llm-wiki-skill/packages/graph-engine/src/layout/edge-geometry.ts +17 -0
  185. package/skills/llm-wiki-skill/packages/graph-engine/src/layout/index.ts +16 -0
  186. package/skills/llm-wiki-skill/packages/graph-engine/src/layout/spatial-index.ts +509 -0
  187. package/skills/llm-wiki-skill/packages/graph-engine/src/model/atlas.ts +18 -0
  188. package/skills/llm-wiki-skill/packages/graph-engine/src/model/index.ts +10 -0
  189. package/skills/llm-wiki-skill/packages/graph-engine/src/model/labels.ts +11 -0
  190. package/skills/llm-wiki-skill/packages/graph-engine/src/model/layout.ts +81 -0
  191. package/skills/llm-wiki-skill/packages/graph-engine/src/model/learning.ts +8 -0
  192. package/skills/llm-wiki-skill/packages/graph-engine/src/model/legacy-helpers.ts +1379 -0
  193. package/skills/llm-wiki-skill/packages/graph-engine/src/model/queue.ts +7 -0
  194. package/skills/llm-wiki-skill/packages/graph-engine/src/model/storage.ts +4 -0
  195. package/skills/llm-wiki-skill/packages/graph-engine/src/model/visibility.ts +9 -0
  196. package/skills/llm-wiki-skill/packages/graph-engine/src/render/.gitkeep +1 -0
  197. package/skills/llm-wiki-skill/packages/graph-engine/src/render/adapter.ts +443 -0
  198. package/skills/llm-wiki-skill/packages/graph-engine/src/render/aggregation-containers.ts +64 -0
  199. package/skills/llm-wiki-skill/packages/graph-engine/src/render/community-cloud-geometry.ts +178 -0
  200. package/skills/llm-wiki-skill/packages/graph-engine/src/render/community-wash.ts +238 -0
  201. package/skills/llm-wiki-skill/packages/graph-engine/src/render/community-washes.ts +19 -0
  202. package/skills/llm-wiki-skill/packages/graph-engine/src/render/compat-contract.ts +14 -0
  203. package/skills/llm-wiki-skill/packages/graph-engine/src/render/controller.ts +705 -0
  204. package/skills/llm-wiki-skill/packages/graph-engine/src/render/controls.ts +288 -0
  205. package/skills/llm-wiki-skill/packages/graph-engine/src/render/dom-svg-renderer.ts +180 -0
  206. package/skills/llm-wiki-skill/packages/graph-engine/src/render/edges.ts +51 -0
  207. package/skills/llm-wiki-skill/packages/graph-engine/src/render/geometry.ts +380 -0
  208. package/skills/llm-wiki-skill/packages/graph-engine/src/render/gestures.ts +673 -0
  209. package/skills/llm-wiki-skill/packages/graph-engine/src/render/graph-renderer-root.ts +387 -0
  210. package/skills/llm-wiki-skill/packages/graph-engine/src/render/hit-testing.ts +56 -0
  211. package/skills/llm-wiki-skill/packages/graph-engine/src/render/host-dom.ts +14 -0
  212. package/skills/llm-wiki-skill/packages/graph-engine/src/render/hover-card.ts +37 -0
  213. package/skills/llm-wiki-skill/packages/graph-engine/src/render/index.ts +213 -0
  214. package/skills/llm-wiki-skill/packages/graph-engine/src/render/keyboard.ts +48 -0
  215. package/skills/llm-wiki-skill/packages/graph-engine/src/render/legend.ts +25 -0
  216. package/skills/llm-wiki-skill/packages/graph-engine/src/render/minimap.ts +45 -0
  217. package/skills/llm-wiki-skill/packages/graph-engine/src/render/model.ts +1339 -0
  218. package/skills/llm-wiki-skill/packages/graph-engine/src/render/node-drag-lifecycle.ts +94 -0
  219. package/skills/llm-wiki-skill/packages/graph-engine/src/render/nodes.ts +103 -0
  220. package/skills/llm-wiki-skill/packages/graph-engine/src/render/offline-reader.ts +209 -0
  221. package/skills/llm-wiki-skill/packages/graph-engine/src/render/overlays-presenter.ts +192 -0
  222. package/skills/llm-wiki-skill/packages/graph-engine/src/render/overlays.ts +73 -0
  223. package/skills/llm-wiki-skill/packages/graph-engine/src/render/pin-position.ts +51 -0
  224. package/skills/llm-wiki-skill/packages/graph-engine/src/render/preview.ts +65 -0
  225. package/skills/llm-wiki-skill/packages/graph-engine/src/render/relation-focus.ts +91 -0
  226. package/skills/llm-wiki-skill/packages/graph-engine/src/render/render-context.ts +85 -0
  227. package/skills/llm-wiki-skill/packages/graph-engine/src/render/render-pipeline.ts +871 -0
  228. package/skills/llm-wiki-skill/packages/graph-engine/src/render/render-styles.ts +1405 -0
  229. package/skills/llm-wiki-skill/packages/graph-engine/src/render/renderer-surface.ts +75 -0
  230. package/skills/llm-wiki-skill/packages/graph-engine/src/render/search.ts +57 -0
  231. package/skills/llm-wiki-skill/packages/graph-engine/src/render/sigma-coordinates.ts +44 -0
  232. package/skills/llm-wiki-skill/packages/graph-engine/src/render/sigma-global-drag.ts +246 -0
  233. package/skills/llm-wiki-skill/packages/graph-engine/src/render/sigma-global-renderer.ts +1425 -0
  234. package/skills/llm-wiki-skill/packages/graph-engine/src/render/sigma-overlay-svg.ts +121 -0
  235. package/skills/llm-wiki-skill/packages/graph-engine/src/render/simulation-bridge.ts +59 -0
  236. package/skills/llm-wiki-skill/packages/graph-engine/src/render/state.ts +262 -0
  237. package/skills/llm-wiki-skill/packages/graph-engine/src/render/toolbar.ts +40 -0
  238. package/skills/llm-wiki-skill/packages/graph-engine/src/render/viewport.ts +336 -0
  239. package/skills/llm-wiki-skill/packages/graph-engine/src/select/.gitkeep +1 -0
  240. package/skills/llm-wiki-skill/packages/graph-engine/src/select/index.ts +189 -0
  241. package/skills/llm-wiki-skill/packages/graph-engine/src/sim/index.ts +372 -0
  242. package/skills/llm-wiki-skill/packages/graph-engine/src/sim/pins.ts +84 -0
  243. package/skills/llm-wiki-skill/packages/graph-engine/src/summary/index.ts +447 -0
  244. package/skills/llm-wiki-skill/packages/graph-engine/src/themes/.gitkeep +1 -0
  245. package/skills/llm-wiki-skill/packages/graph-engine/src/themes/index.ts +8 -0
  246. package/skills/llm-wiki-skill/packages/graph-engine/src/themes/tokens.ts +117 -0
  247. package/skills/llm-wiki-skill/packages/graph-engine/src/types/d3-quadtree.d.ts +22 -0
  248. package/skills/llm-wiki-skill/packages/graph-engine/src/types.ts +531 -0
  249. package/skills/llm-wiki-skill/packages/graph-engine/test/aggregation-fallback-trial-adapter.test.ts +115 -0
  250. package/skills/llm-wiki-skill/packages/graph-engine/test/aggregation-fallback-trial-adapter.ts +222 -0
  251. package/skills/llm-wiki-skill/packages/graph-engine/test/anim.test.ts +121 -0
  252. package/skills/llm-wiki-skill/packages/graph-engine/test/architecture.test.ts +63 -0
  253. package/skills/llm-wiki-skill/packages/graph-engine/test/community-cloud-geometry.test.ts +86 -0
  254. package/skills/llm-wiki-skill/packages/graph-engine/test/community-wash.test.ts +97 -0
  255. package/skills/llm-wiki-skill/packages/graph-engine/test/diff.test.ts +133 -0
  256. package/skills/llm-wiki-skill/packages/graph-engine/test/facade.test.ts +1369 -0
  257. package/skills/llm-wiki-skill/packages/graph-engine/test/geometry.test.ts +147 -0
  258. package/skills/llm-wiki-skill/packages/graph-engine/test/gestures.test.ts +768 -0
  259. package/skills/llm-wiki-skill/packages/graph-engine/test/graph-layout.test.ts +110 -0
  260. package/skills/llm-wiki-skill/packages/graph-engine/test/helpers.test.ts +287 -0
  261. package/skills/llm-wiki-skill/packages/graph-engine/test/interaction-contract.test.ts +106 -0
  262. package/skills/llm-wiki-skill/packages/graph-engine/test/keyboard.test.ts +59 -0
  263. package/skills/llm-wiki-skill/packages/graph-engine/test/large-fixtures.test.ts +47 -0
  264. package/skills/llm-wiki-skill/packages/graph-engine/test/large-graph-fixtures.ts +420 -0
  265. package/skills/llm-wiki-skill/packages/graph-engine/test/learning.test.ts +259 -0
  266. package/skills/llm-wiki-skill/packages/graph-engine/test/node-drag-lifecycle.test.ts +166 -0
  267. package/skills/llm-wiki-skill/packages/graph-engine/test/overlays.test.ts +115 -0
  268. package/skills/llm-wiki-skill/packages/graph-engine/test/preview.test.ts +56 -0
  269. package/skills/llm-wiki-skill/packages/graph-engine/test/queue.test.ts +114 -0
  270. package/skills/llm-wiki-skill/packages/graph-engine/test/relation-focus.test.ts +115 -0
  271. package/skills/llm-wiki-skill/packages/graph-engine/test/render-model.test.ts +1030 -0
  272. package/skills/llm-wiki-skill/packages/graph-engine/test/renderer-adapter-contract.test.ts +271 -0
  273. package/skills/llm-wiki-skill/packages/graph-engine/test/renderer-boundary.test.ts +618 -0
  274. package/skills/llm-wiki-skill/packages/graph-engine/test/renderer-lifecycle.test.ts +1711 -0
  275. package/skills/llm-wiki-skill/packages/graph-engine/test/route-continuity.test.ts +284 -0
  276. package/skills/llm-wiki-skill/packages/graph-engine/test/runtime-state.test.ts +281 -0
  277. package/skills/llm-wiki-skill/packages/graph-engine/test/search-and-legend.test.ts +124 -0
  278. package/skills/llm-wiki-skill/packages/graph-engine/test/select.test.ts +168 -0
  279. package/skills/llm-wiki-skill/packages/graph-engine/test/sigma-coordinates.test.ts +50 -0
  280. package/skills/llm-wiki-skill/packages/graph-engine/test/sigma-global-renderer.test.ts +2210 -0
  281. package/skills/llm-wiki-skill/packages/graph-engine/test/sigma-trial-adapter.test.ts +82 -0
  282. package/skills/llm-wiki-skill/packages/graph-engine/test/sigma-trial-adapter.ts +271 -0
  283. package/skills/llm-wiki-skill/packages/graph-engine/test/sim.test.ts +207 -0
  284. package/skills/llm-wiki-skill/packages/graph-engine/test/simulation-bridge.test.ts +96 -0
  285. package/skills/llm-wiki-skill/packages/graph-engine/test/spatial-index.test.ts +222 -0
  286. package/skills/llm-wiki-skill/packages/graph-engine/test/state.test.ts +189 -0
  287. package/skills/llm-wiki-skill/packages/graph-engine/test/summary-contract.test.ts +422 -0
  288. package/skills/llm-wiki-skill/packages/graph-engine/test/themes.test.ts +62 -0
  289. package/skills/llm-wiki-skill/packages/graph-engine/test/toolbar.test.ts +64 -0
  290. package/skills/llm-wiki-skill/packages/graph-engine/test/viewport.test.ts +213 -0
  291. package/skills/llm-wiki-skill/packages/graph-engine/test/vis-network-trial-adapter.test.ts +82 -0
  292. package/skills/llm-wiki-skill/packages/graph-engine/test/vis-network-trial-adapter.ts +186 -0
  293. package/skills/llm-wiki-skill/packages/graph-engine/tsconfig.json +17 -0
  294. package/skills/llm-wiki-skill/packages/graph-engine/vite.config.ts +15 -0
  295. package/skills/llm-wiki-skill/platforms/claude/CLAUDE.md +37 -0
  296. package/skills/llm-wiki-skill/platforms/claude/companions/llm-wiki-upgrade/SKILL.md +95 -0
  297. package/skills/llm-wiki-skill/platforms/codex/AGENTS.md +23 -0
  298. package/skills/llm-wiki-skill/platforms/hermes/README.md +31 -0
  299. package/skills/llm-wiki-skill/platforms/openclaw/README.md +31 -0
  300. package/skills/llm-wiki-skill/scripts/adapter-state.sh +424 -0
  301. package/skills/llm-wiki-skill/scripts/build-graph-data.sh +395 -0
  302. package/skills/llm-wiki-skill/scripts/build-graph-html.sh +459 -0
  303. package/skills/llm-wiki-skill/scripts/cache.sh +352 -0
  304. package/skills/llm-wiki-skill/scripts/create-source-page.sh +100 -0
  305. package/skills/llm-wiki-skill/scripts/delete-helper.sh +68 -0
  306. package/skills/llm-wiki-skill/scripts/graph-analysis.js +732 -0
  307. package/skills/llm-wiki-skill/scripts/hook-session-start.sh +46 -0
  308. package/skills/llm-wiki-skill/scripts/init-wiki.sh +95 -0
  309. package/skills/llm-wiki-skill/scripts/lib/source-signal-eligibility.js +158 -0
  310. package/skills/llm-wiki-skill/scripts/lint-fix.sh +114 -0
  311. package/skills/llm-wiki-skill/scripts/lint-runner.sh +217 -0
  312. package/skills/llm-wiki-skill/scripts/runtime-context.sh +77 -0
  313. package/skills/llm-wiki-skill/scripts/shared-config.sh +83 -0
  314. package/skills/llm-wiki-skill/scripts/source-record-contract.tsv +10 -0
  315. package/skills/llm-wiki-skill/scripts/source-registry.sh +349 -0
  316. package/skills/llm-wiki-skill/scripts/source-registry.tsv +10 -0
  317. package/skills/llm-wiki-skill/scripts/source-signal-coverage.js +83 -0
  318. package/skills/llm-wiki-skill/scripts/validate-step1.sh +144 -0
  319. package/skills/llm-wiki-skill/scripts/wiki-compat.sh +267 -0
  320. package/skills/llm-wiki-skill/setup.sh +8 -0
  321. package/skills/llm-wiki-skill/templates/entity-template.md +30 -0
  322. package/skills/llm-wiki-skill/templates/graph-styles/wash/footer.html +27 -0
  323. package/skills/llm-wiki-skill/templates/graph-styles/wash/graph-wash-helpers.js +1326 -0
  324. package/skills/llm-wiki-skill/templates/graph-styles/wash/graph-wash.js +1009 -0
  325. package/skills/llm-wiki-skill/templates/graph-styles/wash/header.html +2002 -0
  326. package/skills/llm-wiki-skill/templates/index-en-template.md +51 -0
  327. package/skills/llm-wiki-skill/templates/index-template.md +51 -0
  328. package/skills/llm-wiki-skill/templates/log-en-template.md +11 -0
  329. package/skills/llm-wiki-skill/templates/log-template.md +11 -0
  330. package/skills/llm-wiki-skill/templates/overview-en-template.md +41 -0
  331. package/skills/llm-wiki-skill/templates/overview-template.md +41 -0
  332. package/skills/llm-wiki-skill/templates/purpose-en-template.md +16 -0
  333. package/skills/llm-wiki-skill/templates/purpose-template.md +16 -0
  334. package/skills/llm-wiki-skill/templates/query-template.md +19 -0
  335. package/skills/llm-wiki-skill/templates/schema-template.md +185 -0
  336. package/skills/llm-wiki-skill/templates/source-template.md +51 -0
  337. package/skills/llm-wiki-skill/templates/synthesis-template.md +25 -0
  338. package/skills/llm-wiki-skill/templates/topic-template.md +35 -0
  339. package/skills/llm-wiki-skill/tests/adapter-state.sh +338 -0
  340. package/skills/llm-wiki-skill/tests/browser/graph-aggregation-fallback-trial.ts +737 -0
  341. package/skills/llm-wiki-skill/tests/browser/graph-community-node-map.mjs +255 -0
  342. package/skills/llm-wiki-skill/tests/browser/graph-community-wash-interactions.mjs +170 -0
  343. package/skills/llm-wiki-skill/tests/browser/graph-default-behavior.mjs +630 -0
  344. package/skills/llm-wiki-skill/tests/browser/graph-density-preview.mjs +53 -0
  345. package/skills/llm-wiki-skill/tests/browser/graph-html-insights.mjs +41 -0
  346. package/skills/llm-wiki-skill/tests/browser/graph-large-performance.ts +689 -0
  347. package/skills/llm-wiki-skill/tests/browser/graph-node-slim.mjs +75 -0
  348. package/skills/llm-wiki-skill/tests/browser/graph-offline-phase-6.mjs +660 -0
  349. package/skills/llm-wiki-skill/tests/browser/graph-renderer-trial-shared.ts +291 -0
  350. package/skills/llm-wiki-skill/tests/browser/graph-sigma-global-production.ts +1437 -0
  351. package/skills/llm-wiki-skill/tests/browser/graph-sigma-graphology-trial.ts +949 -0
  352. package/skills/llm-wiki-skill/tests/browser/graph-stage-4-5.mjs +815 -0
  353. package/skills/llm-wiki-skill/tests/browser/graph-vis-network-trial.ts +762 -0
  354. package/skills/llm-wiki-skill/tests/browser/graph-workbench-interactions.mjs +730 -0
  355. package/skills/llm-wiki-skill/tests/browser/validate-graph-trial-result.mjs +149 -0
  356. package/skills/llm-wiki-skill/tests/expected/graph-data-empty.json +60 -0
  357. package/skills/llm-wiki-skill/tests/expected/graph-data-sample.json +396 -0
  358. package/skills/llm-wiki-skill/tests/expected/graph-interactive-basic.html +1736 -0
  359. package/skills/llm-wiki-skill/tests/expected/lint-output.txt +44 -0
  360. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/index.md +1 -0
  361. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/entities/Alpha.md +10 -0
  362. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/entities/Beta.md +7 -0
  363. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/entities/Delta.md +8 -0
  364. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/entities/Gamma.md +8 -0
  365. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/queries/20260422-abc.md +10 -0
  366. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/synthesis/Crystal.md +8 -0
  367. package/skills/llm-wiki-skill/tests/fixtures/coverage-sample-wiki/wiki/topics/Overview.md +9 -0
  368. package/skills/llm-wiki-skill/tests/fixtures/graph-data-empty-wiki/wiki/entities/.gitkeep +0 -0
  369. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/purpose.md +3 -0
  370. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/entities/Attention.md +7 -0
  371. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/entities/Decoder.md +7 -0
  372. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/entities/Encoder.md +7 -0
  373. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/entities/GPT.md +7 -0
  374. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/entities/Transformer.md +13 -0
  375. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/sources/paper.md +9 -0
  376. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/topics/arch.md +12 -0
  377. package/skills/llm-wiki-skill/tests/fixtures/graph-data-sample-wiki/wiki/topics/finetune.md +9 -0
  378. package/skills/llm-wiki-skill/tests/fixtures/graph-interactive-basic/wiki/graph-data.json +40 -0
  379. package/skills/llm-wiki-skill/tests/fixtures/graph-interactive-dense/wiki/graph-data.json +3965 -0
  380. package/skills/llm-wiki-skill/tests/fixtures/graph-interactive-multicomm/wiki/graph-data.json +212 -0
  381. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/index.md +14 -0
  382. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/entities/C++.md +6 -0
  383. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/entities/Lonely.md +4 -0
  384. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/entities/Other.md +8 -0
  385. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/entities/Real.md +7 -0
  386. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/sources/2026-01-01-test-source.md +15 -0
  387. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/sources/2026-02-01-inline-img.md +12 -0
  388. package/skills/llm-wiki-skill/tests/fixtures/lint-sample-wiki/wiki/topics/AIbasic.md +3 -0
  389. package/skills/llm-wiki-skill/tests/graph-aggregation-fallback-trial.regression-1.sh +46 -0
  390. package/skills/llm-wiki-skill/tests/graph-analysis-helper.regression-1.sh +237 -0
  391. package/skills/llm-wiki-skill/tests/graph-browser-large-performance.regression-1.sh +39 -0
  392. package/skills/llm-wiki-skill/tests/graph-browser-stage-4-5.regression-1.sh +163 -0
  393. package/skills/llm-wiki-skill/tests/graph-build-failures.regression-1.sh +91 -0
  394. package/skills/llm-wiki-skill/tests/graph-community-node-map.regression-1.sh +107 -0
  395. package/skills/llm-wiki-skill/tests/graph-community-wash-interactions.regression-1.sh +35 -0
  396. package/skills/llm-wiki-skill/tests/graph-data-confidence-merge.regression-1.sh +309 -0
  397. package/skills/llm-wiki-skill/tests/graph-data-source-paths.regression-1.sh +49 -0
  398. package/skills/llm-wiki-skill/tests/graph-default-behavior.regression-1.sh +35 -0
  399. package/skills/llm-wiki-skill/tests/graph-html-a11y.regression-1.sh +50 -0
  400. package/skills/llm-wiki-skill/tests/graph-html-brand-link.regression-1.sh +47 -0
  401. package/skills/llm-wiki-skill/tests/graph-html-density.regression-1.sh +228 -0
  402. package/skills/llm-wiki-skill/tests/graph-html-drawer-neighbors.regression-1.sh +47 -0
  403. package/skills/llm-wiki-skill/tests/graph-html-insights.regression-1.sh +80 -0
  404. package/skills/llm-wiki-skill/tests/graph-html-long-label.regression-1.sh +92 -0
  405. package/skills/llm-wiki-skill/tests/graph-html-minimap.regression-1.sh +51 -0
  406. package/skills/llm-wiki-skill/tests/graph-html-mobile.regression-1.sh +48 -0
  407. package/skills/llm-wiki-skill/tests/graph-html-oriental-atlas-contract.regression-1.sh +94 -0
  408. package/skills/llm-wiki-skill/tests/graph-html-oriental-design-contract.regression-1.sh +82 -0
  409. package/skills/llm-wiki-skill/tests/graph-html-search.regression-1.sh +52 -0
  410. package/skills/llm-wiki-skill/tests/graph-html-styles.regression-1.sh +66 -0
  411. package/skills/llm-wiki-skill/tests/graph-html-toolbar.regression-1.sh +62 -0
  412. package/skills/llm-wiki-skill/tests/graph-offline-phase-6.regression-1.sh +51 -0
  413. package/skills/llm-wiki-skill/tests/graph-sigma-global-production.regression-1.sh +64 -0
  414. package/skills/llm-wiki-skill/tests/graph-sigma-graphology-trial.regression-1.sh +46 -0
  415. package/skills/llm-wiki-skill/tests/graph-vis-network-trial.regression-1.sh +46 -0
  416. package/skills/llm-wiki-skill/tests/graph-workbench-interactions.regression-1.sh +151 -0
  417. package/skills/llm-wiki-skill/tests/js/graph-wash-bootstrap.test.js +110 -0
  418. package/skills/llm-wiki-skill/tests/js/graph-wash-helpers.test.js +296 -0
  419. package/skills/llm-wiki-skill/tests/js/graph-wash-learning.test.js +260 -0
  420. package/skills/llm-wiki-skill/tests/js/graph-wash-queue.test.js +115 -0
  421. package/skills/llm-wiki-skill/tests/js/graph-wash-runtime-state.test.js +282 -0
  422. package/skills/llm-wiki-skill/tests/js/source-signal-coverage.test.js +48 -0
  423. package/skills/llm-wiki-skill/tests/js/source-signal-eligibility.test.js +202 -0
  424. package/skills/llm-wiki-skill/tests/lib/graph-html-engine-helpers.sh +110 -0
  425. package/skills/llm-wiki-skill/tests/lint-output.regression-1.sh +32 -0
  426. package/skills/llm-wiki-skill/tests/regression.sh +1754 -0
  427. package/skills/llm-wiki-skill/workbench/AGENTS.md +110 -0
  428. package/skills/llm-wiki-skill/workbench/CLAUDE.md +55 -0
  429. package/skills/llm-wiki-skill/workbench/LICENSE +21 -0
  430. package/skills/llm-wiki-skill/workbench/PRODUCT.md +1353 -0
  431. package/skills/llm-wiki-skill/workbench/README.md +30 -0
  432. package/skills/llm-wiki-skill/workbench/docs/current-kb-retrieval-design.md +587 -0
  433. package/skills/llm-wiki-skill/workbench/docs/graph-evolution-1-design.md +210 -0
  434. package/skills/llm-wiki-skill/workbench/docs/stage-2-design.md +1139 -0
  435. package/skills/llm-wiki-skill/workbench/docs/stage-3-design.md +1269 -0
  436. package/skills/llm-wiki-skill/workbench/docs/stage-3.5-design.md +1164 -0
  437. package/skills/llm-wiki-skill/workbench/docs/stage-4-design.md +504 -0
  438. package/skills/llm-wiki-skill/workbench/docs/stage-4.5-design.md +195 -0
  439. package/skills/llm-wiki-skill/workbench/docs/superpowers/specs/2026-05-28-resizable-preview-layout-design.md +165 -0
  440. package/skills/llm-wiki-skill/workbench/docs/superpowers/specs/2026-05-28-settings-panel-scroll-fix.md +50 -0
  441. package/skills/llm-wiki-skill/workbench/server/package.json +31 -0
  442. package/skills/llm-wiki-skill/workbench/server/src/agent.ts +457 -0
  443. package/skills/llm-wiki-skill/workbench/server/src/artifacts.ts +248 -0
  444. package/skills/llm-wiki-skill/workbench/server/src/auth.ts +164 -0
  445. package/skills/llm-wiki-skill/workbench/server/src/config.ts +130 -0
  446. package/skills/llm-wiki-skill/workbench/server/src/conversations.test.ts +159 -0
  447. package/skills/llm-wiki-skill/workbench/server/src/conversations.ts +270 -0
  448. package/skills/llm-wiki-skill/workbench/server/src/digest/batch.ts +189 -0
  449. package/skills/llm-wiki-skill/workbench/server/src/digest/concurrency.test.ts +36 -0
  450. package/skills/llm-wiki-skill/workbench/server/src/digest/concurrency.ts +31 -0
  451. package/skills/llm-wiki-skill/workbench/server/src/digest/subagent.ts +91 -0
  452. package/skills/llm-wiki-skill/workbench/server/src/extensions/artifacts.ts +81 -0
  453. package/skills/llm-wiki-skill/workbench/server/src/extensions/knowledge-base.ts +263 -0
  454. package/skills/llm-wiki-skill/workbench/server/src/extensions/new-wiki.ts +42 -0
  455. package/skills/llm-wiki-skill/workbench/server/src/extensions/synthesis.ts +172 -0
  456. package/skills/llm-wiki-skill/workbench/server/src/graph-watcher.test.ts +196 -0
  457. package/skills/llm-wiki-skill/workbench/server/src/graph.test.ts +113 -0
  458. package/skills/llm-wiki-skill/workbench/server/src/graph.ts +351 -0
  459. package/skills/llm-wiki-skill/workbench/server/src/index.ts +1148 -0
  460. package/skills/llm-wiki-skill/workbench/server/src/knowledge-bases.test.ts +30 -0
  461. package/skills/llm-wiki-skill/workbench/server/src/knowledge-bases.ts +321 -0
  462. package/skills/llm-wiki-skill/workbench/server/src/pages.test.ts +41 -0
  463. package/skills/llm-wiki-skill/workbench/server/src/pages.ts +160 -0
  464. package/skills/llm-wiki-skill/workbench/server/src/retrieval.test.ts +151 -0
  465. package/skills/llm-wiki-skill/workbench/server/src/retrieval.ts +427 -0
  466. package/skills/llm-wiki-skill/workbench/server/src/tool-status-events.test.ts +363 -0
  467. package/skills/llm-wiki-skill/workbench/server/src/tool-status-events.ts +616 -0
  468. package/skills/llm-wiki-skill/workbench/server/src/wiki-init.test.ts +19 -0
  469. package/skills/llm-wiki-skill/workbench/server/src/wiki-init.ts +188 -0
  470. package/skills/llm-wiki-skill/workbench/server/tsconfig.json +10 -0
  471. package/skills/llm-wiki-skill/workbench/tsconfig.json +20 -0
  472. package/skills/llm-wiki-skill/workbench/web/README.md +73 -0
  473. package/skills/llm-wiki-skill/workbench/web/components.json +21 -0
  474. package/skills/llm-wiki-skill/workbench/web/eslint.config.js +22 -0
  475. package/skills/llm-wiki-skill/workbench/web/index.html +16 -0
  476. package/skills/llm-wiki-skill/workbench/web/package.json +54 -0
  477. package/skills/llm-wiki-skill/workbench/web/src/App.tsx +1195 -0
  478. package/skills/llm-wiki-skill/workbench/web/src/components/AddExternalDialog.tsx +375 -0
  479. package/skills/llm-wiki-skill/workbench/web/src/components/AppearancePanel.tsx +158 -0
  480. package/skills/llm-wiki-skill/workbench/web/src/components/ArtifactView.tsx +15 -0
  481. package/skills/llm-wiki-skill/workbench/web/src/components/BatchDigestPanel.tsx +117 -0
  482. package/skills/llm-wiki-skill/workbench/web/src/components/ChatPanel.tsx +890 -0
  483. package/skills/llm-wiki-skill/workbench/web/src/components/CommandMenu.tsx +75 -0
  484. package/skills/llm-wiki-skill/workbench/web/src/components/ExportButtons.tsx +58 -0
  485. package/skills/llm-wiki-skill/workbench/web/src/components/GraphPanel.tsx +800 -0
  486. package/skills/llm-wiki-skill/workbench/web/src/components/GraphReader.tsx +52 -0
  487. package/skills/llm-wiki-skill/workbench/web/src/components/GraphSelection.tsx +100 -0
  488. package/skills/llm-wiki-skill/workbench/web/src/components/GraphSummaryDrawer.tsx +269 -0
  489. package/skills/llm-wiki-skill/workbench/web/src/components/MainViewTabs.tsx +69 -0
  490. package/skills/llm-wiki-skill/workbench/web/src/components/MarkdownView.tsx +106 -0
  491. package/skills/llm-wiki-skill/workbench/web/src/components/NewWikiDialog.tsx +103 -0
  492. package/skills/llm-wiki-skill/workbench/web/src/components/RefMenu.tsx +44 -0
  493. package/skills/llm-wiki-skill/workbench/web/src/components/RightDrawer.tsx +298 -0
  494. package/skills/llm-wiki-skill/workbench/web/src/components/SearchPanel.tsx +165 -0
  495. package/skills/llm-wiki-skill/workbench/web/src/components/SettingsPanel.tsx +320 -0
  496. package/skills/llm-wiki-skill/workbench/web/src/components/Sidebar.tsx +354 -0
  497. package/skills/llm-wiki-skill/workbench/web/src/components/ToolHistorySummary.tsx +111 -0
  498. package/skills/llm-wiki-skill/workbench/web/src/components/ToolStatusRunway.tsx +70 -0
  499. package/skills/llm-wiki-skill/workbench/web/src/components/TopBar.tsx +348 -0
  500. package/skills/llm-wiki-skill/workbench/web/src/components/renderers/DownloadOnlyRenderer.tsx +88 -0
  501. package/skills/llm-wiki-skill/workbench/web/src/components/renderers/HtmlRenderer.tsx +92 -0
  502. package/skills/llm-wiki-skill/workbench/web/src/components/ui/button.tsx +52 -0
  503. package/skills/llm-wiki-skill/workbench/web/src/components/ui/command.tsx +50 -0
  504. package/skills/llm-wiki-skill/workbench/web/src/components/ui/dialog.tsx +156 -0
  505. package/skills/llm-wiki-skill/workbench/web/src/components/ui/input.tsx +21 -0
  506. package/skills/llm-wiki-skill/workbench/web/src/components/ui/tooltip.tsx +57 -0
  507. package/skills/llm-wiki-skill/workbench/web/src/index.css +4204 -0
  508. package/skills/llm-wiki-skill/workbench/web/src/lib/api.ts +648 -0
  509. package/skills/llm-wiki-skill/workbench/web/src/lib/appearance.ts +114 -0
  510. package/skills/llm-wiki-skill/workbench/web/src/lib/drawer-layout.ts +41 -0
  511. package/skills/llm-wiki-skill/workbench/web/src/lib/drawer-state.ts +168 -0
  512. package/skills/llm-wiki-skill/workbench/web/src/lib/graph-reader.ts +25 -0
  513. package/skills/llm-wiki-skill/workbench/web/src/lib/graph-selection-drawer.ts +35 -0
  514. package/skills/llm-wiki-skill/workbench/web/src/lib/graph-selection.ts +96 -0
  515. package/skills/llm-wiki-skill/workbench/web/src/lib/graph-summary-actions.ts +184 -0
  516. package/skills/llm-wiki-skill/workbench/web/src/lib/legacy-tool-status.ts +113 -0
  517. package/skills/llm-wiki-skill/workbench/web/src/lib/model-roles.ts +20 -0
  518. package/skills/llm-wiki-skill/workbench/web/src/lib/search-filter.ts +104 -0
  519. package/skills/llm-wiki-skill/workbench/web/src/lib/sse.ts +72 -0
  520. package/skills/llm-wiki-skill/workbench/web/src/lib/tool-status-format.ts +170 -0
  521. package/skills/llm-wiki-skill/workbench/web/src/lib/tool-status-model.ts +392 -0
  522. package/skills/llm-wiki-skill/workbench/web/src/lib/utils.ts +10 -0
  523. package/skills/llm-wiki-skill/workbench/web/src/lib/view-status.ts +16 -0
  524. package/skills/llm-wiki-skill/workbench/web/src/lib/wiki-links.ts +32 -0
  525. package/skills/llm-wiki-skill/workbench/web/src/main.tsx +10 -0
  526. package/skills/llm-wiki-skill/workbench/web/test/api.test.ts +61 -0
  527. package/skills/llm-wiki-skill/workbench/web/test/app-shell-drawer-layout.test.tsx +48 -0
  528. package/skills/llm-wiki-skill/workbench/web/test/appearance-panel.test.tsx +121 -0
  529. package/skills/llm-wiki-skill/workbench/web/test/appearance.test.ts +262 -0
  530. package/skills/llm-wiki-skill/workbench/web/test/chat-host-source.test.tsx +22 -0
  531. package/skills/llm-wiki-skill/workbench/web/test/chat-panel-auto-scroll.test.tsx +311 -0
  532. package/skills/llm-wiki-skill/workbench/web/test/chat-panel-bubbles.test.tsx +48 -0
  533. package/skills/llm-wiki-skill/workbench/web/test/chat-panel-composer.test.tsx +86 -0
  534. package/skills/llm-wiki-skill/workbench/web/test/chat-panel-tool-status.test.tsx +26 -0
  535. package/skills/llm-wiki-skill/workbench/web/test/export-batch-paper.test.tsx +101 -0
  536. package/skills/llm-wiki-skill/workbench/web/test/graph-drawer-state.test.ts +257 -0
  537. package/skills/llm-wiki-skill/workbench/web/test/graph-panel-paper.test.tsx +200 -0
  538. package/skills/llm-wiki-skill/workbench/web/test/graph-reader-request.test.ts +32 -0
  539. package/skills/llm-wiki-skill/workbench/web/test/graph-reader.test.ts +62 -0
  540. package/skills/llm-wiki-skill/workbench/web/test/graph-selection-drawer.test.ts +56 -0
  541. package/skills/llm-wiki-skill/workbench/web/test/graph-selection.test.ts +83 -0
  542. package/skills/llm-wiki-skill/workbench/web/test/graph-summary-actions.test.ts +188 -0
  543. package/skills/llm-wiki-skill/workbench/web/test/main-view-tabs.test.tsx +34 -0
  544. package/skills/llm-wiki-skill/workbench/web/test/markdown-view.test.tsx +34 -0
  545. package/skills/llm-wiki-skill/workbench/web/test/popup-menus.test.tsx +85 -0
  546. package/skills/llm-wiki-skill/workbench/web/test/render.test.tsx +30 -0
  547. package/skills/llm-wiki-skill/workbench/web/test/render.tsx +38 -0
  548. package/skills/llm-wiki-skill/workbench/web/test/right-drawer-graph-summary.test.tsx +287 -0
  549. package/skills/llm-wiki-skill/workbench/web/test/right-drawer-interactions.test.tsx +182 -0
  550. package/skills/llm-wiki-skill/workbench/web/test/search-filter.test.ts +65 -0
  551. package/skills/llm-wiki-skill/workbench/web/test/search-panel.test.tsx +155 -0
  552. package/skills/llm-wiki-skill/workbench/web/test/setup-dom.ts +66 -0
  553. package/skills/llm-wiki-skill/workbench/web/test/sidebar-v2-source.test.ts +17 -0
  554. package/skills/llm-wiki-skill/workbench/web/test/sidebar.test.tsx +110 -0
  555. package/skills/llm-wiki-skill/workbench/web/test/tool-history-summary.test.tsx +150 -0
  556. package/skills/llm-wiki-skill/workbench/web/test/tool-status-format.test.ts +107 -0
  557. package/skills/llm-wiki-skill/workbench/web/test/tool-status-model.test.ts +324 -0
  558. package/skills/llm-wiki-skill/workbench/web/test/tool-status-runway.test.ts +159 -0
  559. package/skills/llm-wiki-skill/workbench/web/test/topbar.test.tsx +248 -0
  560. package/skills/llm-wiki-skill/workbench/web/test/visual/paper-ui.ts +898 -0
  561. package/skills/llm-wiki-skill/workbench/web/test/wiki-links.test.ts +23 -0
  562. package/skills/llm-wiki-skill/workbench/web/test-results/paper-ui/actual/.gitkeep +1 -0
  563. package/skills/llm-wiki-skill/workbench/web/test-results/paper-ui/baseline/.gitkeep +1 -0
  564. package/skills/llm-wiki-skill/workbench/web/tsconfig.app.json +30 -0
  565. package/skills/llm-wiki-skill/workbench/web/tsconfig.json +7 -0
  566. package/skills/llm-wiki-skill/workbench/web/tsconfig.node.json +24 -0
  567. package/skills/llm-wiki-skill/workbench/web/vite.config.ts +28 -0
@@ -1,3 +1,4 @@
1
+ import { buildLlmCatalog } from '../services/llm-catalog.js';
1
2
  import { serveKanbanEvents } from './kanban-sse.js';
2
3
  function json(res, status, body) {
3
4
  res.statusCode = status;
@@ -12,9 +13,10 @@ function readBody(req) {
12
13
  req.on('error', reject);
13
14
  });
14
15
  }
15
- /** 看板 HTTP 桥(Web GUI 浏览器半消费):GET /kanban/board 读快照;POST /kanban/action 执行状态操作。
16
+ /** 看板 HTTP 桥(Web GUI 浏览器半消费):GET /kanban/board 读快照;POST /kanban/action 执行状态操作;
17
+ * GET/PUT /kanban/config + POST /kanban/config/reset 配置读写;GET /kanban/llm-catalog 模型目录。
16
18
  * 仅在 webServer 服务存在时挂载(CLI/headless/测试裸 Context 不挂)。 */
17
- export function registerKanbanHttp(ctx, provider, config) {
19
+ export function registerKanbanHttp(ctx, provider, configProvider, llm, config) {
18
20
  // 可选服务:经 ctx.get 读取(cordis 4 直接属性读取需 inject;get 不需要)
19
21
  const webServer = ctx.get('webServer');
20
22
  if (!webServer)
@@ -55,7 +57,8 @@ export function registerKanbanHttp(ctx, provider, config) {
55
57
  json(res, 200, { ok: true });
56
58
  return;
57
59
  }
58
- // 整链硬删除(仅 human;GUI 二次确认):purge 无事件流,客户端需自行 resync
60
+ // 整链硬删除(仅 human;GUI 二次确认):purge 无事件流,客户端需自行 resync
61
+ // E/F:删链后联动 dispatcher(游标同步钳回)+ V 编排 entry 清理,防运行中实例跳过后续新链事件。
59
62
  if (body.type === 'delete') {
60
63
  const chainId = String(body.chainId ?? '').trim();
61
64
  if (!chainId) {
@@ -63,6 +66,8 @@ export function registerKanbanHttp(ctx, provider, config) {
63
66
  return;
64
67
  }
65
68
  await provider.service.deleteChain(chainId, 'human');
69
+ if (provider.onChainDeleted)
70
+ await provider.onChainDeleted(chainId);
66
71
  json(res, 200, { ok: true });
67
72
  return;
68
73
  }
@@ -149,6 +154,34 @@ export function registerKanbanHttp(ctx, provider, config) {
149
154
  json(res, 200, { ok: true });
150
155
  return;
151
156
  }
157
+ // 配置读写:reset 是 POST,与 GET/PUT config 经 method 区分(reset 分支前置,防前缀遮蔽)
158
+ if (req.method === 'POST' && req.url?.startsWith('/kanban/config/reset')) {
159
+ json(res, 200, configProvider.reset());
160
+ return;
161
+ }
162
+ if (req.method === 'GET' && req.url?.startsWith('/kanban/config')) {
163
+ json(res, 200, configProvider.snapshot());
164
+ return;
165
+ }
166
+ if (req.method === 'PUT' && req.url?.startsWith('/kanban/config')) {
167
+ const raw = JSON.parse((await readBody(req)) || '{}');
168
+ // 归一化缺省字段,保证缺字段走 400 校验失败而非 500
169
+ const snapshot = {
170
+ wikiVault: { baseUrl: raw.wikiVault?.baseUrl ?? '', pagePrefix: raw.wikiVault?.pagePrefix ?? '' },
171
+ roles: { models: raw.roles?.models ?? {} },
172
+ };
173
+ const r = configProvider.applyOverride(snapshot);
174
+ if (!r.ok) {
175
+ json(res, 400, { error: 'validation failed', fields: r.errors });
176
+ return;
177
+ }
178
+ json(res, 200, { ok: true, effective: r.effective, sources: r.sources });
179
+ return;
180
+ }
181
+ if (req.method === 'GET' && req.url?.startsWith('/kanban/llm-catalog')) {
182
+ json(res, 200, await buildLlmCatalog(llm));
183
+ return;
184
+ }
152
185
  json(res, 404, { error: 'not found' });
153
186
  }
154
187
  catch (err) {
@@ -1,7 +1,9 @@
1
1
  import { KanbanService } from '../domain/kanban-service.js';
2
2
  import type { SpecCard, SpecCardAttachment } from '../domain/types.js';
3
3
  import { type PrefixRoutes } from '../config.js';
4
- /** 阶段 0 规划引导:命令串从 config 派生(决策12),/openspec: 改名时文案自动跟随。 */
4
+ /** 阶段 0 规划引导:命令串从 config 派生(决策12),/openspec: 改名时文案自动跟随。
5
+ * 提问节奏与 skills/grill-me/SKILL.md 对齐:官方 frontier 分轮制(整批问 + 推荐答案 + 答复后解锁下一轮);
6
+ * 增强项:人话硬规则 + 过程风险登记;收敛产物仍为 planning_checklist_save(KB 清单是建链数据源)。 */
5
7
  export declare function buildPlanningGuidance(routes: PrefixRoutes): string;
6
8
  export declare function validateSpecCardForApproval(card: SpecCard): string[];
7
9
  export declare function buildPlanningContext(chainId: string, card: SpecCard, attachments: SpecCardAttachment[], routes?: PrefixRoutes): string;
@@ -1,14 +1,18 @@
1
1
  import { KanbanService } from '../domain/kanban-service.js';
2
2
  import { parsePrefix } from './prefix-router.js';
3
3
  import { DEFAULT_PREFIX_ROUTES } from '../config.js';
4
- /** 阶段 0 规划引导:命令串从 config 派生(决策12),/openspec: 改名时文案自动跟随。 */
4
+ /** 阶段 0 规划引导:命令串从 config 派生(决策12),/openspec: 改名时文案自动跟随。
5
+ * 提问节奏与 skills/grill-me/SKILL.md 对齐:官方 frontier 分轮制(整批问 + 推荐答案 + 答复后解锁下一轮);
6
+ * 增强项:人话硬规则 + 过程风险登记;收敛产物仍为 planning_checklist_save(KB 清单是建链数据源)。 */
5
7
  export function buildPlanningGuidance(routes) {
6
8
  return `
7
- # 阶段 0 规划对话(v2:需求澄清前置化)
8
- 1. 需求澄清(grill-me):一次只问一个问题,先澄清目的、约束、成功标准;逐项拷问假设直至用户"没有任何疑问"。
9
- 2. 仓库事实(planning_prefetch):调只读子代理采集目标仓库/资料/知识库事实(本地路径/分支/目标文件基线/既有实现),不凭空假设。
10
- 3. 收敛(planning_checklist_save):把结论写成结构化需求澄清清单(spec 六段 + manifest repo.files + 澄清问答 + 疑问点)存入 KB(KB 不可达自动兜底临时目录)。
11
- 4. 收尾:提醒用户以 ${routes.openspec} 确认执行结束规划阶段——${routes.openspec} 会从清单建链并自动串行执行。
9
+ # 阶段 0 规划对话(v4:grill-me frontier 分轮,与 skills/grill-me 对齐)
10
+ 1. 需求澄清(grill-me,frontier 分轮):把计划映射为设计决策树——每轮只问当前前提已就绪的问题(frontier),整批问出:编号 + 每问附推荐答案;等用户全部答复后重算 frontier(已定决定向外推进、解锁依赖它的问题)再发下一轮,本轮答不了的依赖问题留到后续轮。先澄清目的、约束、成功标准,逐支拷问直至用户"没有任何疑问"。
11
+ 2. 人话硬规则:问题正文与选项必须通俗;术语避不开时首次出现括号一句话解释;发问前自检「不懂本仓库的人能直接回答吗」,不能就重写。
12
+ 3. 仓库事实(planning_prefetch):事实自查是规划者的职责——调只读子代理采集目标仓库/资料/知识库事实(本地路径/分支/目标文件基线/既有实现),不凭空假设、不拿可自查的问题问用户;只把真正的决定留给用户。
13
+ 4. 风险登记:每轮答复中若发现真实风险或非阻塞关注点,随手记一行(描述 + 来源决定 + 缓解思路),收敛时并入澄清清单;没有就不写,禁止硬凑。
14
+ 5. 收敛(planning_checklist_save):把结论写成结构化需求澄清清单(spec 六段 + manifest repo.files + 澄清问答 + 疑问点 + 风险点(若有))存入 KB(KB 不可达自动兜底临时目录)。
15
+ 6. 收尾:提醒用户以 ${routes.openspec} 确认执行结束规划阶段——${routes.openspec} 会从清单建链并自动串行执行。
12
16
  护栏:规划期只读仓库,禁止任何 git/源码写入;只写 KB 与临时目录。
13
17
  `;
14
18
  }
@@ -1,6 +1,12 @@
1
1
  import { KanbanService } from '../domain/kanban-service.js';
2
2
  import type { PlanningChecklist } from '../domain/planning-checklist.js';
3
3
  import type { PrefixRoutes } from '../config.js';
4
+ /** 防线D:/openspec: 建链后同步等待首张任务卡的最长时长与轮询间隔(fail-open:超时返回 pending,
5
+ * 由链级看门狗接管)。可变对象供测试注入短值(vitest 文件级隔离)。 */
6
+ export declare const OPENSPEC_FIRST_CARD: {
7
+ timeoutMs: number;
8
+ pollIntervalMs: number;
9
+ };
4
10
  export interface PrefixRouteResult {
5
11
  kind: 'plan' | 'openspec' | 'learning' | 'none';
6
12
  chainId?: string;
@@ -9,6 +15,16 @@ export interface PrefixRouteResult {
9
15
  brief?: string;
10
16
  guidance?: string;
11
17
  error?: string;
18
+ /** /openspec: 建链结果;false=被护栏拦截(reason 说明原因),未建任何链/卡。 */
19
+ approved?: boolean;
20
+ reason?: string;
21
+ /** 防线D:建链后同步等待的首卡结果。{taskId,status}=V 已建卡;{pending:true}=等待超时(fail-open,看门狗接管)。 */
22
+ firstCard?: {
23
+ taskId: string;
24
+ status: string;
25
+ } | {
26
+ pending: true;
27
+ };
12
28
  }
13
29
  export declare function parsePrefix(message: string, cfg: PrefixRoutes): PrefixRouteResult;
14
30
  /** v2:/plan: 零副作用——不建链/规格卡/任务卡,仅返回路由结果(workspaceDir/sessionId 由 main-session-tools 捕获)。 */
@@ -1,5 +1,8 @@
1
1
  import { KanbanService, buildChainTitle } from '../domain/kanban-service.js';
2
2
  import { buildLearningBrief, resolveLearningChainId } from '../domain/memory.js';
3
+ /** 防线D:/openspec: 建链后同步等待首张任务卡的最长时长与轮询间隔(fail-open:超时返回 pending,
4
+ * 由链级看门狗接管)。可变对象供测试注入短值(vitest 文件级隔离)。 */
5
+ export const OPENSPEC_FIRST_CARD = { timeoutMs: 120_000, pollIntervalMs: 1_000 };
3
6
  export function parsePrefix(message, cfg) {
4
7
  const trimmed = message.trim();
5
8
  if (trimmed.startsWith(cfg.plan))
@@ -19,6 +22,23 @@ export async function handleOpenspecRoute(message, service, cfg, planning, owner
19
22
  const parsed = parsePrefix(message, cfg);
20
23
  if (parsed.kind !== 'openspec')
21
24
  return parsed;
25
+ // 护栏前移(fail-fast):无 workspaceDir 的链会让 V 在 getVAgent 抛 workspace-unknown
26
+ // 且被 dispatcher 静默吞掉(链上零任务 → 无任何后续事件重试)→ 空壳链死锁。
27
+ // 典型成因:主 agent 进程重启后 planningBySession 重建,仅重存清单未重走 /plan:,
28
+ // workspaceDir 为 null。此处禁止建链建卡,引导用户先 /plan: 重新捕获工作区。
29
+ if (!planning.workspaceDir || !planning.workspaceDir.trim()) {
30
+ return {
31
+ kind: 'openspec', approved: false, reason: 'workspace-unknown', rest: parsed.rest,
32
+ guidance: [
33
+ '## 建链被拦截:workspaceDir 缺失(workspace-unknown)',
34
+ '当前规划上下文没有目标仓库工作区(多为主 agent 重启后清单内存重建所致)。',
35
+ '处理步骤(严格顺序):',
36
+ '1. 重新发送 ' + cfg.plan + ' <需求描述> 让主 agent 捕获工作区(必要时按提示注册工作区);',
37
+ '2. 清单仍在时重发 ' + cfg.openspec + ' 确认即可建链;清单丢失则重新澄清后再确认。',
38
+ '禁止:在无工作区时建链建卡;猜测工作区路径。',
39
+ ].join('\n'),
40
+ };
41
+ }
22
42
  const chain = await service.createChain({
23
43
  title: buildChainTitle(planning.checklist.requirementName ?? planning.requirementName ?? null, parsed.rest, planning.checklist.spec.problem),
24
44
  ownerSessionId, workspaceDir: planning.workspaceDir,
@@ -27,7 +47,22 @@ export async function handleOpenspecRoute(message, service, cfg, planning, owner
27
47
  await service.addSpecCardAttachment(card.id, { name: '需求澄清清单(仓库事实)', kind: 'file-prefetch', ref: planning.checklist.manifest.repo.localPath }, 'v');
28
48
  await service.addSpecCardAttachment(card.id, { name: '需求澄清清单(完整资料)', kind: 'kb', ref: planning.checklistRef }, 'v');
29
49
  await service.approveSpecCard(card.id, 'human');
30
- return { kind: 'openspec', chainId: chain.id, specCardId: card.id, rest: parsed.rest };
50
+ const firstCard = await waitFirstCard(service, chain.id);
51
+ return { kind: 'openspec', chainId: chain.id, specCardId: card.id, rest: parsed.rest, firstCard };
52
+ }
53
+ /** 防线D:轮询看板等首张任务卡(任意 assignee/mode,V 首轮建 p 卡)。成功即返;
54
+ * 超时 fail-open 返回 {pending:true}——不挂死工具调用,失败面由链级看门狗兜底。 */
55
+ async function waitFirstCard(service, chainId) {
56
+ const deadline = Date.now() + OPENSPEC_FIRST_CARD.timeoutMs;
57
+ for (;;) {
58
+ const state = await service.snapshot();
59
+ const t = [...state.tasks.values()].filter((x) => x.chainId === chainId).at(-1);
60
+ if (t)
61
+ return { taskId: t.id, status: t.status };
62
+ if (Date.now() >= deadline)
63
+ return { pending: true };
64
+ await new Promise((r) => setTimeout(r, Math.min(OPENSPEC_FIRST_CARD.pollIntervalMs, Math.max(1, deadline - Date.now()))));
65
+ }
31
66
  }
32
67
  /** /learning 零副作用引导文案:命令串从 config 派生(决策12),歧义/未找到时注入主 agent。 */
33
68
  export function buildLearningGuidance(routes) {
@@ -35,7 +70,7 @@ export function buildLearningGuidance(routes) {
35
70
  '## 经验蒸馏指令(' + routes.learning + ')',
36
71
  '消化上方「链上下文 + 机械信号证据包」,蒸馏 1-3 条可复用经验(返工根因 / 阻塞原因 / 审计教训)。',
37
72
  '每条约成 LearningEntry(title 一句话≤80 字符;lesson 教训;evidence 必须填本链 chain id 作机械证据;tags 自由标签)。',
38
- '调 planning_learning_save:scope=chain 存需求级 projects/<chainId>/learnings/;仓库通用经验用 scope=project(自动归入目标仓库项目级)。',
73
+ '调 planning_learning_save:scope=chain 存需求级 projects/<repoSlug>/<chainId>/learnings/;仓库通用经验用 scope=project(projects/<repoSlug>/learnings/,repoSlug 由链 workspaceDir 派生)。',
39
74
  '无值得沉淀的经验时,明确回复「无新经验」,不要硬凑。',
40
75
  ].join('\n');
41
76
  }
@@ -0,0 +1,42 @@
1
+ import { Service, type Context } from '@deepseek-ai/cordis';
2
+ import type { EditableSnapshot, SourceMap } from '../domain/config-override.js';
3
+ import type { KanbanConfig } from '../config.js';
4
+ declare module '@deepseek-ai/cordis' {
5
+ interface Context {
6
+ swarmConfig: ConfigProvider;
7
+ }
8
+ }
9
+ export type ApplyResult = {
10
+ ok: true;
11
+ effective: EditableSnapshot;
12
+ sources: SourceMap;
13
+ changed: string[];
14
+ } | {
15
+ ok: false;
16
+ errors: string[];
17
+ };
18
+ export declare class ConfigProvider extends Service {
19
+ private readonly baseline;
20
+ private readonly overrideFile;
21
+ private readonly auditFile;
22
+ private override;
23
+ private effective;
24
+ private sources;
25
+ constructor(ctx: Context, baseline: KanbanConfig, storageDir: string);
26
+ getEffective(): KanbanConfig;
27
+ getSources(): SourceMap;
28
+ get mode(): 'remote' | 'local';
29
+ snapshot(): {
30
+ effective: EditableSnapshot;
31
+ sources: SourceMap;
32
+ };
33
+ applyOverride(snapshot: EditableSnapshot): ApplyResult;
34
+ reset(): {
35
+ effective: EditableSnapshot;
36
+ sources: SourceMap;
37
+ };
38
+ private readOverride;
39
+ private writeOverride;
40
+ private appendAudit;
41
+ private diffKeys;
42
+ }
@@ -0,0 +1,94 @@
1
+ import { Service } from '@deepseek-ai/cordis';
2
+ import { readFileSync, writeFileSync, renameSync, existsSync, appendFileSync, mkdirSync } from 'node:fs';
3
+ import { join, dirname } from 'node:path';
4
+ import { mergeConfig, computeSources, projectEditable, validateConfig, diffOverride, } from '../domain/config-override.js';
5
+ export class ConfigProvider extends Service {
6
+ baseline;
7
+ overrideFile;
8
+ auditFile;
9
+ override;
10
+ effective;
11
+ sources;
12
+ constructor(ctx, baseline, storageDir) {
13
+ super(ctx, 'swarmConfig');
14
+ this.baseline = baseline;
15
+ this.overrideFile = join(storageDir, 'config-override.json');
16
+ this.auditFile = join(storageDir, 'config-audit.log');
17
+ this.override = this.readOverride();
18
+ this.effective = mergeConfig(baseline, this.override);
19
+ this.sources = computeSources(this.override);
20
+ }
21
+ getEffective() { return this.effective; }
22
+ getSources() { return this.sources; }
23
+ // mode 派生自 effective.wikiVault.baseUrl;运行期改 baseUrl 需重启 dsh 使客户端注册面同步(D11 不可热切换):
24
+ // 注册期冻结(dispatcher、main-session-tools 客户端构造)与运行期活读(agent-runner guard、kanban-provider 交付闸)
25
+ // 分属两类读取点,中途 applyOverride 改 baseUrl 会产生混合态(后果 fail-closed 可见,不静默)。
26
+ get mode() { return (this.effective.wikiVault?.baseUrl ?? '').trim() ? 'remote' : 'local'; }
27
+ snapshot() {
28
+ return { effective: projectEditable(this.effective), sources: this.sources };
29
+ }
30
+ applyOverride(snapshot) {
31
+ const errors = validateConfig(snapshot);
32
+ if (errors.length)
33
+ return { ok: false, errors };
34
+ const next = diffOverride(this.baseline, snapshot);
35
+ const changed = this.diffKeys(this.override, next);
36
+ this.writeOverride(next);
37
+ if (changed.length)
38
+ this.appendAudit(changed);
39
+ this.override = next;
40
+ this.effective = mergeConfig(this.baseline, next);
41
+ this.sources = computeSources(next);
42
+ return { ok: true, effective: projectEditable(this.effective), sources: this.sources, changed };
43
+ }
44
+ reset() {
45
+ const next = {};
46
+ this.writeOverride(next);
47
+ this.override = next;
48
+ this.effective = mergeConfig(this.baseline, next);
49
+ this.sources = computeSources(next);
50
+ return { effective: projectEditable(this.effective), sources: this.sources };
51
+ }
52
+ readOverride() {
53
+ try {
54
+ if (!existsSync(this.overrideFile))
55
+ return {};
56
+ const raw = JSON.parse(readFileSync(this.overrideFile, 'utf8'));
57
+ return raw ?? {};
58
+ }
59
+ catch (err) {
60
+ console.warn('[dsh-swarm] config-override.json 损坏,回退基线: ' + String(err));
61
+ return {};
62
+ }
63
+ }
64
+ writeOverride(next) {
65
+ mkdirSync(dirname(this.overrideFile), { recursive: true });
66
+ const tmp = this.overrideFile + '.tmp-' + Date.now();
67
+ writeFileSync(tmp, JSON.stringify(next, null, 2));
68
+ renameSync(tmp, this.overrideFile);
69
+ }
70
+ appendAudit(changed) {
71
+ const line = new Date().toISOString() + ' | ' + changed.join(', ') + '\n';
72
+ try {
73
+ mkdirSync(dirname(this.auditFile), { recursive: true });
74
+ appendFileSync(this.auditFile, line);
75
+ }
76
+ catch { /* 审计失败不阻断 */ }
77
+ }
78
+ diffKeys(prev, next) {
79
+ const keys = new Set();
80
+ for (const k of ['baseUrl', 'pagePrefix']) {
81
+ if (prev.wikiVault?.[k] !== next.wikiVault?.[k])
82
+ keys.add('wikiVault.' + k);
83
+ }
84
+ for (const role of ['v', 'p', 'w', 'd', 'pt', 'dt']) {
85
+ for (const f of ['provider', 'model', 'reasoningEffort']) {
86
+ const a = prev.roles?.models?.[role]?.[f];
87
+ const b = next.roles?.models?.[role]?.[f];
88
+ if (a !== b)
89
+ keys.add(`roles.models.${role}.${f}`);
90
+ }
91
+ }
92
+ return [...keys];
93
+ }
94
+ }
@@ -0,0 +1,24 @@
1
+ import type { GateCommand } from '../domain/gate-policy.js';
2
+ export interface GateResult {
3
+ command: string;
4
+ exitCode: number | null;
5
+ durationMs: number;
6
+ output: string;
7
+ truncated: boolean;
8
+ }
9
+ export interface GateRunReport {
10
+ ok: boolean;
11
+ results: GateResult[];
12
+ failure?: {
13
+ command: string;
14
+ code: 'NONZERO' | 'TIMEOUT' | 'FORBIDDEN' | 'SPAWN_FAIL';
15
+ detail: string;
16
+ };
17
+ }
18
+ export declare function runOne(cmd: GateCommand, timeoutMs: number): Promise<GateResult & {
19
+ timedOut?: boolean;
20
+ }>;
21
+ export declare function runGateCommands(commands: GateCommand[], cfg: {
22
+ timeoutMs: number;
23
+ forbidden: string[];
24
+ }, run?: typeof runOne): Promise<GateRunReport>;
@@ -0,0 +1,87 @@
1
+ // src/services/gate-runner.ts
2
+ /** kanban_complete 实测闸执行层(services 层唯一允许 child_process 之处之一):
3
+ * spawn bash -c 执行 GateCommand,带超时整组 SIGKILL(detached 独立进程组,连孙进程一起杀,
4
+ * 防其持住 stdio 管道导致 close 不触发、Promise 挂死)、输出 256KB 截断、
5
+ * 黑名单子串预检(纵深防御,命中即不执行)。
6
+ * 命令串行执行,任一失败(FORBIDDEN/TIMEOUT/SPAWN_FAIL/NONZERO)立即返回,后续命令不再执行。 */
7
+ import { spawn } from 'node:child_process';
8
+ const MAX_OUTPUT = 256 * 1024;
9
+ /** exit 后 close 迟迟不触发(如整组击杀失败、孙进程仍持管道)时的兜底 resolve 宽限 */
10
+ const EXIT_GRACE_MS = 1000;
11
+ export function runOne(cmd, timeoutMs) {
12
+ return new Promise((resolve) => {
13
+ const started = Date.now();
14
+ const child = spawn('bash', ['-c', cmd.command], {
15
+ cwd: cmd.cwd,
16
+ stdio: ['ignore', 'pipe', 'pipe'],
17
+ detached: process.platform !== 'win32', // 独立进程组:超时按组 SIGKILL,防孙进程持管道挂死
18
+ });
19
+ let out = '';
20
+ let truncated = false;
21
+ let timedOut = false;
22
+ let settled = false;
23
+ let exitGrace;
24
+ const finish = (exitCode, output) => {
25
+ if (settled)
26
+ return;
27
+ settled = true;
28
+ clearTimeout(timer);
29
+ if (exitGrace !== undefined)
30
+ clearTimeout(exitGrace);
31
+ resolve({ command: cmd.command, exitCode, durationMs: Date.now() - started, output, truncated, timedOut });
32
+ };
33
+ const killGroup = () => {
34
+ if (child.pid === undefined) {
35
+ child.kill('SIGKILL');
36
+ return;
37
+ }
38
+ try {
39
+ process.kill(-child.pid, 'SIGKILL');
40
+ }
41
+ catch {
42
+ child.kill('SIGKILL');
43
+ }
44
+ };
45
+ const timer = setTimeout(() => { timedOut = true; killGroup(); }, timeoutMs);
46
+ const collect = (chunk) => {
47
+ if (out.length >= MAX_OUTPUT) {
48
+ truncated = true;
49
+ return;
50
+ }
51
+ out += chunk.toString('utf8');
52
+ if (out.length > MAX_OUTPUT) {
53
+ out = out.slice(0, MAX_OUTPUT);
54
+ truncated = true;
55
+ }
56
+ };
57
+ child.stdout.on('data', collect);
58
+ child.stderr.on('data', collect);
59
+ child.on('error', (err) => {
60
+ finish(null, String(err));
61
+ });
62
+ // close 需 stdio 管道全部关闭;exit 先到而 close 迟迟不来时按宽限兜底 resolve(尽力收集已到输出)
63
+ child.on('exit', (code) => {
64
+ exitGrace = setTimeout(() => finish(code, out), EXIT_GRACE_MS);
65
+ });
66
+ child.on('close', (code) => {
67
+ finish(code, out);
68
+ });
69
+ });
70
+ }
71
+ export async function runGateCommands(commands, cfg, run = runOne) {
72
+ const results = [];
73
+ for (const cmd of commands) {
74
+ if (cfg.forbidden.some((f) => cmd.command.includes(f))) {
75
+ return { ok: false, results, failure: { command: cmd.command, code: 'FORBIDDEN', detail: '黑名单命中(纵深防御,不执行)' } };
76
+ }
77
+ const r = await run(cmd, cfg.timeoutMs);
78
+ results.push({ command: r.command, exitCode: r.exitCode, durationMs: r.durationMs, output: r.output, truncated: r.truncated });
79
+ if (r.timedOut)
80
+ return { ok: false, results, failure: { command: r.command, code: 'TIMEOUT', detail: `超时(${cfg.timeoutMs}ms)` } };
81
+ if (r.exitCode === null)
82
+ return { ok: false, results, failure: { command: r.command, code: 'SPAWN_FAIL', detail: r.output } };
83
+ if (r.exitCode !== 0)
84
+ return { ok: false, results, failure: { command: r.command, code: 'NONZERO', detail: `退出码 ${r.exitCode}` } };
85
+ }
86
+ return { ok: true, results };
87
+ }
@@ -1,6 +1,7 @@
1
1
  import { Service, type Context } from '@deepseek-ai/cordis';
2
2
  import { KanbanService } from '../domain/kanban-service.js';
3
3
  import type { KanbanConfig } from '../config.js';
4
+ import type { ConfigProvider } from './config-provider.js';
4
5
  declare module '@deepseek-ai/cordis' {
5
6
  interface Context {
6
7
  kanban: KanbanProvider;
@@ -12,5 +13,8 @@ export declare class KanbanProvider extends Service {
12
13
  runner: {
13
14
  runTask(taskId: string): Promise<void>;
14
15
  } | null;
15
- constructor(ctx: Context, config: KanbanConfig);
16
+ /** 整链硬删除后的联动钩子(由 startDispatcher 装配注入):dispatcher 游标同步 + V 编排 entry 清理。
17
+ * purge 物理重排 events seq,若不同步则删链后新建链的可唤醒事件被运行中实例永久跳过。 */
18
+ onChainDeleted: ((chainId: string) => Promise<void> | void) | null;
19
+ constructor(ctx: Context, config: KanbanConfig, configProvider: ConfigProvider);
16
20
  }
@@ -1,14 +1,52 @@
1
1
  import { Service } from '@deepseek-ai/cordis';
2
2
  import { homedir } from 'node:os';
3
+ import { spawn } from 'node:child_process';
3
4
  import { KanbanService } from '../domain/kanban-service.js';
4
5
  import { FileEventStore } from '../domain/event-store.js';
6
+ import { deriveGatePlan, isGatePlan, branchMatches } from '../domain/gate-policy.js';
7
+ import { runGateCommands } from './gate-runner.js';
5
8
  export class KanbanProvider extends Service {
6
9
  service;
7
10
  /** T32 fix:GUI retry 的任务执行器(由 startDispatcher 装配后注入;webServer 先于 agents 就绪时可为 null)。 */
8
11
  runner = null;
9
- constructor(ctx, config) {
12
+ /** 整链硬删除后的联动钩子(由 startDispatcher 装配注入):dispatcher 游标同步 + V 编排 entry 清理。
13
+ * purge 物理重排 events seq,若不同步则删链后新建链的可唤醒事件被运行中实例永久跳过。 */
14
+ onChainDeleted = null;
15
+ // Task 6:经 configProvider getter 读 effective 配置——配置面板改 wikiVault.baseUrl 后 kb_url 前缀校验热生效。
16
+ constructor(ctx, config, configProvider) {
10
17
  super(ctx, 'kanban');
11
18
  const dir = config.storageDir.replace('$DSH_HOME', process.env.DSH_HOME ?? homedir());
12
- this.service = new KanbanService(new FileEventStore(dir), config.wikiVault?.baseUrl);
19
+ this.service = new KanbanService(new FileEventStore(dir), () => configProvider.getEffective().wikiVault?.baseUrl);
20
+ // P1 实测闸装配(组合根):complete 前派生 GatePlan → 分支一致性核对 → 实测执行。
21
+ // hook 绝不 throw:意外异常记日志并返回 null(零感知 skip,fail-open 与分支不一致语义一致)。
22
+ this.service.setGateHook(async (task, handoff) => {
23
+ try {
24
+ // 热读取(同 wikiVault.baseUrl 先例,getEffective):配置面板改 gates 后无需重建即生效。
25
+ const cfg = configProvider.getEffective().gates ?? { enabled: true, timeoutMs: 600000, forbidden: ['rm -rf /', 'git push'] };
26
+ const plan = deriveGatePlan({ assignee: task.assignee, mode: task.mode, handoff, config: { enabled: cfg.enabled } });
27
+ if (!isGatePlan(plan))
28
+ return null; // skip:disabled/非 D/旧卡/路径违规
29
+ const wt = plan.commands[0].cwd;
30
+ // 分支一致性核对(防报假 worktree 绕闸):查询失败或与 metadata.branch 不一致 → skip 零感知。
31
+ const current = await new Promise((resolve) => {
32
+ const child = spawn('git', ['-C', wt, 'rev-parse', '--abbrev-ref', 'HEAD'], { stdio: ['ignore', 'pipe', 'pipe'] });
33
+ let out = '';
34
+ child.stdout.on('data', (c) => { out += c.toString('utf8'); });
35
+ child.on('error', () => resolve(null));
36
+ child.on('close', (code) => resolve(code === 0 ? out.trim() || null : null));
37
+ });
38
+ if (!branchMatches(current, handoff.metadata?.['branch']))
39
+ return null;
40
+ const report = await runGateCommands(plan.commands, { timeoutMs: cfg.timeoutMs, forbidden: cfg.forbidden });
41
+ const detail = report.ok
42
+ ? plan.commands.map((c) => c.command).join(' && ') + ' exit 0'
43
+ : `${report.failure.code}: ${report.failure.command} — ${report.failure.detail}\n${(report.results.at(-1)?.output ?? '').slice(-2000)}`;
44
+ return { ok: report.ok, detail };
45
+ }
46
+ catch (error) {
47
+ console.error('[dsh-swarm] gate hook failed (zero-awareness skip): ' + String(error));
48
+ return null;
49
+ }
50
+ });
13
51
  }
14
52
  }
@@ -0,0 +1,35 @@
1
+ export interface CatalogProvider {
2
+ id: string;
3
+ name: string;
4
+ }
5
+ export interface CatalogModel {
6
+ id: string;
7
+ name: string;
8
+ efforts: Array<{
9
+ id: string;
10
+ name: string;
11
+ }>;
12
+ }
13
+ export interface LlmCatalog {
14
+ providers: CatalogProvider[];
15
+ models: Record<string, CatalogModel[]>;
16
+ }
17
+ export interface LlmRuntimeLike {
18
+ listProviders(): Array<{
19
+ id: string;
20
+ name: string;
21
+ }>;
22
+ listModels(provider: string): Promise<Array<{
23
+ id: string;
24
+ name: string;
25
+ }>>;
26
+ resolveModelInfo(provider: string, model: string): Promise<{
27
+ reasoning?: {
28
+ efforts?: Array<{
29
+ id: string;
30
+ name: string;
31
+ }>;
32
+ };
33
+ }>;
34
+ }
35
+ export declare function buildLlmCatalog(llm: LlmRuntimeLike): Promise<LlmCatalog>;
@@ -0,0 +1,19 @@
1
+ export async function buildLlmCatalog(llm) {
2
+ const providers = llm.listProviders().map((p) => ({ id: p.id, name: p.name }));
3
+ const models = {};
4
+ for (const p of providers) {
5
+ const list = await llm.listModels(p.id);
6
+ const entries = [];
7
+ for (const m of list) {
8
+ let efforts = [];
9
+ try {
10
+ const info = await llm.resolveModelInfo(p.id, m.id);
11
+ efforts = (info.reasoning?.efforts ?? []).map((e) => ({ id: e.id, name: e.name }));
12
+ }
13
+ catch { /* effort 解析失败 → 空 */ }
14
+ entries.push({ id: m.id, name: m.name, efforts });
15
+ }
16
+ models[p.id] = entries;
17
+ }
18
+ return { providers, models };
19
+ }
@@ -1,4 +1,5 @@
1
1
  import { defineTool } from '@deepseek-ai/dsh-tools';
2
+ import {} from '@deepseek-ai/dsh-util-values';
2
3
  import { KanbanService } from '../domain/kanban-service.js';
3
4
  import { can } from '../domain/permissions.js';
4
5
  function guard(action, caller, task = null) {
@@ -1,5 +1,6 @@
1
1
  import type { Context } from '@deepseek-ai/cordis';
2
- import type { KanbanConfig } from '../config.js';
2
+ import type { PrefixRoutes } from '../config.js';
3
+ import type { ConfigProvider } from '../services/config-provider.js';
3
4
  import { type PlanningToolDeps } from './planning-tools.js';
4
5
  import type { PlanningChecklist } from '../domain/planning-checklist.js';
5
6
  /** v2 规划上下文(/plan: 捕获 → planning_checklist_save 回写 → /openspec: 建链)。模块级内存,随插件进程存活。 */
@@ -13,8 +14,22 @@ export interface PlanningContext {
13
14
  requirementName: string | null;
14
15
  }
15
16
  export declare const planningBySession: Map<string, PlanningContext>;
17
+ export declare const KANBAN_HANDOFF_RULE: (routes: PrefixRoutes) => string;
18
+ /** 防线③:/openspec: 成功后的逐链确定性叙述规则(2026-09-04 mtmgp81q:模型口播 ch_1_mtjrhkrf
19
+ * 与工具结果 ch_1_mtmgp81q 脱节)。逐字引用锚点 + firstCard 成败结论;整包缓存回放仍可能
20
+ * 绕过 prompt 层——最终防线是链级看门狗(防线①)。 */
21
+ export declare function buildOpenspecNarrationRule(r: {
22
+ chainId: string;
23
+ specCardId: string;
24
+ firstCard?: {
25
+ taskId: string;
26
+ status: string;
27
+ } | {
28
+ pending: true;
29
+ };
30
+ }): string;
16
31
  export declare function buildSpawnPrefetch(ctx: Context): PlanningToolDeps['spawnPrefetch'] | undefined;
17
32
  /** v2 主会话工具面:/plan: 捕获规划上下文(零副作用)→ planning_checklist_save 回写 → /openspec: 用清单建链。
18
33
  * 工具面 = kanban_route + 只读 kanban 子集 + spec_card_view + planning 工具;
19
34
  * 无 spec_card_edit/approve、无 kanban_create/complete/block(主会话越权写由工具面裁剪 + prefetch 子代理只读护栏双保险)。 */
20
- export declare function registerMainSessionTools(ctx: Context, config: KanbanConfig): void;
35
+ export declare function registerMainSessionTools(ctx: Context, configProvider: ConfigProvider): void;