pmx-canvas 0.11.0 → 0.12.1

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 (300) hide show
  1. package/.github/extensions/pmx-canvas/extension.mjs +4 -1
  2. package/.github/extensions/pmx-canvas/runtime.json +1 -1
  3. package/.github/extensions/pmx-canvas/tools.json +440 -18
  4. package/CHANGELOG.md +51 -0
  5. package/dist/amp-plugin/pmx-canvas/LICENSE +21 -0
  6. package/dist/amp-plugin/pmx-canvas/THIRD_PARTY_LICENSES.txt +331 -0
  7. package/dist/amp-plugin/pmx-canvas/index.js +5445 -0
  8. package/dist/amp-plugin/pmx-canvas/runtime.json +3 -0
  9. package/dist/amp-plugin/pmx-canvas/shared-runtime.mjs +194 -0
  10. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/SKILL.md +267 -0
  11. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/evals.json +1168 -0
  12. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/fixtures/code-exploration/src/auth/jwt.ts +17 -0
  13. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/fixtures/code-exploration/src/auth/login.ts +12 -0
  14. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/fixtures/code-exploration/src/auth/middleware.ts +13 -0
  15. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/fixtures/code-exploration/src/routes/auth.ts +13 -0
  16. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/evals/fixtures/investigation-board/src/handlers/users.ts +27 -0
  17. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/mcp.json +36 -0
  18. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/ax-html-control-surface.md +101 -0
  19. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/codex-app-adapter.md +151 -0
  20. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/excalidraw-diagram-authoring.md +150 -0
  21. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/full-reference.md +1839 -0
  22. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/github-copilot-app-adapter.md +223 -0
  23. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/html-primitives.md +139 -0
  24. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/importing-context.md +132 -0
  25. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/installing-pmx-canvas.md +301 -0
  26. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/tours-and-recording.md +117 -0
  27. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas/references/workbench-workflows.md +908 -0
  28. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas-orchestration/SKILL.md +141 -0
  29. package/dist/amp-plugin/pmx-canvas/skills/pmx-canvas-testing/SKILL.md +266 -0
  30. package/dist/amp-plugin/pmx-canvas/start-mcp.mjs +14857 -0
  31. package/dist/amp-plugin/pmx-canvas/tools.json +10963 -0
  32. package/dist/canvas/chunks/{abnfDiagram-N423BO3Z-p8dtp6va.js → abnfDiagram-N423BO3Z-cwtsds5d.js} +1 -1
  33. package/dist/canvas/chunks/architecture-TIHT7OUA-x63cwejs.js +1 -0
  34. package/dist/canvas/chunks/{architectureDiagram-T3A2C74G-5jhmxrzf.js → architectureDiagram-T3A2C74G-b4xc9tpz.js} +3 -3
  35. package/dist/canvas/chunks/{blockDiagram-VBNYF7ZC-pw1fa9yb.js → blockDiagram-VBNYF7ZC-ahp3yxxs.js} +7 -7
  36. package/dist/canvas/chunks/{c4Diagram-5PPSVZJV-x07nq0tt.js → c4Diagram-5PPSVZJV-nappnay7.js} +4 -4
  37. package/dist/canvas/chunks/classDiagram-JCYQIIEL-k1j2xc1t.js +1 -0
  38. package/dist/canvas/chunks/classDiagram-v2-OCEON4UE-33x08xf2.js +1 -0
  39. package/dist/canvas/chunks/{cose-bilkent-JH36ORCC-nm39npq0.js → cose-bilkent-JH36ORCC-a428syda.js} +1 -1
  40. package/dist/canvas/chunks/cynefin-VYW2F7L2-8v6jxfz8.js +1 -0
  41. package/dist/canvas/chunks/{cynefinDiagram-MW4NZA55-vdxrwahz.js → cynefinDiagram-MW4NZA55-nspsqebj.js} +1 -1
  42. package/dist/canvas/chunks/{dagre-VZM6K2ZE-bqdm7wpd.js → dagre-VZM6K2ZE-8y6177fh.js} +2 -2
  43. package/dist/canvas/chunks/{diagram-7IWD3JNH-gs5gpr93.js → diagram-7IWD3JNH-vym028wn.js} +4 -4
  44. package/dist/canvas/chunks/{diagram-B4RE2ZJO-cgwjg47s.js → diagram-B4RE2ZJO-jddqb8sy.js} +1 -1
  45. package/dist/canvas/chunks/{diagram-LBJQPF4R-w3vahpav.js → diagram-LBJQPF4R-bjwbpkrn.js} +1 -1
  46. package/dist/canvas/chunks/{diagram-Q27KOJAE-42837z6h.js → diagram-Q27KOJAE-j6ph6hcx.js} +2 -2
  47. package/dist/canvas/chunks/{diagram-UB23O5K3-4fz83q59.js → diagram-UB23O5K3-p09w8jej.js} +1 -1
  48. package/dist/canvas/chunks/{ebnfDiagram-BXEA7PRR-zphtgegj.js → ebnfDiagram-BXEA7PRR-j975ycq5.js} +1 -1
  49. package/dist/canvas/chunks/{erDiagram-JOGREHBK-zvbbdxp4.js → erDiagram-JOGREHBK-sxp6hjn8.js} +5 -5
  50. package/dist/canvas/chunks/eventmodeling-45OFAUF4-xzfgn6xg.js +1 -0
  51. package/dist/canvas/chunks/flowDiagram-UKHOOZJN-2nsmkskb.js +1 -0
  52. package/dist/canvas/chunks/{ganttDiagram-PKOTCBZU-282jzycm.js → ganttDiagram-PKOTCBZU-4tv230y2.js} +2 -2
  53. package/dist/canvas/chunks/gitGraph-TEB2WS4Q-macbhand.js +1 -0
  54. package/dist/canvas/chunks/{gitGraphDiagram-DS77QQ5N-vqqy6p1b.js → gitGraphDiagram-DS77QQ5N-mqgmnw9g.js} +1 -1
  55. package/dist/canvas/chunks/{index-wgv7en21.js → index-037z5dz2.js} +2 -2
  56. package/dist/canvas/chunks/{index-w2mra17t.js → index-081n3har.js} +1 -1
  57. package/dist/canvas/chunks/{index-353m7b0p.js → index-5n03dmb9.js} +1 -1
  58. package/dist/canvas/chunks/{index-yw8h9vha.js → index-60pgzdqe.js} +1 -1
  59. package/dist/canvas/chunks/index-8g1vb57n.js +2 -0
  60. package/dist/canvas/chunks/{index-vv56h019.js → index-8rjes9r6.js} +1 -1
  61. package/dist/canvas/chunks/{index-nprm96xp.js → index-9022d1n9.js} +1 -1
  62. package/dist/canvas/chunks/{index-194m3hc3.js → index-9b02042t.js} +1 -1
  63. package/dist/canvas/chunks/{index-0rk4gp1g.js → index-ap4q4vez.js} +1 -1
  64. package/dist/canvas/chunks/{index-rh7nv68n.js → index-dyp2nhd3.js} +1 -1
  65. package/dist/canvas/chunks/index-frvta4tm.js +2 -0
  66. package/dist/canvas/chunks/{index-s4j678gj.js → index-h9ycj8n2.js} +1 -1
  67. package/dist/canvas/chunks/{index-fjtdggjn.js → index-mergmj97.js} +2 -2
  68. package/dist/canvas/chunks/index-nwsya6dj.js +301 -0
  69. package/dist/canvas/chunks/{index-3cy1bzwh.js → index-nz8qbd1p.js} +1 -1
  70. package/dist/canvas/chunks/{index-d3b3gqe9.js → index-qhfrazv3.js} +1 -1
  71. package/dist/canvas/chunks/{index-6qmsnxwy.js → index-v119nznk.js} +4 -4
  72. package/dist/canvas/chunks/{index-r2fyc9w1.js → index-vpt37m3d.js} +6 -6
  73. package/dist/canvas/chunks/{index-qj8fxwsf.js → index-y9ma6azy.js} +1 -1
  74. package/dist/canvas/chunks/{index-tb1wf525.js → index-zx0j3a2z.js} +26 -26
  75. package/dist/canvas/chunks/info-DKCQHKI2-a0ykzs9z.js +1 -0
  76. package/dist/canvas/chunks/{infoDiagram-6WML65LV-v1yvggqj.js → infoDiagram-6WML65LV-qv97qq6a.js} +2 -2
  77. package/dist/canvas/chunks/ishikawaDiagram-WSZJBQD7-p9306gh0.js +70 -0
  78. package/dist/canvas/chunks/{journeyDiagram-NVQOT4AX-zjcffveh.js → journeyDiagram-NVQOT4AX-sv67zats.js} +5 -5
  79. package/dist/canvas/chunks/{kanban-definition-27J2QSJJ-dakqtfp1.js → kanban-definition-27J2QSJJ-k2pfam6p.js} +1 -1
  80. package/dist/canvas/chunks/{mermaid.core-j2geswrd.js → mermaid.core-83r0fdce.js} +4 -4
  81. package/dist/canvas/chunks/{mindmap-definition-FAOFIHXS-142xhr3k.js → mindmap-definition-FAOFIHXS-vg2newm1.js} +1 -1
  82. package/dist/canvas/chunks/packet-7NZHBO7P-tqnabcdv.js +1 -0
  83. package/dist/canvas/chunks/{pegDiagram-VL7TDLO6-5wvk7vsd.js → pegDiagram-VL7TDLO6-k2h7zc5n.js} +1 -1
  84. package/dist/canvas/chunks/pie-RZYD4A2V-wke6gyhe.js +1 -0
  85. package/dist/canvas/chunks/{pieDiagram-7S7Q4E2Y-ztdhwycc.js → pieDiagram-7S7Q4E2Y-hg169p1v.js} +2 -2
  86. package/dist/canvas/chunks/{quadrantDiagram-CIZ2JOQS-c5p9gmg6.js → quadrantDiagram-CIZ2JOQS-bxtvsq0b.js} +5 -5
  87. package/dist/canvas/chunks/radar-I7S5WNFK-w7ka0drw.js +1 -0
  88. package/dist/canvas/chunks/railroad-3IZDKUUU-y3vg318x.js +1 -0
  89. package/dist/canvas/chunks/railroad-abnf-AHOZXSZD-6hqvcz3c.js +1 -0
  90. package/dist/canvas/chunks/railroad-ebnf-EBAXGLYW-vcae260m.js +1 -0
  91. package/dist/canvas/chunks/railroad-peg-LSFZ7HO6-0dbyme23.js +1 -0
  92. package/dist/canvas/chunks/{railroadDiagram-AXF67PYL-xkmqkjwf.js → railroadDiagram-AXF67PYL-njyhcp4p.js} +1 -1
  93. package/dist/canvas/chunks/{requirementDiagram-LRYGKXZP-9wm2dyaw.js → requirementDiagram-LRYGKXZP-2z6v09gm.js} +4 -4
  94. package/dist/canvas/chunks/{sankeyDiagram-W5VNT64P-2w19etgb.js → sankeyDiagram-W5VNT64P-15mzam0e.js} +1 -1
  95. package/dist/canvas/chunks/{sequenceDiagram-SI44F4Z6-0jn0vwmz.js → sequenceDiagram-SI44F4Z6-rbshyd2c.js} +12 -12
  96. package/dist/canvas/chunks/{sizeCapture-X5ZJPWSS-x75epwdq.js → sizeCapture-X5ZJPWSS-sg26xwts.js} +1 -1
  97. package/dist/canvas/chunks/{stateDiagram-OKZ733FA-schjpy6d.js → stateDiagram-OKZ733FA-6eahp98e.js} +1 -1
  98. package/dist/canvas/chunks/stateDiagram-v2-UEYNNEHI-tty0ggn5.js +1 -0
  99. package/dist/canvas/chunks/{swimlanes-SLNWSIFB-gkw4xce3.js → swimlanes-SLNWSIFB-ze5db10t.js} +1 -1
  100. package/dist/canvas/chunks/swimlanesDiagram-ULZ7WXOC-thze75gq.js +8 -0
  101. package/dist/canvas/chunks/{timeline-definition-Z64GVDOM-x7nkcy01.js → timeline-definition-Z64GVDOM-vnp7jyy8.js} +3 -3
  102. package/dist/canvas/chunks/treeView-QDETBFTQ-6ysffnm6.js +1 -0
  103. package/dist/canvas/chunks/treemap-6X3UGDF4-m3h9p066.js +1 -0
  104. package/dist/canvas/chunks/vennDiagram-T6HMQDX7-0qrnb7mj.js +34 -0
  105. package/dist/canvas/chunks/wardley-OPB4EBWU-dp37drwx.js +1 -0
  106. package/dist/canvas/chunks/{wardleyDiagram-T6FBY63Y-t1j52t9r.js → wardleyDiagram-T6FBY63Y-8nxg8wqt.js} +4 -4
  107. package/dist/canvas/chunks/{xychartDiagram-ELKLHX3M-38t16pme.js → xychartDiagram-ELKLHX3M-nj921e7s.js} +5 -5
  108. package/dist/canvas/global.css +94 -1
  109. package/dist/canvas/index.js +154 -145
  110. package/dist/canvas/mcp-app.html +600 -498
  111. package/dist/json-render/index.css +1 -1
  112. package/dist/types/client/canvas/BoardMoveDialog.d.ts +2 -0
  113. package/dist/types/client/canvas/EdgeEditor.d.ts +19 -0
  114. package/dist/types/client/canvas/GroupNavigation.d.ts +2 -0
  115. package/dist/types/client/canvas/TextPrompt.d.ts +4 -0
  116. package/dist/types/client/nodes/PromptNode.d.ts +1 -0
  117. package/dist/types/client/nodes/ViewerFrame.d.ts +1 -1
  118. package/dist/types/client/nodes/WorkCard.d.ts +7 -0
  119. package/dist/types/client/nodes/use-ax-surface-bridge.d.ts +1 -0
  120. package/dist/types/client/state/canvas-store.d.ts +15 -0
  121. package/dist/types/client/state/human-store.d.ts +2 -0
  122. package/dist/types/client/state/intent-bridge.d.ts +4 -2
  123. package/dist/types/client/state/relation-store.d.ts +11 -0
  124. package/dist/types/client/types.d.ts +1 -1
  125. package/dist/types/json-render/catalog.d.ts +2 -2
  126. package/dist/types/server/agent-presence.d.ts +1 -0
  127. package/dist/types/server/ax-interaction.d.ts +1 -0
  128. package/dist/types/server/ax-state-manager.d.ts +10 -2
  129. package/dist/types/server/board-local.d.ts +4 -0
  130. package/dist/types/server/board-move.d.ts +38 -0
  131. package/dist/types/server/canvas-db.d.ts +12 -2
  132. package/dist/types/server/canvas-operations.d.ts +5 -6
  133. package/dist/types/server/canvas-provenance.d.ts +1 -1
  134. package/dist/types/server/canvas-serialization.d.ts +1 -0
  135. package/dist/types/server/canvas-state.d.ts +84 -20
  136. package/dist/types/server/card-relocation.d.ts +6 -0
  137. package/dist/types/server/context-reads.d.ts +3 -1
  138. package/dist/types/server/human-presence.d.ts +1 -1
  139. package/dist/types/server/index.d.ts +16 -5
  140. package/dist/types/server/intent-registry.d.ts +8 -4
  141. package/dist/types/server/knowledge-lifecycle.d.ts +4 -2
  142. package/dist/types/server/mutation-history.d.ts +7 -5
  143. package/dist/types/server/operations/registry.d.ts +2 -0
  144. package/dist/types/server/trace-manager.d.ts +1 -0
  145. package/dist/types/shared/ax-kinds.d.ts +6 -0
  146. package/dist/types/shared/ax-surface-protocol.d.ts +8 -0
  147. package/dist/types/shared/human-presence.d.ts +1 -0
  148. package/dist/types/shared/lifecycle-status.d.ts +2 -0
  149. package/docs/RELEASE.md +21 -14
  150. package/docs/agent-plugin.md +22 -2
  151. package/docs/amp-plugin.md +270 -0
  152. package/docs/cli.md +42 -3
  153. package/docs/design/GuestName.dc.html +50 -0
  154. package/docs/design/PluginLogo.svg +7 -0
  155. package/docs/design/WorkCards.dc.html +39 -0
  156. package/docs/design/canvas.json +16 -0
  157. package/docs/design/plugin-logo.png +0 -0
  158. package/docs/design.md +111 -8
  159. package/docs/evals/agents-md-sections.md +38 -0
  160. package/docs/http-api.md +128 -10
  161. package/docs/mcp.md +61 -9
  162. package/docs/node-types.md +71 -1
  163. package/docs/plans/plan-009-tech-debt-backlog.md +1 -1
  164. package/docs/plans/plan-019-post-0.9-roadmap.md +44 -20
  165. package/docs/plans/plan-020-wave-5-work-planning.md +553 -0
  166. package/docs/product-vision-2026-09.md +33 -17
  167. package/docs/sdk.md +18 -0
  168. package/package.json +6 -3
  169. package/plugins/pmx-canvas/assets/preview.png +0 -0
  170. package/plugins/pmx-canvas/com.github.copilot/extensions/pmx-canvas/extension.mjs +4 -1
  171. package/plugins/pmx-canvas/com.github.copilot/extensions/pmx-canvas/runtime.json +1 -1
  172. package/plugins/pmx-canvas/plugin.json +2 -2
  173. package/plugins/pmx-canvas/runtime.json +1 -1
  174. package/plugins/pmx-canvas/tools.json +440 -18
  175. package/skills/data-analysis/SKILL.md +13 -26
  176. package/skills/frontend-design/LICENSE.txt +177 -0
  177. package/skills/frontend-design/SKILL.md +3 -0
  178. package/skills/pmx-canvas/SKILL.md +248 -842
  179. package/skills/pmx-canvas/evals/evals.json +110 -5
  180. package/skills/pmx-canvas/references/full-reference.md +142 -28
  181. package/skills/pmx-canvas/references/html-primitives.md +7 -0
  182. package/skills/pmx-canvas/references/installing-pmx-canvas.md +61 -11
  183. package/skills/pmx-canvas/references/tours-and-recording.md +39 -6
  184. package/skills/pmx-canvas/references/workbench-workflows.md +908 -0
  185. package/skills/pmx-canvas-testing/SKILL.md +7 -5
  186. package/skills/published-consumer-e2e/SKILL.md +25 -8
  187. package/skills/published-consumer-e2e/scripts/run-published-consumer-e2e.sh +51 -75
  188. package/skills/web-artifacts-builder/LICENSE.txt +202 -0
  189. package/skills/web-artifacts-builder/SKILL.md +6 -0
  190. package/skills/web-artifacts-builder/scripts/bundle-artifact.sh +2 -2
  191. package/skills/web-artifacts-builder/scripts/init-artifact.sh +8 -8
  192. package/src/cli/commands/apps.ts +1 -0
  193. package/src/cli/commands/boards.ts +30 -0
  194. package/src/client/App.tsx +20 -4
  195. package/src/client/canvas/AttentionHistory.tsx +10 -2
  196. package/src/client/canvas/BoardMoveDialog.tsx +225 -0
  197. package/src/client/canvas/CanvasNode.tsx +45 -2
  198. package/src/client/canvas/CanvasViewport.tsx +38 -9
  199. package/src/client/canvas/ContextMenu.tsx +34 -12
  200. package/src/client/canvas/EdgeEditor.tsx +149 -0
  201. package/src/client/canvas/EdgeLayer.tsx +87 -16
  202. package/src/client/canvas/ExpandedNodeOverlay.tsx +4 -0
  203. package/src/client/canvas/GroupNavigation.tsx +85 -0
  204. package/src/client/canvas/RelationsPanel.tsx +9 -0
  205. package/src/client/canvas/SelectionBar.tsx +21 -0
  206. package/src/client/canvas/SessionPanel.tsx +35 -1
  207. package/src/client/canvas/TextPrompt.tsx +18 -1
  208. package/src/client/canvas/TopBar.tsx +30 -0
  209. package/src/client/canvas/canvas-area.ts +1 -1
  210. package/src/client/nodes/ExtAppFrame.tsx +26 -10
  211. package/src/client/nodes/MarkdownNode.tsx +6 -7
  212. package/src/client/nodes/PromptNode.tsx +32 -3
  213. package/src/client/nodes/StatusNode.tsx +12 -0
  214. package/src/client/nodes/StatusSummary.tsx +11 -0
  215. package/src/client/nodes/ViewerFrame.tsx +21 -10
  216. package/src/client/nodes/WorkCard.tsx +175 -0
  217. package/src/client/nodes/use-ax-surface-bridge.ts +18 -14
  218. package/src/client/state/attention-bridge.ts +5 -0
  219. package/src/client/state/attention-store.ts +1 -0
  220. package/src/client/state/canvas-store.ts +185 -15
  221. package/src/client/state/human-store.ts +22 -2
  222. package/src/client/state/intent-bridge.ts +19 -5
  223. package/src/client/state/relation-store.ts +127 -1
  224. package/src/client/theme/global.css +94 -1
  225. package/src/client/types.ts +1 -0
  226. package/src/mcp/server.ts +13 -3
  227. package/src/server/agent-presence.ts +43 -23
  228. package/src/server/ax-flow-loop.ts +6 -0
  229. package/src/server/ax-gate-ttl.ts +8 -1
  230. package/src/server/ax-interaction.ts +16 -10
  231. package/src/server/ax-state-manager.ts +17 -4
  232. package/src/server/ax-wait.ts +20 -6
  233. package/src/server/board-export.ts +19 -6
  234. package/src/server/board-local.ts +20 -0
  235. package/src/server/board-move.ts +297 -0
  236. package/src/server/canvas-db.ts +262 -160
  237. package/src/server/canvas-operations.ts +139 -109
  238. package/src/server/canvas-schema.ts +21 -0
  239. package/src/server/canvas-serialization.ts +2 -0
  240. package/src/server/canvas-state.ts +792 -159
  241. package/src/server/card-relocation.ts +53 -0
  242. package/src/server/code-graph.ts +4 -3
  243. package/src/server/context-reads.ts +83 -55
  244. package/src/server/demo-state.json +35 -15
  245. package/src/server/file-watcher.ts +30 -10
  246. package/src/server/human-presence.ts +18 -5
  247. package/src/server/index.ts +35 -15
  248. package/src/server/intent-registry.ts +43 -5
  249. package/src/server/knowledge-lifecycle.ts +32 -9
  250. package/src/server/lifecycle-status.ts +29 -1
  251. package/src/server/mcp-app-runtime.ts +26 -7
  252. package/src/server/mutation-history.ts +37 -8
  253. package/src/server/operations/composites.ts +6 -3
  254. package/src/server/operations/mcp-contracts.ts +15 -0
  255. package/src/server/operations/mcp.ts +36 -9
  256. package/src/server/operations/ops/annotation.ts +22 -1
  257. package/src/server/operations/ops/ax-await.ts +1 -0
  258. package/src/server/operations/ops/ax-timeline.ts +28 -2
  259. package/src/server/operations/ops/batch.ts +25 -11
  260. package/src/server/operations/ops/boards.ts +44 -3
  261. package/src/server/operations/ops/nodes.ts +70 -0
  262. package/src/server/operations/ops/query.ts +32 -3
  263. package/src/server/operations/ops/snapshots.ts +1 -0
  264. package/src/server/operations/registry.ts +49 -4
  265. package/src/server/server.ts +62 -16
  266. package/src/server/tour-control.ts +37 -12
  267. package/src/server/trace-manager.ts +4 -0
  268. package/src/server/web-artifacts/scripts/bundle-artifact.sh +2 -2
  269. package/src/server/web-artifacts/scripts/init-artifact.sh +8 -8
  270. package/src/shared/agent-context.ts +7 -1
  271. package/src/shared/auto-arrange.ts +5 -4
  272. package/src/shared/ax-kinds.ts +13 -0
  273. package/src/shared/ax-surface-protocol.ts +22 -0
  274. package/src/shared/human-presence.ts +1 -0
  275. package/src/shared/lifecycle-status.ts +2 -0
  276. package/dist/canvas/chunks/architecture-TIHT7OUA-9tffvpsv.js +0 -1
  277. package/dist/canvas/chunks/classDiagram-JCYQIIEL-nc6g5x1r.js +0 -1
  278. package/dist/canvas/chunks/classDiagram-v2-OCEON4UE-0qnbpwvh.js +0 -1
  279. package/dist/canvas/chunks/cynefin-VYW2F7L2-ys8p46ts.js +0 -1
  280. package/dist/canvas/chunks/eventmodeling-45OFAUF4-v9q6dn4c.js +0 -1
  281. package/dist/canvas/chunks/flowDiagram-UKHOOZJN-yrr5z8tc.js +0 -1
  282. package/dist/canvas/chunks/gitGraph-TEB2WS4Q-kdwb8m0a.js +0 -1
  283. package/dist/canvas/chunks/index-1r72hdzb.js +0 -301
  284. package/dist/canvas/chunks/index-g3pwnqeb.js +0 -2
  285. package/dist/canvas/chunks/index-rft2hcz5.js +0 -2
  286. package/dist/canvas/chunks/info-DKCQHKI2-wpzs6sz3.js +0 -1
  287. package/dist/canvas/chunks/ishikawaDiagram-WSZJBQD7-5hnq1a9p.js +0 -70
  288. package/dist/canvas/chunks/packet-7NZHBO7P-xn439f0s.js +0 -1
  289. package/dist/canvas/chunks/pie-RZYD4A2V-0kf16rwh.js +0 -1
  290. package/dist/canvas/chunks/radar-I7S5WNFK-0g2pz36t.js +0 -1
  291. package/dist/canvas/chunks/railroad-3IZDKUUU-fcaran6j.js +0 -1
  292. package/dist/canvas/chunks/railroad-abnf-AHOZXSZD-wgdya41q.js +0 -1
  293. package/dist/canvas/chunks/railroad-ebnf-EBAXGLYW-gy07a4ka.js +0 -1
  294. package/dist/canvas/chunks/railroad-peg-LSFZ7HO6-ewk6wtkh.js +0 -1
  295. package/dist/canvas/chunks/stateDiagram-v2-UEYNNEHI-k8sfp2e7.js +0 -1
  296. package/dist/canvas/chunks/swimlanesDiagram-ULZ7WXOC-nqysw67j.js +0 -8
  297. package/dist/canvas/chunks/treeView-QDETBFTQ-cesw6gp0.js +0 -1
  298. package/dist/canvas/chunks/treemap-6X3UGDF4-zdv4knp9.js +0 -1
  299. package/dist/canvas/chunks/vennDiagram-T6HMQDX7-x8dqn9yf.js +0 -34
  300. package/dist/canvas/chunks/wardley-OPB4EBWU-44pdddez.js +0 -1
@@ -78,10 +78,10 @@ import { validateLocalImageFile } from './image-source.js';
78
78
  import {
79
79
  addCanvasNode,
80
80
  cancelCodeGraphRecompute,
81
- primeCanvasRuntimeBackends,
82
81
  setCanvasLayoutUpdateEmitter,
83
- syncCanvasRuntimeBackends,
82
+ startBoardRuntime,
84
83
  } from './canvas-operations.js';
84
+ import { createBoardLocal } from './board-local.js';
85
85
  import { MAX_ATTACHMENT_BYTES, MAX_ATTACHMENT_NAME_LENGTH } from './document-import.js';
86
86
  import { dispatchOperationRoute, setOperationEventEmitter } from './operations/index.js';
87
87
  import { intentRegistry } from './intent-registry.js';
@@ -105,7 +105,10 @@ const DEFAULT_PORT = 4313;
105
105
 
106
106
  let server: ReturnType<typeof Bun.serve> | null = null;
107
107
  let activeWorkspaceRoot = resolve(process.cwd());
108
- let primaryWorkbenchPath: string | null = null;
108
+ const boardReplay = createBoardLocal(() => ({
109
+ path: null as string | null,
110
+ contextCards: null as Record<string, unknown> | null,
111
+ }));
109
112
  let primaryWorkbenchSessionId = `pmx-${Date.now().toString(36)}`;
110
113
  let nextWorkbenchEventId = 1;
111
114
  let nextWorkbenchSubscriberId = 1;
@@ -113,7 +116,6 @@ const workbenchSubscribers = new Map<number, ReadableStreamDefaultController<Uin
113
116
  const textEncoder = new TextEncoder();
114
117
  let primaryWorkbenchAutoOpenEnabled = true;
115
118
  const initialCanvasThemeSetting = normalizeCanvasTheme(process.env.PMX_CANVAS_THEME);
116
- let lastWorkbenchContextCardsEnvelope: Record<string, unknown> | null = null;
117
119
 
118
120
  // Operation-registry SSE wiring (plan-005): the registry never imports this
119
121
  // module — the workbench event emitter is injected here, mirroring the
@@ -941,6 +943,21 @@ export function onWorkbenchEvent(listener: (event: string) => void): () => void
941
943
  }
942
944
 
943
945
  function broadcastWorkbenchEvent(event: string, payload: PrimaryWorkbenchEventPayload): void {
946
+ if (canvasState.isBackgroundBoard) {
947
+ if (event === 'canvas-layout-update' || event === 'boards-changed')
948
+ canvasState.withVisibleBoard(() => broadcastWorkbenchEvent('boards-changed', boardsPayload()));
949
+ else if (event === 'ax-state-changed') {
950
+ const ownerBoardId = canvasState.activeBoardId;
951
+ canvasState.withVisibleBoard(() => {
952
+ const layout = canvasState.getLayout();
953
+ if (layout.nodes.some((node) => node.type === 'status' && node.data.workItemBoardId === ownerBoardId))
954
+ broadcastWorkbenchEvent('canvas-layout-update', { layout });
955
+ });
956
+ } else if (event === 'agent-presence')
957
+ canvasState.withVisibleBoard(() => broadcastWorkbenchEvent(event, { ...payload, ...agentPresence.snapshot() }));
958
+ return;
959
+ }
960
+ payload = { ...payload, boardId: canvasState.visibleBoardId };
944
961
  let remoteEdgesChanged = false;
945
962
  if (event === 'canvas-layout-update') {
946
963
  // Remote footer titles come from the catalog. Refresh it on endpoint changes
@@ -960,7 +977,7 @@ function broadcastWorkbenchEvent(event: string, payload: PrimaryWorkbenchEventPa
960
977
  payload = {
961
978
  ...payload,
962
979
  catalogEpoch: boardCatalogEpoch,
963
- boardGeneration: canvasState.boardGeneration,
980
+ boardGeneration: canvasState.visibleBoardGeneration,
964
981
  boardId: canvasState.activeBoardId,
965
982
  };
966
983
  }
@@ -990,8 +1007,8 @@ function broadcastWorkbenchEvent(event: string, payload: PrimaryWorkbenchEventPa
990
1007
 
991
1008
  function setPrimaryWorkbenchPath(safePath: string, source: string): void {
992
1009
  const resolved = resolve(safePath);
993
- if (primaryWorkbenchPath === resolved) return;
994
- primaryWorkbenchPath = resolved;
1010
+ if (boardReplay.current.path === resolved) return;
1011
+ boardReplay.current.path = resolved;
995
1012
  broadcastWorkbenchEvent('workbench-open', {
996
1013
  path: resolved,
997
1014
  title: basename(resolved),
@@ -2073,6 +2090,7 @@ function handleRead(pathLike: string): Response {
2073
2090
 
2074
2091
  function handleWorkbenchState(): Response {
2075
2092
  const mcpAppHost = getMcpAppHostSnapshot();
2093
+ const primaryWorkbenchPath = boardReplay.current.path;
2076
2094
  if (!primaryWorkbenchPath) {
2077
2095
  return responseJson({
2078
2096
  sessionId: primaryWorkbenchSessionId,
@@ -2085,7 +2103,7 @@ function handleWorkbenchState(): Response {
2085
2103
 
2086
2104
  const safePath = resolveWorkspaceMarkdownPath(primaryWorkbenchPath);
2087
2105
  if (!safePath || !existsSync(safePath)) {
2088
- primaryWorkbenchPath = null;
2106
+ boardReplay.current.path = null;
2089
2107
  return responseJson({
2090
2108
  sessionId: primaryWorkbenchSessionId,
2091
2109
  path: null,
@@ -2202,6 +2220,7 @@ async function handleWorkbenchIntent(req: Request): Promise<Response> {
2202
2220
  function buildWorkbenchConnectSnapshot(
2203
2221
  requestedSessionId: string,
2204
2222
  ): Array<{ event: string; payload: Record<string, unknown> }> {
2223
+ const { path: primaryWorkbenchPath, contextCards: lastWorkbenchContextCardsEnvelope } = boardReplay.current;
2205
2224
  const continuity =
2206
2225
  requestedSessionId.length === 0
2207
2226
  ? 'fresh'
@@ -3311,10 +3330,16 @@ export function emitPrimaryWorkbenchEvent(event: string, payload: PrimaryWorkben
3311
3330
  timestamp: new Date().toISOString(),
3312
3331
  };
3313
3332
  if (event === 'context-cards') {
3314
- lastWorkbenchContextCardsEnvelope = { ...envelope };
3333
+ boardReplay.current.contextCards = { ...envelope };
3315
3334
  }
3316
3335
  syncEventToCanvasState(event, envelope);
3317
- if (primaryWorkbenchAutoOpenEnabled && (event === 'workbench-open' || event === 'ext-app-open')) {
3336
+ // Events can create server state. Apply them to their producer's board before
3337
+ // deciding whether they belong in the human's currently visible projection.
3338
+ if (
3339
+ !canvasState.isBackgroundBoard &&
3340
+ primaryWorkbenchAutoOpenEnabled &&
3341
+ (event === 'workbench-open' || event === 'ext-app-open')
3342
+ ) {
3318
3343
  ensureCanvasBrowserOpen();
3319
3344
  }
3320
3345
  broadcastWorkbenchEvent(event, envelope);
@@ -3401,6 +3426,27 @@ export interface CanvasServerOptions {
3401
3426
  allowExternalMcp?: boolean;
3402
3427
  }
3403
3428
 
3429
+ // SDK/MCP producers can own cards before an HTTP listener starts.
3430
+ canvasState.setMoveRuntimeBlockers(() => {
3431
+ const blockers = new Map<string, string>();
3432
+ for (const id of traceManager.ownedNodeIds) blockers.set(id, 'the trace manager still owns this card');
3433
+ for (const [response, prompt] of serverResponseToThreadMap) {
3434
+ blockers.set(response, 'an active response is routed to this card');
3435
+ blockers.set(prompt, 'an active response is routed to this prompt');
3436
+ }
3437
+ for (const intent of pendingWorkbenchIntents) {
3438
+ if (intent.type !== 'canvas-prompt') continue;
3439
+ for (const id of [
3440
+ intent.payload.nodeId,
3441
+ intent.payload.parentNodeId,
3442
+ ...(Array.isArray(intent.payload.contextNodeIds) ? intent.payload.contextNodeIds : []),
3443
+ ]) {
3444
+ if (typeof id === 'string') blockers.set(id, 'a queued prompt still refers to this card');
3445
+ }
3446
+ }
3447
+ return blockers;
3448
+ });
3449
+
3404
3450
  export function startCanvasServer(options: CanvasServerOptions = {}): string | null {
3405
3451
  if (server) {
3406
3452
  return typeof server.port === 'number' ? loopbackBaseUrl(server.port) : null;
@@ -3447,12 +3493,9 @@ export function startCanvasServer(options: CanvasServerOptions = {}): string | n
3447
3493
  });
3448
3494
  if (loaded) {
3449
3495
  console.log(' Canvas state restored from .pmx-canvas/canvas.db');
3450
- primeCanvasRuntimeBackends({ forceRehydrateExtApps: true });
3451
- const rehydrate = () => syncCanvasRuntimeBackends({ forceRehydrateExtApps: true, alreadyPrimed: true });
3452
- const pending = options.allowExternalMcp === false ? withoutExternalMcp(rehydrate) : rehydrate();
3453
- void pending.finally(() => {
3454
- emitPrimaryWorkbenchEvent('canvas-layout-update', { layout: canvasState.getLayout() });
3455
- });
3496
+ const rehydrate = () => startBoardRuntime({ forceRehydrateExtApps: true });
3497
+ if (options.allowExternalMcp === false) withoutExternalMcp(rehydrate);
3498
+ else rehydrate();
3456
3499
  }
3457
3500
 
3458
3501
  rotatePrimaryWorkbenchSessionIfNeeded();
@@ -3507,6 +3550,9 @@ export function startCanvasServer(options: CanvasServerOptions = {}): string | n
3507
3550
  workspace: activeWorkspaceRoot,
3508
3551
  pid: process.pid,
3509
3552
  version: serverPackageVersion(),
3553
+ // The stamp open tabs reload on, read once per process: after a rebuild it lags
3554
+ // dist/ on disk, and already-open tabs keep old JS until the server restarts.
3555
+ bundleStamp: canvasBundleStamp(),
3510
3556
  contracts: [CANVAS_APP_WRITE_CONTRACT],
3511
3557
  persistence: canvasState.persistenceHealth,
3512
3558
  });
@@ -21,6 +21,7 @@ import {
21
21
  import { boardCatalogEpoch, canvasState } from './canvas-state.js';
22
22
  import { getClientViewportSize } from './canvas-operations.js';
23
23
  import { OperationError } from './operations/types.js';
24
+ import { createBoardLocal } from './board-local.js';
24
25
 
25
26
  export type TourStep = number | 'next' | 'previous';
26
27
 
@@ -46,19 +47,28 @@ export interface TourState {
46
47
  position: number | null;
47
48
  }
48
49
 
49
- let cursor: { boardGeneration: number; tour: string; index: number } | null = null;
50
+ const boardTour = createBoardLocal(() => ({
51
+ cursor: null as { boardGeneration: number; viewGeneration: number; tour: string; index: number } | null,
52
+ presenterGeneration: -1,
53
+ presenterIntents: new Map<string, number>(),
54
+ }));
50
55
  // One order for both HTTP acknowledgements and event delivery in this server run.
51
56
  let sequence = 0;
52
- let presenterGeneration = -1;
53
- const presenterIntents = new Map<string, number>();
54
57
 
55
58
  function claimPresenter(presenter: TourPresenter | undefined): boolean {
56
59
  if (presenter === undefined) return true;
60
+ const state = boardTour.current;
61
+ const { presenterIntents } = state;
57
62
  const { clientId, intent, catalogEpoch, boardGeneration } = tourPresenterSchema.parse(presenter);
58
- if (catalogEpoch !== boardCatalogEpoch || boardGeneration !== canvasState.boardGeneration) return false;
59
- if (presenterGeneration !== boardGeneration) {
63
+ if (
64
+ canvasState.isBackgroundBoard ||
65
+ catalogEpoch !== boardCatalogEpoch ||
66
+ boardGeneration !== canvasState.visibleBoardGeneration
67
+ )
68
+ return false;
69
+ if (state.presenterGeneration !== boardGeneration) {
60
70
  presenterIntents.clear();
61
- presenterGeneration = boardGeneration;
71
+ state.presenterGeneration = boardGeneration;
62
72
  }
63
73
  const previous = presenterIntents.get(clientId);
64
74
  if (previous !== undefined && intent <= previous) return false;
@@ -74,7 +84,11 @@ function claimPresenter(presenter: TourPresenter | undefined): boolean {
74
84
  }
75
85
 
76
86
  function nextDelivery(): TourDelivery {
77
- return { catalogEpoch: boardCatalogEpoch, boardGeneration: canvasState.boardGeneration, sequence: ++sequence };
87
+ return {
88
+ catalogEpoch: boardCatalogEpoch,
89
+ boardGeneration: canvasState.isBackgroundBoard ? canvasState.boardGeneration : canvasState.visibleBoardGeneration,
90
+ sequence: ++sequence,
91
+ };
78
92
  }
79
93
 
80
94
  export function currentTour(): TourState {
@@ -85,10 +99,16 @@ export function currentTour(): TourState {
85
99
 
86
100
  /** The stop the tour is on for the active board, or null when not touring. */
87
101
  function tourPosition(tour: Tour): number | null {
88
- if (cursor && (cursor.boardGeneration !== canvasState.boardGeneration || cursor.tour !== JSON.stringify(tour))) {
89
- cursor = null;
102
+ const { cursor } = boardTour.current;
103
+ if (
104
+ cursor &&
105
+ (cursor.boardGeneration !== canvasState.boardLifetimeGeneration ||
106
+ (!canvasState.isBackgroundBoard && cursor.viewGeneration !== canvasState.visibleBoardGeneration) ||
107
+ cursor.tour !== JSON.stringify(tour))
108
+ ) {
109
+ boardTour.current.cursor = null;
90
110
  }
91
- return cursor?.index ?? null;
111
+ return boardTour.current.cursor?.index ?? null;
92
112
  }
93
113
 
94
114
  /** Move the shared cursor. `next`/`previous` clamp at the ends; an explicit index must exist. */
@@ -106,7 +126,12 @@ export function goToTourStop(step: TourStep, presenter?: TourPresenter): TourSte
106
126
  else if (step === 'previous') index = at === null ? 0 : Math.max(0, Math.min(stops.length - 1, at - 1));
107
127
  else if (Number.isInteger(step) && step >= 0 && step < stops.length) index = step;
108
128
  else throw new OperationError(`Tour stop ${step} does not exist (stops 0–${stops.length - 1}).`, 400);
109
- cursor = { boardGeneration: canvasState.boardGeneration, tour: JSON.stringify(tour), index };
129
+ boardTour.current.cursor = {
130
+ boardGeneration: canvasState.boardLifetimeGeneration,
131
+ viewGeneration: canvasState.visibleBoardGeneration,
132
+ tour: JSON.stringify(tour),
133
+ index,
134
+ };
110
135
  return {
111
136
  ...nextDelivery(),
112
137
  index,
@@ -119,7 +144,7 @@ export function exitTour(): TourDelivery;
119
144
  export function exitTour(presenter: TourPresenter | undefined): TourDelivery | TourSuperseded;
120
145
  export function exitTour(presenter?: TourPresenter): TourDelivery | TourSuperseded {
121
146
  if (!claimPresenter(presenter)) return { superseded: true };
122
- cursor = null;
147
+ boardTour.current.cursor = null;
123
148
  return nextDelivery();
124
149
  }
125
150
 
@@ -72,6 +72,10 @@ class TraceManager {
72
72
  return this._enabled;
73
73
  }
74
74
 
75
+ get ownedNodeIds(): readonly string[] {
76
+ return this.traceNodeIds;
77
+ }
78
+
75
79
  setEnabled(value: boolean): void {
76
80
  this._enabled = value;
77
81
  if (value) {
@@ -68,7 +68,7 @@ function run_with_filtered_stderr() {
68
68
  }
69
69
 
70
70
  function run_pnpm_quiet() {
71
- run_with_filtered_stderr "${PNPM_CMD[@]}" --silent "$@"
71
+ run_with_filtered_stderr "${PNPM_CMD[@]}" --reporter=append-only "$@"
72
72
  }
73
73
 
74
74
  function run_pnpm_allow_build() {
@@ -77,7 +77,7 @@ function run_pnpm_allow_build() {
77
77
  for package_name in "${ALLOWED_BUILD_PACKAGES[@]}"; do
78
78
  allow_build_args+=(--allow-build="$package_name")
79
79
  done
80
- run_with_filtered_stderr "${PNPM_CMD[@]}" --silent "$@" "${allow_build_args[@]}"
80
+ run_with_filtered_stderr "${PNPM_CMD[@]}" --reporter=append-only "$@" "${allow_build_args[@]}"
81
81
  }
82
82
 
83
83
  function package_has_dependency() {
@@ -70,21 +70,21 @@ function replay_filtered_stderr() {
70
70
 
71
71
  function run_with_filtered_stderr() {
72
72
  local stderr_file
73
+ local status
73
74
  stderr_file="$(mktemp)"
74
75
  if "$@" 2>"$stderr_file"; then
75
- replay_filtered_stderr "$stderr_file"
76
- rm -f "$stderr_file"
77
- return 0
76
+ status=0
77
+ else
78
+ status=$?
78
79
  fi
79
80
 
80
- local status=$?
81
81
  replay_filtered_stderr "$stderr_file"
82
82
  rm -f "$stderr_file"
83
83
  return "$status"
84
84
  }
85
85
 
86
86
  function run_pnpm_quiet() {
87
- run_with_filtered_stderr "${PNPM_CMD[@]}" --silent "$@"
87
+ run_with_filtered_stderr "${PNPM_CMD[@]}" --reporter=append-only "$@"
88
88
  }
89
89
 
90
90
  function run_pnpm_allow_build() {
@@ -93,7 +93,7 @@ function run_pnpm_allow_build() {
93
93
  for package_name in "${ALLOWED_BUILD_PACKAGES[@]}"; do
94
94
  allow_build_args+=(--allow-build="$package_name")
95
95
  done
96
- run_with_filtered_stderr "${PNPM_CMD[@]}" --silent "$@" "${allow_build_args[@]}"
96
+ run_with_filtered_stderr "${PNPM_CMD[@]}" --reporter=append-only "$@" "${allow_build_args[@]}"
97
97
  }
98
98
 
99
99
  RUNTIME_INFO="$(detect_runtime_major)"
@@ -146,8 +146,8 @@ fi
146
146
 
147
147
  echo "🚀 Creating new React + Vite project: $PROJECT_NAME"
148
148
 
149
- # Create new Vite project (always use latest create-vite, pin vite version later)
150
- run_pnpm_quiet create vite "$PROJECT_NAME" --template react-ts --no-interactive
149
+ # 9.3.2 shipped without templates; keep scaffolding on the verified complete package.
150
+ run_pnpm_quiet create vite@9.3.1 "$PROJECT_NAME" --template react-ts --no-interactive
151
151
 
152
152
  # Navigate into project directory
153
153
  cd "$PROJECT_NAME"
@@ -374,8 +374,14 @@ export function summarizeNodeForAgentContext(node: CanvasNodeState, options: Age
374
374
  return truncateContextText(`${prefix}${fileContent}`, defaultTextLength);
375
375
  }
376
376
  case 'status':
377
+ if (typeof node.data.workItemId === 'string') {
378
+ return truncateContextText(
379
+ `Read-only live task: ${node.data.workItemId}\n${node.data.liveWorkAvailable === false ? 'Task unavailable' : textFields(node.data, ['title', 'workState', 'detail', 'liveWorkSource'])}`,
380
+ defaultTextLength,
381
+ );
382
+ }
377
383
  return truncateContextText(
378
- `Status: ${textFields(node.data, ['phase']) || textFields(node.data, ['content']) || textFields(node.data, ['status']) || 'unknown'}\n${textFields(node.data, ['detail', 'message', 'activeTool'])}`,
384
+ `Status: ${textFields(node.data, ['workState']) || textFields(node.data, ['phase']) || textFields(node.data, ['content']) || textFields(node.data, ['status']) || 'unknown'}\n${textFields(node.data, ['detail', 'message', 'activeTool'])}${typeof node.data.progress === 'number' ? `\nProgress: ${node.data.progress}%` : ''}`,
379
385
  defaultTextLength,
380
386
  );
381
387
  case 'context':
@@ -463,10 +463,11 @@ export function computeAutoArrange(
463
463
  const { outgoing, undirected, indegree, outdegree } = buildUnitGraphs(units, nodeToUnit, allEdges);
464
464
  const clusters = collectSpatialClusters(units, undirected);
465
465
  const absoluteUnitPositions = new Map<string, ArrangePosition>();
466
- // Already-packed cluster rects: a cluster that grew past its old bounds is
467
- // shifted below earlier clusters instead of overlapping them. Clusters are
468
- // processed top-left first, so the cascade is deterministic.
469
- const packedRects: Array<ArrangePosition & ArrangeSize> = [];
466
+ // Reserve fixed cards as well as already-packed clusters. A growing cluster
467
+ // shifts below blockers without moving pinned cards or splitting its groups.
468
+ const packedRects: Array<ArrangePosition & ArrangeSize> = allNodes
469
+ .filter((node) => node.pinned)
470
+ .map((node) => ({ ...node.position, ...node.size }));
470
471
 
471
472
  for (const clusterUnits of clusters) {
472
473
  const components = collectComponents(clusterUnits, undirected).map((component) =>
@@ -5,6 +5,19 @@
5
5
  */
6
6
  export type AxWorkItemStatus = 'todo' | 'in-progress' | 'blocked' | 'done' | 'cancelled';
7
7
 
8
+ /** Authored work cards use the task vocabulary without creating an AX task. */
9
+ export const WORK_CARD_STATES: Record<AxWorkItemStatus, { label: string; glyph: string }> = {
10
+ todo: { label: 'To do', glyph: '○' },
11
+ 'in-progress': { label: 'In progress', glyph: '◐' },
12
+ blocked: { label: 'Blocked', glyph: '⧗' },
13
+ done: { label: 'Done', glyph: '✓' },
14
+ cancelled: { label: 'Cancelled', glyph: '×' },
15
+ };
16
+
17
+ export function isWorkCardState(value: unknown): value is AxWorkItemStatus {
18
+ return typeof value === 'string' && Object.hasOwn(WORK_CARD_STATES, value);
19
+ }
20
+
8
21
  /** `held` = auto-held by the unattended-approval policy: the action did NOT proceed. */
9
22
  export type AxApprovalStatus = 'pending' | 'approved' | 'rejected' | 'held';
10
23
 
@@ -20,3 +20,25 @@ export const HTML_SURFACE_PUSH_SOURCE = 'pmx-canvas-html-node';
20
20
 
21
21
  /** Tab-local JSON viewer state handoff, independent of AX capabilities. */
22
22
  export const JSON_VIEWER_STATE_SOURCE = 'pmx-canvas-json-state';
23
+
24
+ /** MCP apps share their window channel with an SDK JSON-RPC transport. */
25
+ export const MCP_SURFACE_METHOD = 'notifications/pmx/surface';
26
+
27
+ export function surfaceNotification(params: Record<string, unknown>) {
28
+ return { jsonrpc: '2.0' as const, method: MCP_SURFACE_METHOD, params };
29
+ }
30
+
31
+ export function readSurfaceNotification(message: unknown): unknown {
32
+ if (
33
+ message &&
34
+ typeof message === 'object' &&
35
+ 'jsonrpc' in message &&
36
+ message.jsonrpc === '2.0' &&
37
+ 'method' in message &&
38
+ message.method === MCP_SURFACE_METHOD &&
39
+ !('id' in message) &&
40
+ 'params' in message
41
+ )
42
+ return message.params;
43
+ return null;
44
+ }
@@ -21,6 +21,7 @@ export interface HumanPresenceSnapshot {
21
21
  humans: HumanPresence[];
22
22
  }
23
23
 
24
+ export const HUMAN_NAME_MAX_LENGTH = 40;
24
25
  /** A tab that stops reporting is gone after this. */
25
26
  export const HUMAN_PRESENCE_TTL_MS = 30_000;
26
27
  /** A grab the tab stops renewing (crash, tab closed mid-drag) releases after this. */
@@ -21,6 +21,8 @@ export interface LifecycleQualification {
21
21
  contentChangedAt: string | null;
22
22
  /** The revisions a validating reviewer must have inspected, qualified by source relation. */
23
23
  observations: Record<string, number | null>;
24
+ /** Warnings keyed by the same qualified source identity as observations. */
25
+ sourceWarnings?: Record<string, string[]>;
24
26
  sources: SourceQualification[];
25
27
  relevance: 'card-pinned' | 'board-pinned' | 'not-selected';
26
28
  }
@@ -1 +0,0 @@
1
- import{ci}from"./index-tb1wf525.js";export{ci as createArchitectureServices};
@@ -1 +0,0 @@
1
- import{e}from"./index-1r72hdzb.js";import"./index-6qmsnxwy.js";import"./index-qj8fxwsf.js";import{Sr,Er,_r,Ar}from"./index-w2mra17t.js";import"./index-nprm96xp.js";import"./index-s4j678gj.js";import"./index-3cy1bzwh.js";var k={parser:Sr,get db(){return new Er},renderer:Ar,styles:_r,init:e((r)=>{if(!r.class)r.class={};r.class.arrowMarkerAbsolute=r.arrowMarkerAbsolute},"init")};export{k as diagram};
@@ -1 +0,0 @@
1
- import{e}from"./index-1r72hdzb.js";import"./index-6qmsnxwy.js";import"./index-qj8fxwsf.js";import{Sr,Er,_r,Ar}from"./index-w2mra17t.js";import"./index-nprm96xp.js";import"./index-s4j678gj.js";import"./index-3cy1bzwh.js";var k={parser:Sr,get db(){return new Er},renderer:Ar,styles:_r,init:e((r)=>{if(!r.class)r.class={};r.class.arrowMarkerAbsolute=r.arrowMarkerAbsolute},"init")};export{k as diagram};
@@ -1 +0,0 @@
1
- import{ni}from"./index-tb1wf525.js";export{ni as createCynefinServices};
@@ -1 +0,0 @@
1
- import{ui}from"./index-tb1wf525.js";export{ui as createEventModelingServices};
@@ -1 +0,0 @@
1
- import"./index-1r72hdzb.js";import"./index-6qmsnxwy.js";import"./index-qj8fxwsf.js";import{qi}from"./index-yw8h9vha.js";import"./index-nprm96xp.js";import"./index-g3pwnqeb.js";import"./index-s4j678gj.js";import"./index-3cy1bzwh.js";export{qi as diagram};
@@ -1 +0,0 @@
1
- import{ii}from"./index-tb1wf525.js";export{ii as createGitGraphServices};