termdock 1.4.309 → 1.4.311

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 (375) hide show
  1. package/README.en.md +3 -1
  2. package/README.md +3 -1
  3. package/THIRD_PARTY_NOTICES.md +30 -0
  4. package/dist/client/assets/{App-ggIA_xqR.js → App-ChS2-lkz.js} +62 -55
  5. package/dist/client/assets/App-ChS2-lkz.js.br +0 -0
  6. package/dist/client/assets/App-ChS2-lkz.js.gz +0 -0
  7. package/dist/client/assets/{ArchitecturePanel-Cmpmp6FS.css → ArchitecturePanel-B_BDrrfR.css} +1 -1
  8. package/dist/client/assets/ArchitecturePanel-B_BDrrfR.css.br +0 -0
  9. package/dist/client/assets/ArchitecturePanel-B_BDrrfR.css.gz +0 -0
  10. package/dist/client/assets/ArchitecturePanel-JtjyyJoW.js +9 -0
  11. package/dist/client/assets/ArchitecturePanel-JtjyyJoW.js.br +0 -0
  12. package/dist/client/assets/ArchitecturePanel-JtjyyJoW.js.gz +0 -0
  13. package/dist/client/assets/{ChangeWalkthroughPanel-D1Puc7B3.js → ChangeWalkthroughPanel-BlQ5-VPp.js} +2 -2
  14. package/dist/client/assets/ChangeWalkthroughPanel-BlQ5-VPp.js.br +0 -0
  15. package/dist/client/assets/ChangeWalkthroughPanel-BlQ5-VPp.js.gz +0 -0
  16. package/dist/client/assets/CollaborationMainWorkspace-aFLAMqDr.js +1 -0
  17. package/dist/client/assets/CollaborationMainWorkspace-aFLAMqDr.js.br +0 -0
  18. package/dist/client/assets/CollaborationMainWorkspace-aFLAMqDr.js.gz +0 -0
  19. package/dist/client/assets/CollaborationTaskContent-BDQMRhU9.js +2 -0
  20. package/dist/client/assets/{ComputerControlView-D5Lw9sNA.js → ComputerControlView-TAKDbBUl.js} +2 -2
  21. package/dist/client/assets/ComputerControlView-TAKDbBUl.js.br +0 -0
  22. package/dist/client/assets/ComputerControlView-TAKDbBUl.js.gz +0 -0
  23. package/dist/client/assets/{DagPlayground-DYJrGfiG.js → DagPlayground-CR4uDFOx.js} +1 -1
  24. package/dist/client/assets/DagPlayground-CR4uDFOx.js.br +0 -0
  25. package/dist/client/assets/DagPlayground-CR4uDFOx.js.gz +0 -0
  26. package/dist/client/assets/{DiffLab-5zdcFW3z.js → DiffLab-BqeHMDOy.js} +1 -1
  27. package/dist/client/assets/DiffLab-BqeHMDOy.js.br +0 -0
  28. package/dist/client/assets/DiffLab-BqeHMDOy.js.gz +0 -0
  29. package/dist/client/assets/{DiffReview-BBBC_NjV.js → DiffReview-DqrOcRfP.js} +1 -1
  30. package/dist/client/assets/DiffReview-DqrOcRfP.js.br +0 -0
  31. package/dist/client/assets/DiffReview-DqrOcRfP.js.gz +0 -0
  32. package/dist/client/assets/{DiffReviewLab-CbhosFSB.js → DiffReviewLab-CEYpbrL6.js} +2 -2
  33. package/dist/client/assets/DiffReviewLab-CEYpbrL6.js.br +0 -0
  34. package/dist/client/assets/DiffReviewLab-CEYpbrL6.js.gz +0 -0
  35. package/dist/client/assets/{DiffViewer-BuQwFQ4V.js → DiffViewer-F-uQSmhG.js} +8 -8
  36. package/dist/client/assets/DiffViewer-F-uQSmhG.js.br +0 -0
  37. package/dist/client/assets/DiffViewer-F-uQSmhG.js.gz +0 -0
  38. package/dist/client/assets/{ModelPreview-nO2VmqdP.js → ModelPreview-KmXFkgij.js} +1 -1
  39. package/dist/client/assets/ModelPreview-KmXFkgij.js.br +0 -0
  40. package/dist/client/assets/ModelPreview-KmXFkgij.js.gz +0 -0
  41. package/dist/client/assets/RightSidebar-VMdXpo4h.js +1677 -0
  42. package/dist/client/assets/RightSidebar-VMdXpo4h.js.br +0 -0
  43. package/dist/client/assets/RightSidebar-VMdXpo4h.js.gz +0 -0
  44. package/dist/client/assets/{abnfDiagram-VCTEODGH-yi0K8GDG.js → abnfDiagram-VCTEODGH-CAMk1C0N.js} +1 -1
  45. package/dist/client/assets/abnfDiagram-VCTEODGH-CAMk1C0N.js.br +0 -0
  46. package/dist/client/assets/abnfDiagram-VCTEODGH-CAMk1C0N.js.gz +0 -0
  47. package/dist/client/assets/{app-B6FdOF6K.js → app-CHxLSuGQ.js} +4 -4
  48. package/dist/client/assets/app-CHxLSuGQ.js.br +0 -0
  49. package/dist/client/assets/app-CHxLSuGQ.js.gz +0 -0
  50. package/dist/client/assets/{arc-_nLI_-XZ.js → arc-CYG_-1vC.js} +1 -1
  51. package/dist/client/assets/arc-CYG_-1vC.js.br +0 -0
  52. package/dist/client/assets/arc-CYG_-1vC.js.gz +0 -0
  53. package/dist/client/assets/{architectureDiagram-5GKGNRK7-CikrA78O.js → architectureDiagram-5GKGNRK7-BqHzezLR.js} +1 -1
  54. package/dist/client/assets/architectureDiagram-5GKGNRK7-BqHzezLR.js.br +0 -0
  55. package/dist/client/assets/architectureDiagram-5GKGNRK7-BqHzezLR.js.gz +0 -0
  56. package/dist/client/assets/{blockDiagram-I7D4REHJ-CWJq6qJ7.js → blockDiagram-I7D4REHJ-D6GWRO_Z.js} +1 -1
  57. package/dist/client/assets/blockDiagram-I7D4REHJ-D6GWRO_Z.js.br +0 -0
  58. package/dist/client/assets/blockDiagram-I7D4REHJ-D6GWRO_Z.js.gz +0 -0
  59. package/dist/client/assets/{c4Diagram-7LVT6UL2-gzPzLGvs.js → c4Diagram-7LVT6UL2-CutmGIGb.js} +1 -1
  60. package/dist/client/assets/c4Diagram-7LVT6UL2-CutmGIGb.js.br +0 -0
  61. package/dist/client/assets/c4Diagram-7LVT6UL2-CutmGIGb.js.gz +0 -0
  62. package/dist/client/assets/channel-B3BKM2gg.js +1 -0
  63. package/dist/client/assets/{chunk-2Q5K7J3B-CfX9l18E.js → chunk-2Q5K7J3B-DwiUpGFu.js} +1 -1
  64. package/dist/client/assets/{chunk-5VM5RSS4-JSV1yrXM.js → chunk-5VM5RSS4-C35gLPSH.js} +1 -1
  65. package/dist/client/assets/{chunk-F27PBJKO-CQ0LXeap.js → chunk-F27PBJKO-CNptP19P.js} +1 -1
  66. package/dist/client/assets/chunk-F27PBJKO-CNptP19P.js.br +0 -0
  67. package/dist/client/assets/chunk-F27PBJKO-CNptP19P.js.gz +0 -0
  68. package/dist/client/assets/{chunk-IMKFNOWR-CJOEPkK9.js → chunk-IMKFNOWR-DHdpB9A0.js} +1 -1
  69. package/dist/client/assets/chunk-IMKFNOWR-DHdpB9A0.js.br +0 -0
  70. package/dist/client/assets/chunk-IMKFNOWR-DHdpB9A0.js.gz +0 -0
  71. package/dist/client/assets/{chunk-JWPE2WC7-Dpp7Xu_E.js → chunk-JWPE2WC7-CrKSOzdE.js} +1 -1
  72. package/dist/client/assets/{chunk-POPQ4Y6H-9hDa1b8z.js → chunk-POPQ4Y6H-CiZGLRSk.js} +1 -1
  73. package/dist/client/assets/{chunk-SVP7TREG-BskkG9gg.js → chunk-SVP7TREG-B70pX8OB.js} +1 -1
  74. package/dist/client/assets/chunk-SVP7TREG-B70pX8OB.js.br +0 -0
  75. package/dist/client/assets/chunk-SVP7TREG-B70pX8OB.js.gz +0 -0
  76. package/dist/client/assets/{chunk-TICWLB2K-DyzuP-9I.js → chunk-TICWLB2K-Ba1mI99F.js} +1 -1
  77. package/dist/client/assets/chunk-TICWLB2K-Ba1mI99F.js.br +0 -0
  78. package/dist/client/assets/chunk-TICWLB2K-Ba1mI99F.js.gz +0 -0
  79. package/dist/client/assets/{chunk-XXDRQBXY-C31_1i6z.js → chunk-XXDRQBXY-DmKIl18h.js} +1 -1
  80. package/dist/client/assets/classDiagram-ZZMXUADV-CS4V_MQS.js +1 -0
  81. package/dist/client/assets/classDiagram-v2-VYDZK3BY-CS4V_MQS.js +1 -0
  82. package/dist/client/assets/{cose-bilkent-JH36ORCC-Bm-ESDOc.js → cose-bilkent-JH36ORCC-C-NMDUHW.js} +1 -1
  83. package/dist/client/assets/cose-bilkent-JH36ORCC-C-NMDUHW.js.br +0 -0
  84. package/dist/client/assets/cose-bilkent-JH36ORCC-C-NMDUHW.js.gz +0 -0
  85. package/dist/client/assets/{cynefin-OW5HDTMX-DbFWAPvX.js → cynefin-OW5HDTMX-CZgEc1ab.js} +1 -1
  86. package/dist/client/assets/cynefin-OW5HDTMX-CZgEc1ab.js.br +0 -0
  87. package/dist/client/assets/cynefin-OW5HDTMX-CZgEc1ab.js.gz +0 -0
  88. package/dist/client/assets/{cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js → cynefinDiagram-5FMLGOSQ-CHQeSNm2.js} +1 -1
  89. package/dist/client/assets/cynefinDiagram-5FMLGOSQ-CHQeSNm2.js.br +0 -0
  90. package/dist/client/assets/cynefinDiagram-5FMLGOSQ-CHQeSNm2.js.gz +0 -0
  91. package/dist/client/assets/{dagre-GXQ25YYZ-D_5uEMjJ.js → dagre-GXQ25YYZ-B_jkMdPS.js} +1 -1
  92. package/dist/client/assets/dagre-GXQ25YYZ-B_jkMdPS.js.br +0 -0
  93. package/dist/client/assets/dagre-GXQ25YYZ-B_jkMdPS.js.gz +0 -0
  94. package/dist/client/assets/{diagram-S7CK7UJ4-DWVpndRP.js → diagram-S7CK7UJ4-nv6Lnsrp.js} +1 -1
  95. package/dist/client/assets/diagram-S7CK7UJ4-nv6Lnsrp.js.br +0 -0
  96. package/dist/client/assets/diagram-S7CK7UJ4-nv6Lnsrp.js.gz +0 -0
  97. package/dist/client/assets/{diagram-UQ7AKVKN-DmYTya3w.js → diagram-UQ7AKVKN-BZf2fzaA.js} +1 -1
  98. package/dist/client/assets/diagram-UQ7AKVKN-BZf2fzaA.js.br +0 -0
  99. package/dist/client/assets/diagram-UQ7AKVKN-BZf2fzaA.js.gz +0 -0
  100. package/dist/client/assets/{diagram-VSXAHHWV-BEA6kqNj.js → diagram-VSXAHHWV-CxL0_BH8.js} +1 -1
  101. package/dist/client/assets/diagram-VSXAHHWV-CxL0_BH8.js.br +0 -0
  102. package/dist/client/assets/diagram-VSXAHHWV-CxL0_BH8.js.gz +0 -0
  103. package/dist/client/assets/{diagram-VX7I27RA-CU9vP0P0.js → diagram-VX7I27RA-Dm9MqpIE.js} +1 -1
  104. package/dist/client/assets/diagram-VX7I27RA-Dm9MqpIE.js.br +0 -0
  105. package/dist/client/assets/diagram-VX7I27RA-Dm9MqpIE.js.gz +0 -0
  106. package/dist/client/assets/{diagram-Z3DM3KII-B_GvE2g-.js → diagram-Z3DM3KII-BIfTa7P5.js} +1 -1
  107. package/dist/client/assets/diagram-Z3DM3KII-BIfTa7P5.js.br +0 -0
  108. package/dist/client/assets/diagram-Z3DM3KII-BIfTa7P5.js.gz +0 -0
  109. package/dist/client/assets/{ebnfDiagram-PWID7BFC-BLrPQuLE.js → ebnfDiagram-PWID7BFC-D4XhCDFS.js} +1 -1
  110. package/dist/client/assets/ebnfDiagram-PWID7BFC-D4XhCDFS.js.br +0 -0
  111. package/dist/client/assets/ebnfDiagram-PWID7BFC-D4XhCDFS.js.gz +0 -0
  112. package/dist/client/assets/{erDiagram-RLTQ6QDP-DlXgoyZ-.js → erDiagram-RLTQ6QDP-Dxd48dXC.js} +1 -1
  113. package/dist/client/assets/erDiagram-RLTQ6QDP-Dxd48dXC.js.br +0 -0
  114. package/dist/client/assets/erDiagram-RLTQ6QDP-Dxd48dXC.js.gz +0 -0
  115. package/dist/client/assets/{flowDiagram-HODETNUW-fPHWxEDZ.js → flowDiagram-HODETNUW-BXBMsEmE.js} +1 -1
  116. package/dist/client/assets/flowDiagram-HODETNUW-BXBMsEmE.js.br +0 -0
  117. package/dist/client/assets/flowDiagram-HODETNUW-BXBMsEmE.js.gz +0 -0
  118. package/dist/client/assets/{ganttDiagram-EL5Y4UJY-B8MOv6ug.js → ganttDiagram-EL5Y4UJY-CBfDd-KZ.js} +1 -1
  119. package/dist/client/assets/ganttDiagram-EL5Y4UJY-CBfDd-KZ.js.br +0 -0
  120. package/dist/client/assets/ganttDiagram-EL5Y4UJY-CBfDd-KZ.js.gz +0 -0
  121. package/dist/client/assets/{gestureArbiter-JW8vcVRm.js → gestureArbiter-DXLmNGli.js} +1 -1
  122. package/dist/client/assets/gestureArbiter-DXLmNGli.js.br +0 -0
  123. package/dist/client/assets/gestureArbiter-DXLmNGli.js.gz +0 -0
  124. package/dist/client/assets/{gitGraphDiagram-WWUBYQGX-lH9gSoFx.js → gitGraphDiagram-WWUBYQGX-DtLM68fN.js} +1 -1
  125. package/dist/client/assets/gitGraphDiagram-WWUBYQGX-DtLM68fN.js.br +0 -0
  126. package/dist/client/assets/gitGraphDiagram-WWUBYQGX-DtLM68fN.js.gz +0 -0
  127. package/dist/client/assets/index-KuPaZyuZ.css +1 -0
  128. package/dist/client/assets/index-KuPaZyuZ.css.br +0 -0
  129. package/dist/client/assets/{index-CNY7CTVa.css.gz → index-KuPaZyuZ.css.gz} +0 -0
  130. package/dist/client/assets/{infoDiagram-27XIBGKW-CSG29Ty_.js → infoDiagram-27XIBGKW-FRhqdJvW.js} +1 -1
  131. package/dist/client/assets/{ishikawaDiagram-5VMMS53U-CcwSE5qV.js → ishikawaDiagram-5VMMS53U-DAHBvAZ-.js} +1 -1
  132. package/dist/client/assets/ishikawaDiagram-5VMMS53U-DAHBvAZ-.js.br +0 -0
  133. package/dist/client/assets/ishikawaDiagram-5VMMS53U-DAHBvAZ-.js.gz +0 -0
  134. package/dist/client/assets/{journeyDiagram-3NMN7TZE-CXFUeP2c.js → journeyDiagram-3NMN7TZE-CVuWuL3Z.js} +1 -1
  135. package/dist/client/assets/journeyDiagram-3NMN7TZE-CVuWuL3Z.js.br +0 -0
  136. package/dist/client/assets/journeyDiagram-3NMN7TZE-CVuWuL3Z.js.gz +0 -0
  137. package/dist/client/assets/{kanban-definition-UXKFOSKX-KEHwljd2.js → kanban-definition-UXKFOSKX-ByQSUVJV.js} +1 -1
  138. package/dist/client/assets/kanban-definition-UXKFOSKX-ByQSUVJV.js.br +0 -0
  139. package/dist/client/assets/kanban-definition-UXKFOSKX-ByQSUVJV.js.gz +0 -0
  140. package/dist/client/assets/{layout-DqYx0MnO.js → layout-Bb3Nb1c4.js} +1 -1
  141. package/dist/client/assets/layout-Bb3Nb1c4.js.br +0 -0
  142. package/dist/client/assets/layout-Bb3Nb1c4.js.gz +0 -0
  143. package/dist/client/assets/{linear-BnG3XaJW.js → linear-DHMMQlOo.js} +1 -1
  144. package/dist/client/assets/linear-DHMMQlOo.js.br +0 -0
  145. package/dist/client/assets/linear-DHMMQlOo.js.gz +0 -0
  146. package/dist/client/assets/{mermaid.core-Ce00rdM6.js → mermaid.core-BYfniK0H.js} +5 -5
  147. package/dist/client/assets/mermaid.core-BYfniK0H.js.br +0 -0
  148. package/dist/client/assets/mermaid.core-BYfniK0H.js.gz +0 -0
  149. package/dist/client/assets/{mindmap-definition-YA3MSWOX-D0hOW4SY.js → mindmap-definition-YA3MSWOX-EDLD5AyH.js} +1 -1
  150. package/dist/client/assets/mindmap-definition-YA3MSWOX-EDLD5AyH.js.br +0 -0
  151. package/dist/client/assets/mindmap-definition-YA3MSWOX-EDLD5AyH.js.gz +0 -0
  152. package/dist/client/assets/passwordBootstrap-DCrtirwT.js +2 -0
  153. package/dist/client/assets/passwordBootstrap-DCrtirwT.js.br +0 -0
  154. package/dist/client/assets/{passwordBootstrap-Bncb8qF_.js.gz → passwordBootstrap-DCrtirwT.js.gz} +0 -0
  155. package/dist/client/assets/{pegDiagram-XKGWAZYB-UKp9t91x.js → pegDiagram-XKGWAZYB-BHYhkqJN.js} +1 -1
  156. package/dist/client/assets/pegDiagram-XKGWAZYB-BHYhkqJN.js.br +0 -0
  157. package/dist/client/assets/pegDiagram-XKGWAZYB-BHYhkqJN.js.gz +0 -0
  158. package/dist/client/assets/{pieDiagram-E7YTZNPT-Dif97wbH.js → pieDiagram-E7YTZNPT-BUIJlswC.js} +1 -1
  159. package/dist/client/assets/pieDiagram-E7YTZNPT-BUIJlswC.js.br +0 -0
  160. package/dist/client/assets/pieDiagram-E7YTZNPT-BUIJlswC.js.gz +0 -0
  161. package/dist/client/assets/{quadrantDiagram-AXDQQJYC-BPyHtH91.js → quadrantDiagram-AXDQQJYC-D8Im-7yC.js} +1 -1
  162. package/dist/client/assets/quadrantDiagram-AXDQQJYC-D8Im-7yC.js.br +0 -0
  163. package/dist/client/assets/quadrantDiagram-AXDQQJYC-D8Im-7yC.js.gz +0 -0
  164. package/dist/client/assets/{railroadDiagram-O6MQD6OU-Wleq9LmS.js → railroadDiagram-O6MQD6OU-D7n6z2G1.js} +1 -1
  165. package/dist/client/assets/railroadDiagram-O6MQD6OU-D7n6z2G1.js.br +0 -0
  166. package/dist/client/assets/railroadDiagram-O6MQD6OU-D7n6z2G1.js.gz +0 -0
  167. package/dist/client/assets/{rdpSession-CobFMSUs.js → rdpSession-DJlNIbVk.js} +1 -1
  168. package/dist/client/assets/rdpSession-DJlNIbVk.js.br +0 -0
  169. package/dist/client/assets/rdpSession-DJlNIbVk.js.gz +0 -0
  170. package/dist/client/assets/{referenceLongPress-bZ0xp-v2.js → referenceLongPress-DFSrssSr.js} +1 -1
  171. package/dist/client/assets/referenceLongPress-DFSrssSr.js.br +0 -0
  172. package/dist/client/assets/referenceLongPress-DFSrssSr.js.gz +0 -0
  173. package/dist/client/assets/{requirementDiagram-BXWQKSXE-BL4pp0Ta.js → requirementDiagram-BXWQKSXE-Ki0rR-F7.js} +1 -1
  174. package/dist/client/assets/requirementDiagram-BXWQKSXE-Ki0rR-F7.js.br +0 -0
  175. package/dist/client/assets/requirementDiagram-BXWQKSXE-Ki0rR-F7.js.gz +0 -0
  176. package/dist/client/assets/{sankeyDiagram-P5KCCOFB-CV1cKx37.js → sankeyDiagram-P5KCCOFB-36NmMqsW.js} +1 -1
  177. package/dist/client/assets/sankeyDiagram-P5KCCOFB-36NmMqsW.js.br +0 -0
  178. package/dist/client/assets/sankeyDiagram-P5KCCOFB-36NmMqsW.js.gz +0 -0
  179. package/dist/client/assets/{sequenceDiagram-WJ2MYXX4-BF2InLwV.js → sequenceDiagram-WJ2MYXX4-5vsPuFyO.js} +1 -1
  180. package/dist/client/assets/sequenceDiagram-WJ2MYXX4-5vsPuFyO.js.br +0 -0
  181. package/dist/client/assets/sequenceDiagram-WJ2MYXX4-5vsPuFyO.js.gz +0 -0
  182. package/dist/client/assets/{sizeCapture-INFHLROL-CldUyStR.js → sizeCapture-INFHLROL-DbAulwBg.js} +1 -1
  183. package/dist/client/assets/sizeCapture-INFHLROL-DbAulwBg.js.br +0 -0
  184. package/dist/client/assets/sizeCapture-INFHLROL-DbAulwBg.js.gz +0 -0
  185. package/dist/client/assets/{sparkles-Cg-yPdE2.js → sparkles-CapLTKAs.js} +1 -1
  186. package/dist/client/assets/{stateDiagram-D77RDMKH-CByehbEd.js → stateDiagram-D77RDMKH-Bgwe0g5S.js} +1 -1
  187. package/dist/client/assets/stateDiagram-D77RDMKH-Bgwe0g5S.js.br +0 -0
  188. package/dist/client/assets/stateDiagram-D77RDMKH-Bgwe0g5S.js.gz +0 -0
  189. package/dist/client/assets/stateDiagram-v2-MP3YSRHH-Bg6S3Zm0.js +1 -0
  190. package/dist/client/assets/{swimlanes-42K2YHIH--1_7YTL4.js → swimlanes-42K2YHIH-COGAWe-g.js} +1 -1
  191. package/dist/client/assets/swimlanes-42K2YHIH-COGAWe-g.js.br +0 -0
  192. package/dist/client/assets/swimlanes-42K2YHIH-COGAWe-g.js.gz +0 -0
  193. package/dist/client/assets/swimlanesDiagram-VR7AAH4N-DwBBOocG.js +8 -0
  194. package/dist/client/assets/{timeline-definition-24CTP7MA-CXfXJFK6.js → timeline-definition-24CTP7MA-C4gt5z68.js} +1 -1
  195. package/dist/client/assets/timeline-definition-24CTP7MA-C4gt5z68.js.br +0 -0
  196. package/dist/client/assets/timeline-definition-24CTP7MA-C4gt5z68.js.gz +0 -0
  197. package/dist/client/assets/{triangle-alert-CbMRJ6sx.js → triangle-alert-xPHw25jD.js} +1 -1
  198. package/dist/client/assets/{vennDiagram-4TSXK5OY-byr6UQpL.js → vennDiagram-4TSXK5OY-CIEXh9oD.js} +1 -1
  199. package/dist/client/assets/vennDiagram-4TSXK5OY-CIEXh9oD.js.br +0 -0
  200. package/dist/client/assets/vennDiagram-4TSXK5OY-CIEXh9oD.js.gz +0 -0
  201. package/dist/client/assets/{videoCompression-ivJAy00d.js → videoCompression-CUkCS2-q.js} +1 -1
  202. package/dist/client/assets/videoCompression-CUkCS2-q.js.br +0 -0
  203. package/dist/client/assets/videoCompression-CUkCS2-q.js.gz +0 -0
  204. package/dist/client/assets/{wardleyDiagram-VM6X3IG4-FJduk-7s.js → wardleyDiagram-VM6X3IG4-gQhcW1vd.js} +1 -1
  205. package/dist/client/assets/wardleyDiagram-VM6X3IG4-gQhcW1vd.js.br +0 -0
  206. package/dist/client/assets/wardleyDiagram-VM6X3IG4-gQhcW1vd.js.gz +0 -0
  207. package/dist/client/assets/{xychartDiagram-S5SC5T6Z-Ct1fBPFS.js → xychartDiagram-S5SC5T6Z-BmIcdejz.js} +1 -1
  208. package/dist/client/assets/xychartDiagram-S5SC5T6Z-BmIcdejz.js.br +0 -0
  209. package/dist/client/assets/xychartDiagram-S5SC5T6Z-BmIcdejz.js.gz +0 -0
  210. package/dist/client/index.html +2 -2
  211. package/dist/client/index.html.br +0 -0
  212. package/dist/client/index.html.gz +0 -0
  213. package/dist/client/sw.js +1 -1
  214. package/dist/client/sw.js.br +0 -0
  215. package/dist/client/sw.js.gz +0 -0
  216. package/dist/server/agent/collaborationCli.js +6 -4
  217. package/dist/server/agent/collaborationDeliveryWorker.js +3 -97
  218. package/dist/server/agent/collaborationTmuxDelivery.js +23 -51
  219. package/dist/server/agent/integrationCli.js +23 -0
  220. package/dist/server/agent/integrationServer.js +7 -0
  221. package/dist/server/agent/integrationSessions.js +24 -1
  222. package/dist/server/agent/promptDelivery.js +20 -7
  223. package/dist/server/agent/sessionLifecycle.js +2 -2
  224. package/dist/server/architecture/cli.js +320 -0
  225. package/dist/server/architecture/document.js +328 -0
  226. package/dist/server/architecture/documentDiff.js +39 -0
  227. package/dist/server/architecture/fieldMutation.js +52 -0
  228. package/dist/server/architecture/flowchart.js +62 -0
  229. package/dist/server/architecture/mermaidDiff.js +85 -0
  230. package/dist/server/architecture/routes.js +117 -0
  231. package/dist/server/architecture/store.js +502 -0
  232. package/dist/server/cli.js +7 -1
  233. package/dist/server/entry.js +2 -0
  234. package/dist/server/federation/accessPolicy.js +9 -1
  235. package/dist/server/routes/terminal.js +8 -12
  236. package/docs/integrations.md +45 -1
  237. package/package.json +3 -1
  238. package/runtime-manifest.json +4 -4
  239. package/dist/client/assets/App-ggIA_xqR.js.br +0 -0
  240. package/dist/client/assets/App-ggIA_xqR.js.gz +0 -0
  241. package/dist/client/assets/ArchitecturePanel-Cmpmp6FS.css.br +0 -0
  242. package/dist/client/assets/ArchitecturePanel-Cmpmp6FS.css.gz +0 -0
  243. package/dist/client/assets/ArchitecturePanel-CoBspW_C.js +0 -12
  244. package/dist/client/assets/ArchitecturePanel-CoBspW_C.js.br +0 -0
  245. package/dist/client/assets/ArchitecturePanel-CoBspW_C.js.gz +0 -0
  246. package/dist/client/assets/ChangeWalkthroughPanel-D1Puc7B3.js.br +0 -0
  247. package/dist/client/assets/ChangeWalkthroughPanel-D1Puc7B3.js.gz +0 -0
  248. package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js +0 -1
  249. package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js.br +0 -0
  250. package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js.gz +0 -0
  251. package/dist/client/assets/CollaborationTaskContent-CTSJJqze.js +0 -2
  252. package/dist/client/assets/ComputerControlView-D5Lw9sNA.js.br +0 -0
  253. package/dist/client/assets/ComputerControlView-D5Lw9sNA.js.gz +0 -0
  254. package/dist/client/assets/DagPlayground-DYJrGfiG.js.br +0 -0
  255. package/dist/client/assets/DagPlayground-DYJrGfiG.js.gz +0 -0
  256. package/dist/client/assets/DiffLab-5zdcFW3z.js.br +0 -0
  257. package/dist/client/assets/DiffLab-5zdcFW3z.js.gz +0 -0
  258. package/dist/client/assets/DiffReview-BBBC_NjV.js.br +0 -0
  259. package/dist/client/assets/DiffReview-BBBC_NjV.js.gz +0 -0
  260. package/dist/client/assets/DiffReviewLab-CbhosFSB.js.br +0 -0
  261. package/dist/client/assets/DiffReviewLab-CbhosFSB.js.gz +0 -0
  262. package/dist/client/assets/DiffViewer-BuQwFQ4V.js.br +0 -0
  263. package/dist/client/assets/DiffViewer-BuQwFQ4V.js.gz +0 -0
  264. package/dist/client/assets/ModelPreview-nO2VmqdP.js.br +0 -0
  265. package/dist/client/assets/ModelPreview-nO2VmqdP.js.gz +0 -0
  266. package/dist/client/assets/RightSidebar-BoNzpS2K.js +0 -1677
  267. package/dist/client/assets/RightSidebar-BoNzpS2K.js.br +0 -0
  268. package/dist/client/assets/RightSidebar-BoNzpS2K.js.gz +0 -0
  269. package/dist/client/assets/abnfDiagram-VCTEODGH-yi0K8GDG.js.br +0 -0
  270. package/dist/client/assets/abnfDiagram-VCTEODGH-yi0K8GDG.js.gz +0 -0
  271. package/dist/client/assets/app-B6FdOF6K.js.br +0 -0
  272. package/dist/client/assets/app-B6FdOF6K.js.gz +0 -0
  273. package/dist/client/assets/arc-_nLI_-XZ.js.br +0 -0
  274. package/dist/client/assets/arc-_nLI_-XZ.js.gz +0 -0
  275. package/dist/client/assets/architectureDiagram-5GKGNRK7-CikrA78O.js.br +0 -0
  276. package/dist/client/assets/architectureDiagram-5GKGNRK7-CikrA78O.js.gz +0 -0
  277. package/dist/client/assets/blockDiagram-I7D4REHJ-CWJq6qJ7.js.br +0 -0
  278. package/dist/client/assets/blockDiagram-I7D4REHJ-CWJq6qJ7.js.gz +0 -0
  279. package/dist/client/assets/c4Diagram-7LVT6UL2-gzPzLGvs.js.br +0 -0
  280. package/dist/client/assets/c4Diagram-7LVT6UL2-gzPzLGvs.js.gz +0 -0
  281. package/dist/client/assets/channel-BYsFmOmF.js +0 -1
  282. package/dist/client/assets/chunk-F27PBJKO-CQ0LXeap.js.br +0 -0
  283. package/dist/client/assets/chunk-F27PBJKO-CQ0LXeap.js.gz +0 -0
  284. package/dist/client/assets/chunk-IMKFNOWR-CJOEPkK9.js.br +0 -0
  285. package/dist/client/assets/chunk-IMKFNOWR-CJOEPkK9.js.gz +0 -0
  286. package/dist/client/assets/chunk-SVP7TREG-BskkG9gg.js.br +0 -0
  287. package/dist/client/assets/chunk-SVP7TREG-BskkG9gg.js.gz +0 -0
  288. package/dist/client/assets/chunk-TICWLB2K-DyzuP-9I.js.br +0 -0
  289. package/dist/client/assets/chunk-TICWLB2K-DyzuP-9I.js.gz +0 -0
  290. package/dist/client/assets/classDiagram-ZZMXUADV-BnmZv6Ns.js +0 -1
  291. package/dist/client/assets/classDiagram-v2-VYDZK3BY-BnmZv6Ns.js +0 -1
  292. package/dist/client/assets/cose-bilkent-JH36ORCC-Bm-ESDOc.js.br +0 -0
  293. package/dist/client/assets/cose-bilkent-JH36ORCC-Bm-ESDOc.js.gz +0 -0
  294. package/dist/client/assets/cynefin-OW5HDTMX-DbFWAPvX.js.br +0 -0
  295. package/dist/client/assets/cynefin-OW5HDTMX-DbFWAPvX.js.gz +0 -0
  296. package/dist/client/assets/cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js.br +0 -0
  297. package/dist/client/assets/cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js.gz +0 -0
  298. package/dist/client/assets/dagre-GXQ25YYZ-D_5uEMjJ.js.br +0 -0
  299. package/dist/client/assets/dagre-GXQ25YYZ-D_5uEMjJ.js.gz +0 -0
  300. package/dist/client/assets/diagram-S7CK7UJ4-DWVpndRP.js.br +0 -0
  301. package/dist/client/assets/diagram-S7CK7UJ4-DWVpndRP.js.gz +0 -0
  302. package/dist/client/assets/diagram-UQ7AKVKN-DmYTya3w.js.br +0 -0
  303. package/dist/client/assets/diagram-UQ7AKVKN-DmYTya3w.js.gz +0 -0
  304. package/dist/client/assets/diagram-VSXAHHWV-BEA6kqNj.js.br +0 -0
  305. package/dist/client/assets/diagram-VSXAHHWV-BEA6kqNj.js.gz +0 -0
  306. package/dist/client/assets/diagram-VX7I27RA-CU9vP0P0.js.br +0 -0
  307. package/dist/client/assets/diagram-VX7I27RA-CU9vP0P0.js.gz +0 -0
  308. package/dist/client/assets/diagram-Z3DM3KII-B_GvE2g-.js.br +0 -0
  309. package/dist/client/assets/diagram-Z3DM3KII-B_GvE2g-.js.gz +0 -0
  310. package/dist/client/assets/ebnfDiagram-PWID7BFC-BLrPQuLE.js.br +0 -0
  311. package/dist/client/assets/ebnfDiagram-PWID7BFC-BLrPQuLE.js.gz +0 -0
  312. package/dist/client/assets/erDiagram-RLTQ6QDP-DlXgoyZ-.js.br +0 -0
  313. package/dist/client/assets/erDiagram-RLTQ6QDP-DlXgoyZ-.js.gz +0 -0
  314. package/dist/client/assets/flowDiagram-HODETNUW-fPHWxEDZ.js.br +0 -0
  315. package/dist/client/assets/flowDiagram-HODETNUW-fPHWxEDZ.js.gz +0 -0
  316. package/dist/client/assets/ganttDiagram-EL5Y4UJY-B8MOv6ug.js.br +0 -0
  317. package/dist/client/assets/ganttDiagram-EL5Y4UJY-B8MOv6ug.js.gz +0 -0
  318. package/dist/client/assets/gestureArbiter-JW8vcVRm.js.br +0 -0
  319. package/dist/client/assets/gestureArbiter-JW8vcVRm.js.gz +0 -0
  320. package/dist/client/assets/gitGraphDiagram-WWUBYQGX-lH9gSoFx.js.br +0 -0
  321. package/dist/client/assets/gitGraphDiagram-WWUBYQGX-lH9gSoFx.js.gz +0 -0
  322. package/dist/client/assets/index-CNY7CTVa.css +0 -1
  323. package/dist/client/assets/index-CNY7CTVa.css.br +0 -0
  324. package/dist/client/assets/ishikawaDiagram-5VMMS53U-CcwSE5qV.js.br +0 -0
  325. package/dist/client/assets/ishikawaDiagram-5VMMS53U-CcwSE5qV.js.gz +0 -0
  326. package/dist/client/assets/journeyDiagram-3NMN7TZE-CXFUeP2c.js.br +0 -0
  327. package/dist/client/assets/journeyDiagram-3NMN7TZE-CXFUeP2c.js.gz +0 -0
  328. package/dist/client/assets/kanban-definition-UXKFOSKX-KEHwljd2.js.br +0 -0
  329. package/dist/client/assets/kanban-definition-UXKFOSKX-KEHwljd2.js.gz +0 -0
  330. package/dist/client/assets/layout-DqYx0MnO.js.br +0 -0
  331. package/dist/client/assets/layout-DqYx0MnO.js.gz +0 -0
  332. package/dist/client/assets/linear-BnG3XaJW.js.br +0 -0
  333. package/dist/client/assets/linear-BnG3XaJW.js.gz +0 -0
  334. package/dist/client/assets/mermaid.core-Ce00rdM6.js.br +0 -0
  335. package/dist/client/assets/mermaid.core-Ce00rdM6.js.gz +0 -0
  336. package/dist/client/assets/mindmap-definition-YA3MSWOX-D0hOW4SY.js.br +0 -0
  337. package/dist/client/assets/mindmap-definition-YA3MSWOX-D0hOW4SY.js.gz +0 -0
  338. package/dist/client/assets/passwordBootstrap-Bncb8qF_.js +0 -2
  339. package/dist/client/assets/passwordBootstrap-Bncb8qF_.js.br +0 -0
  340. package/dist/client/assets/pegDiagram-XKGWAZYB-UKp9t91x.js.br +0 -0
  341. package/dist/client/assets/pegDiagram-XKGWAZYB-UKp9t91x.js.gz +0 -0
  342. package/dist/client/assets/pieDiagram-E7YTZNPT-Dif97wbH.js.br +0 -0
  343. package/dist/client/assets/pieDiagram-E7YTZNPT-Dif97wbH.js.gz +0 -0
  344. package/dist/client/assets/quadrantDiagram-AXDQQJYC-BPyHtH91.js.br +0 -0
  345. package/dist/client/assets/quadrantDiagram-AXDQQJYC-BPyHtH91.js.gz +0 -0
  346. package/dist/client/assets/railroadDiagram-O6MQD6OU-Wleq9LmS.js.br +0 -0
  347. package/dist/client/assets/railroadDiagram-O6MQD6OU-Wleq9LmS.js.gz +0 -0
  348. package/dist/client/assets/rdpSession-CobFMSUs.js.br +0 -0
  349. package/dist/client/assets/rdpSession-CobFMSUs.js.gz +0 -0
  350. package/dist/client/assets/referenceLongPress-bZ0xp-v2.js.br +0 -0
  351. package/dist/client/assets/referenceLongPress-bZ0xp-v2.js.gz +0 -0
  352. package/dist/client/assets/requirementDiagram-BXWQKSXE-BL4pp0Ta.js.br +0 -0
  353. package/dist/client/assets/requirementDiagram-BXWQKSXE-BL4pp0Ta.js.gz +0 -0
  354. package/dist/client/assets/sankeyDiagram-P5KCCOFB-CV1cKx37.js.br +0 -0
  355. package/dist/client/assets/sankeyDiagram-P5KCCOFB-CV1cKx37.js.gz +0 -0
  356. package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BF2InLwV.js.br +0 -0
  357. package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BF2InLwV.js.gz +0 -0
  358. package/dist/client/assets/sizeCapture-INFHLROL-CldUyStR.js.br +0 -0
  359. package/dist/client/assets/sizeCapture-INFHLROL-CldUyStR.js.gz +0 -0
  360. package/dist/client/assets/stateDiagram-D77RDMKH-CByehbEd.js.br +0 -0
  361. package/dist/client/assets/stateDiagram-D77RDMKH-CByehbEd.js.gz +0 -0
  362. package/dist/client/assets/stateDiagram-v2-MP3YSRHH-CTcrJ-w0.js +0 -1
  363. package/dist/client/assets/swimlanes-42K2YHIH--1_7YTL4.js.br +0 -0
  364. package/dist/client/assets/swimlanes-42K2YHIH--1_7YTL4.js.gz +0 -0
  365. package/dist/client/assets/swimlanesDiagram-VR7AAH4N-RSMV9AhO.js +0 -8
  366. package/dist/client/assets/timeline-definition-24CTP7MA-CXfXJFK6.js.br +0 -0
  367. package/dist/client/assets/timeline-definition-24CTP7MA-CXfXJFK6.js.gz +0 -0
  368. package/dist/client/assets/vennDiagram-4TSXK5OY-byr6UQpL.js.br +0 -0
  369. package/dist/client/assets/vennDiagram-4TSXK5OY-byr6UQpL.js.gz +0 -0
  370. package/dist/client/assets/videoCompression-ivJAy00d.js.br +0 -0
  371. package/dist/client/assets/videoCompression-ivJAy00d.js.gz +0 -0
  372. package/dist/client/assets/wardleyDiagram-VM6X3IG4-FJduk-7s.js.br +0 -0
  373. package/dist/client/assets/wardleyDiagram-VM6X3IG4-FJduk-7s.js.gz +0 -0
  374. package/dist/client/assets/xychartDiagram-S5SC5T6Z-Ct1fBPFS.js.br +0 -0
  375. package/dist/client/assets/xychartDiagram-S5SC5T6Z-Ct1fBPFS.js.gz +0 -0
@@ -1,5 +1,5 @@
1
1
  import { plainCollaborationSnapshot } from './collaborationText.js';
2
- import { normalizePromptForPaste } from './promptDelivery.js';
2
+ import { normalizePromptForPaste, waitForPromptSubmit } from './promptDelivery.js';
3
3
  const TMUX_KEY_NAMES = {
4
4
  enter: 'Enter', escape: 'Escape', space: 'Space', left: 'Left', right: 'Right', up: 'Up', down: 'Down',
5
5
  };
@@ -19,26 +19,9 @@ const APPROVAL_DIALOG_PATTERNS = [
19
19
  /\b1\.\s*是\b/,
20
20
  /允许.*执行|确认.*执行/i,
21
21
  ];
22
- /** Agent TUIs collapse pasted input in the input box to a marker line like
23
- * "[Pasted text #3 +42 lines]". While the paste sits unsubmitted the marker
24
- * stays on screen; a submitted paste clears the box and only the transcript
25
- * holds the content. Session-unique #N lets us diff screen captures. */
26
- const PASTE_MARKER_PATTERN = /\[Pasted text #(\d+)/g;
27
22
  export function detectApprovalDialog(content) {
28
23
  return APPROVAL_DIALOG_PATTERNS.some((pattern) => pattern.test(content));
29
24
  }
30
- /** Paste marker sequence numbers visible in a screen capture. */
31
- export function extractPasteMarkerNumbers(content) {
32
- return new Set([...content.matchAll(PASTE_MARKER_PATTERN)].map((match) => Number(match[1])));
33
- }
34
- /** True when `after` shows a paste marker that was not in `before`. Diffing
35
- * prevents a recovery Enter from submitting a stale paste that predates this
36
- * delivery (or someone else's draft): we only ever submit what we just put
37
- * there, at most once per delivery. */
38
- export function hasNewPasteMarker(after, before) {
39
- const beforeNumbers = extractPasteMarkerNumbers(before);
40
- return [...extractPasteMarkerNumbers(after)].some((number) => !beforeNumbers.has(number));
41
- }
42
25
  async function assertSamePane(run, pane) {
43
26
  const identity = (await run(['display-message', '-p', '-t', pane.paneId,
44
27
  '#{pid}:#{session_id}:#{pane_id}:#{pane_pid}'])).trim();
@@ -48,15 +31,19 @@ async function assertSamePane(run, pane) {
48
31
  /** Unique-per-process buffer name so concurrent deliveries to different panes
49
32
  * never share (or clobber) a buffer. */
50
33
  let bufferSequence = 0;
51
- export async function writeCollaborationTmuxPane(run, pane, prompt,
52
- /** Sends `input` to the tmux client's stdin. The steps below are one `\;`
53
- * chain (see the comment inside), and a chain is argv, so the body must not
54
- * ride in argv: tmux treats an element that is exactly `;` as a separator
55
- * even after `--`, and its backslash unescaping is version-dependent
56
- * (`\\` survives verbatim while `\;` collapses to `;`). Reading the body
57
- * from stdin sidesteps both — every byte round-trips unchanged. Required,
58
- * not optional: a run() that ignored the payload would load an empty buffer
59
- * and fail the delivery rather than deliver the wrong thing. */
34
+ const paneWrites = new Map();
35
+ /** Serialize TD paste/submit pairs for this exact runtime pane. */
36
+ export function writeCollaborationTmuxPane(run, pane, prompt, stdin) {
37
+ const key = `${pane.serverPid}:${pane.sessionId}:${pane.paneId}:${pane.panePid}`;
38
+ const previous = paneWrites.get(key) ?? Promise.resolve();
39
+ const operation = previous.catch(() => undefined).then(() => writeTmuxPrompt(run, pane, prompt, stdin))
40
+ .finally(() => { if (paneWrites.get(key) === operation)
41
+ paneWrites.delete(key); });
42
+ paneWrites.set(key, operation);
43
+ return operation;
44
+ }
45
+ async function writeTmuxPrompt(run, pane, prompt,
46
+ /** Body travels on stdin so tmux cannot parse its semicolons/backslashes. */
60
47
  stdin) {
61
48
  await assertSamePane(run, pane);
62
49
  // A fixed pane target is independent of the current window, keyboard focus
@@ -77,13 +64,8 @@ stdin) {
77
64
  // every tmux version.
78
65
  const buffer = `termdock-collab-${process.pid}-${bufferSequence++}`;
79
66
  try {
80
- // The four steps ride one client invocation joined by tmux's `\;`: the
81
- // server runs them back to back in a single queue item, so no other
82
- // client's paste can interleave between our text and our submit CR
83
- // (measured: one contiguous block, 0ms apart, versus two invocations
84
- // ~14ms apart). A failing step stops the rest — verified on 3.4 and 3.7 —
85
- // which is the safe direction: a failed text paste is never followed by a
86
- // bare CR into whatever the input box already held.
67
+ // Paste once, then send one unbracketed CR after 50ms. No screen parsing,
68
+ // Agent-specific recovery, consumption confirmation or additional Enter.
87
69
  await stdin([
88
70
  // The body arrives on stdin, not argv: it is user content, and in a
89
71
  // `\;` chain argv is a language where `;` and `\` mean something.
@@ -91,13 +73,17 @@ stdin) {
91
73
  // -r keeps LF as LF rather than the separator default of CR. The
92
74
  // normalizer already folded every line break to CR, so no LF is left
93
75
  // for it to rewrite — the flag is insurance, not the mechanism.
94
- 'paste-buffer', '-p', '-r', '-d', '-b', buffer, '-t', pane.paneId, ';',
76
+ 'paste-buffer', '-p', '-r', '-d', '-b', buffer, '-t', pane.paneId,
77
+ ], normalizePromptForPaste(prompt));
78
+ await waitForPromptSubmit();
79
+ await assertSamePane(run, pane);
80
+ await run([
95
81
  // The submit key rides outside the paste block: inside it, an editor
96
82
  // inserts a pasted CR as text instead of acting on it. Pasting the bare
97
83
  // CR (no -p) keeps the key in the same mode-proof channel as the text.
98
84
  'set-buffer', '-b', buffer, '--', '\r', ';',
99
85
  'paste-buffer', '-d', '-b', buffer, '-t', pane.paneId,
100
- ], normalizePromptForPaste(prompt));
86
+ ]);
101
87
  }
102
88
  finally {
103
89
  // -d consumed the buffer on the happy path; this sweeps up after a failed
@@ -139,21 +125,7 @@ export async function approveCollaborationDialog(run, pane) {
139
125
  await sendTmuxPaneKey(run, pane, 'enter');
140
126
  return true;
141
127
  }
142
- /** Submit a paste that arrived while the agent was finishing its previous
143
- * turn and is still sitting unsubmitted in the input box. Only acts on
144
- * differential evidence — a paste marker that appeared after the write —
145
- * never on pre-existing stale markers, and returns whether Enter was sent.
146
- * Committing the whole input buffer is safe: each delivery is written once,
147
- * so each marker's content enters the transcript exactly once. */
148
- export async function recoverStuckPaste(run, pane, baseline) {
149
- const viewport = await captureTmuxPaneText(run, pane);
150
- if (!hasNewPasteMarker(viewport, baseline))
151
- return false;
152
- await sendTmuxPaneKey(run, pane, 'enter');
153
- return true;
154
- }
155
- /** History-inclusive pane text (scrollback + viewport) used to confirm a
156
- * delivery was actually rendered by the agent, not wiped by a boot clear. */
128
+ /** History-inclusive terminal observation, without inferring consumption. */
157
129
  export async function captureTmuxPaneHistory(run, pane, lines = 800, rawOutput = false) {
158
130
  await assertSamePane(run, pane);
159
131
  if (!Number.isInteger(lines) || lines < 1 || lines > 10000)
@@ -8,6 +8,17 @@ import { COLLAB_HELP, executeCollaborationCommand, duration } from './collaborat
8
8
  import { getTermdockVersion } from '../utils/version.js';
9
9
  export const INTEGRATION_HELP = `td integration — local scoped integration administration
10
10
  groups | list
11
+ clear-startup-input <TD-session-id> --generation <N>
12
+ Administrator removes this session's saved screen conditions and disables
13
+ inheritance on later restores; original identity/launch/history are preserved.
14
+ Pending messages may then use the ordinary delivery worker; delivered bodies
15
+ are never replayed. No Agent restart, resize, RPC or readiness claim.
16
+ The generation increments once; read session get for the new generation and
17
+ startup_input_disabled=true. Repeating with the old generation is rejected.
18
+ Minimum CLI/running service 1.4.310; session_startup_input_clear=true.
19
+ Errors: SESSION_STARTUP_INPUT_CLEAR_UNSUPPORTED, INVALID_SESSION_GENERATION,
20
+ SESSION_GENERATION_MISMATCH, SESSION_OPERATION_IN_PROGRESS,
21
+ INTEGRATION_SESSION_NOT_FOUND. Profile policy update alone keeps old snapshots.
11
22
  resume-configuration <TD-session-id> (read current/recorded fingerprints; no mutation)
12
23
  confirm-resume <TD-session-id> --generation <N> --fingerprint <sha256>
13
24
  Administrator explicitly authorizes the current launcher/plugin recovery semantics.
@@ -72,6 +83,18 @@ export async function runIntegrationAdmin(argv, port, adminToken, write) {
72
83
  return 0;
73
84
  }
74
85
  const socketPath = integrationSocketPath(port);
86
+ if (action === 'clear-startup-input') {
87
+ const id = argv[1];
88
+ if (argv.length !== 4 || !id || !/^[a-zA-Z0-9._-]{1,80}$/.test(id) || argv[2] !== '--generation'
89
+ || !/^[1-9][0-9]*$/.test(argv[3]) || !Number.isSafeInteger(Number(argv[3]))) {
90
+ throw new Error('Usage: td integration clear-startup-input <TD-session-id> --generation <positive integer>');
91
+ }
92
+ const capabilities = parsed(await request(socketPath, 'GET', '/admin/capabilities', undefined, headers(undefined, adminToken)));
93
+ if (capabilities.session_startup_input_clear !== true)
94
+ throw new CollaborationError('SESSION_STARTUP_INPUT_CLEAR_UNSUPPORTED', 'CLI and running service must be at least 1.4.310', 409);
95
+ write(JSON.stringify(parsed(await request(socketPath, 'POST', `/admin/sessions/${encodeURIComponent(id)}/startup-input/clear`, { generation: Number(argv[3]) }, headers(undefined, adminToken)))));
96
+ return 0;
97
+ }
75
98
  if (action === 'resume-configuration' || action === 'confirm-resume') {
76
99
  const id = argv[1];
77
100
  if (!id || !/^[a-zA-Z0-9._-]{1,80}$/.test(id))
@@ -73,6 +73,12 @@ export class IntegrationRuntime {
73
73
  app.get('/admin/sessions/:id/restore-diagnostics', run(req => { admin(req); return this.sessions.restoreDiagnostics(req.params.id); }));
74
74
  app.get('/admin/sessions/:id/resume-configuration', run(async (req) => { admin(req); return this.sessions.resumeConfiguration(req.params.id); }));
75
75
  app.post('/admin/sessions/:id/resume-configuration', run(async (req) => { admin(req); return { session: publicIntegrationSession(await this.sessions.confirmResumeConfiguration(req.params.id, req.body?.generation, req.body?.fingerprint)) }; }));
76
+ app.post('/admin/sessions/:id/startup-input/clear', run(async (req) => {
77
+ admin(req);
78
+ const session = await this.sessions.clearStartupInput(req.params.id, req.body?.generation);
79
+ this.sync();
80
+ return { session: publicIntegrationSession(session) };
81
+ }));
76
82
  app.get('/admin/principals', run(req => { admin(req); return { integrations: this.store.policies() }; }));
77
83
  app.post('/admin/principals', run(req => { admin(req); this.group(req.body?.groupId); const provisioned = this.store.provision(req.body); try {
78
84
  this.sync();
@@ -217,6 +223,7 @@ export class IntegrationRuntime {
217
223
  idempotent_session_create: true, exact_session_restore: true, external_validation: false,
218
224
  startup_input_conditions: true, session_runtime_release: true, stable_session_identity: true, session_lifecycle_generation: true,
219
225
  session_resume_configuration: true, session_lifecycle_min_version: '1.4.309',
226
+ session_startup_input_clear: true, session_startup_input_clear_min_version: '1.4.310',
220
227
  integration_policy_update: true,
221
228
  session_restore_diagnostics: true,
222
229
  native_identity_linux_flock_owner: process.platform === 'linux',
@@ -14,6 +14,8 @@ export function integrationLaunchCommand(record, restore) {
14
14
  return `cd -- ${quote(record.cwd)} && ${[record.profile.executable, ...args].map(quote).join(' ')}`;
15
15
  }
16
16
  function startupInput(record, now) {
17
+ if (record.startup_input_disabled)
18
+ return undefined;
17
19
  const condition = record.startup_condition ?? record.profile.startupInput;
18
20
  return condition ? { state: 'pending', deadline: now + (condition.timeoutMs ?? 120000), matched_since: null, observed_at: null } : undefined;
19
21
  }
@@ -308,7 +310,7 @@ export class IntegrationSessions {
308
310
  record.deadline = Date.now() + this.bindingTimeout;
309
311
  record.updated_at = Date.now();
310
312
  record.restore_diagnostics = undefined;
311
- if (!record.profile.startupInput && !record.startup_condition)
313
+ if (!record.startup_input_disabled && !record.profile.startupInput && !record.startup_condition)
312
314
  record.startup_condition = structuredClone(principal.launchProfiles.find(profile => profile.id === record.launch_profile)?.startupInput);
313
315
  record.startup_input = startupInput(record, Date.now());
314
316
  this.doc.requests[request.scoped] = { hash: request.hash, sessionId: id, operationId: record.operation_id, generation: record.generation };
@@ -332,6 +334,27 @@ export class IntegrationSessions {
332
334
  return { session_id: id, generation: record.generation ?? 1, recorded_fingerprint: record.resume_configuration_fingerprint ?? null,
333
335
  current_fingerprint: await resumeConfigurationFingerprint(record, this.adapter), confirmation_required: !record.resume_configuration_fingerprint };
334
336
  }
337
+ async clearStartupInput(id, generation) {
338
+ return this.lifecycle.run(id, async () => {
339
+ const record = structuredClone(this.doc.sessions.find(s => s.session_id === id));
340
+ if (!record)
341
+ return integrationError('INTEGRATION_SESSION_NOT_FOUND', 'Recovery record does not exist', 404);
342
+ assertReleaseGeneration(record, generation);
343
+ if (this.pending.has(id) || record.operation_uncertain || ['starting', 'restoring', 'binding_pending', 'releasing'].includes(record.state)) {
344
+ integrationError('SESSION_OPERATION_IN_PROGRESS', 'Resolve the current lifecycle operation before clearing startup input conditions', 409);
345
+ }
346
+ if (record.startup_input_disabled && !record.profile.startupInput && !record.startup_condition && !record.startup_input)
347
+ return record;
348
+ delete record.profile.startupInput;
349
+ delete record.startup_condition;
350
+ delete record.startup_input;
351
+ record.startup_input_disabled = true;
352
+ record.generation = generation + 1;
353
+ record.updated_at = Date.now();
354
+ this.saveRecord(record);
355
+ return record;
356
+ });
357
+ }
335
358
  async confirmResumeConfiguration(id, generation, fingerprint) {
336
359
  return this.lifecycle.run(id, async () => {
337
360
  const record = structuredClone(this.doc.sessions.find(s => s.session_id === id));
@@ -8,13 +8,26 @@
8
8
  export function normalizePromptForPaste(prompt) {
9
9
  return prompt.replace(/\r\n|\r|\n/g, '\r').replace(/\x1b/g, '␛');
10
10
  }
11
- /**
12
- * Encode a prompt as one bracketed-paste block followed by one real Enter.
13
- * Agent TUIs then keep embedded newlines inside the editor instead of treating
14
- * each line as a separate submission.
15
- */
16
- export function buildBracketedSubmitBytes(prompt) {
17
- return `\x1b[200~${normalizePromptForPaste(prompt)}\x1b[201~\r`;
11
+ /** Separate the paste and its single unbracketed CR by 50ms. */
12
+ export const PROMPT_SUBMIT_DELAY_MS = 50;
13
+ export function waitForPromptSubmit() {
14
+ return new Promise((resolve) => setTimeout(resolve, PROMPT_SUBMIT_DELAY_MS));
15
+ }
16
+ export function buildBracketedPasteBytes(prompt) {
17
+ return `\x1b[200~${normalizePromptForPaste(prompt)}\x1b[201~`;
18
+ }
19
+ const promptWrites = new WeakMap();
20
+ /** Serialize TD prompt pairs per PTY. Success only records terminal writes. */
21
+ export function writeBracketedPrompt(target, prompt) {
22
+ const previous = promptWrites.get(target) ?? Promise.resolve();
23
+ const operation = previous.catch(() => undefined).then(async () => {
24
+ target.write(buildBracketedPasteBytes(prompt));
25
+ await waitForPromptSubmit();
26
+ target.write('\r');
27
+ }).finally(() => { if (promptWrites.get(target) === operation)
28
+ promptWrites.delete(target); });
29
+ promptWrites.set(target, operation);
30
+ return operation;
18
31
  }
19
32
  /**
20
33
  * Process detection and hook events are independent Agent signals. A target is
@@ -33,9 +33,9 @@ export class SessionLifecycleCoordinator {
33
33
  }
34
34
  export function assertReleaseGeneration(record, generation) {
35
35
  if (!Number.isSafeInteger(generation) || Number(generation) < 1)
36
- fail('INVALID_SESSION_GENERATION', 'release requires the generation returned by session get');
36
+ fail('INVALID_SESSION_GENERATION', 'Operation requires the generation returned by session get');
37
37
  if (generation !== (record.generation ?? 1))
38
- fail('SESSION_GENERATION_MISMATCH', 'Session generation changed; read its current state before releasing');
38
+ fail('SESSION_GENERATION_MISMATCH', 'Session generation changed; read its current state before retrying');
39
39
  }
40
40
  export function assertReleaseFacts(record, facts) {
41
41
  if (!record.agent_native_session_id)
@@ -0,0 +1,320 @@
1
+ import fs from 'node:fs/promises';
2
+ import path from 'node:path';
3
+ import { createHash } from 'node:crypto';
4
+ import { updateArchitectureField } from './fieldMutation.js';
5
+ import { ARCHITECTURE_FIELDS, ARCHITECTURE_FILE, analysisFile, architectureSourceDiagram, buildArchitecturePrompt, buildOmmScanPrompt, parseArchitecture } from './document.js';
6
+ import { ArchitectureStore } from './store.js';
7
+ import { parseFlowchart } from './flowchart.js';
8
+ import { diffMermaid } from './mermaidDiff.js';
9
+ import { diffArchitecture } from './documentDiff.js';
10
+ export const ARCHITECTURE_HELP = `Termdock architecture — recursive code architecture documents
11
+ Usage: td architecture <command> [--project <directory>] [--file <map.json>] [--format native|omm]
12
+ prompt [--language en|zh] Print the recursive analysis instructions
13
+ setup [claude|codex|cursor|openclaw|antigravity] [--teardown]
14
+ init | list | status Initialize or inspect project maps
15
+ tree [perspective/element] Browse the recursive document tree
16
+ read <element> <field> Read a field
17
+ write <element> <field> <text|-> Write a field (stdin with -)
18
+ show <element> Read all fields and metadata
19
+ delete <element> Delete that element and descendants
20
+ save <json|-> Validate and atomically save a native map, retaining history
21
+ validate [element] Check diagrams, documents and references
22
+ refs <element> Show incoming/outgoing and cross-perspective references
23
+ diff [element] | history Show changes and previous versions
24
+ config language [en|zh|...] Read/write the .omm content language
25
+ export [--format omm] Export native JSON or a portable .omm file bundle
26
+ import <json|-> Import a native map or a .omm file bundle
27
+ view Print the native Termdock viewer link
28
+ Fields: description, diagram, context, constraint, concern, todo, note.
29
+ Examples: td architecture prompt --project .
30
+ td architecture write --format omm overall-architecture/auth description -
31
+ td architecture save --file .termdock/architecture.json -`;
32
+ function elementPath(view, node) {
33
+ if (!node)
34
+ return view.id;
35
+ if (node.documentPath)
36
+ return node.documentPath;
37
+ const parts = [node.id];
38
+ let parent = node.parentId;
39
+ while (parent) {
40
+ parts.unshift(parent);
41
+ parent = view.nodes.find(item => item.id === parent)?.parentId;
42
+ }
43
+ return [view.id, ...parts].join('/');
44
+ }
45
+ function target(document, element) {
46
+ const [perspective, ...parts] = element.split('/');
47
+ const view = document.perspectives.find(view => view.id === perspective);
48
+ if (!view)
49
+ throw new Error(`Perspective not found: ${perspective}`);
50
+ let node;
51
+ for (const [index, part] of parts.entries()) {
52
+ const id = document.origin === 'omm' ? `e_${createHash('sha256').update([perspective, ...parts.slice(0, index + 1)].join('/')).digest('hex').slice(0, 20)}` : part;
53
+ const next = view.nodes.find(item => item.id === id && item.parentId === node?.id);
54
+ if (!next)
55
+ throw new Error(`Element not found: ${element}`);
56
+ node = next;
57
+ }
58
+ return { view, node, value: node ?? view };
59
+ }
60
+ export async function runArchitectureCli(args, io = { write: value => process.stdout.write(`${value}\n`), stdin: async () => { let text = ''; for await (const chunk of process.stdin) {
61
+ text += String(chunk);
62
+ if (text.length > 5_000_000)
63
+ throw new Error('Input exceeds the architecture limit');
64
+ } return text; } }) {
65
+ try {
66
+ const positional = [], options = {};
67
+ for (let index = 0; index < args.length; index++) {
68
+ const arg = args[index];
69
+ if (['--project', '--file', '--format', '--language'].includes(arg)) {
70
+ if (!args[index + 1] || args[index + 1].startsWith('--'))
71
+ throw new Error(`Missing value for ${arg}`);
72
+ options[arg.slice(2)] = args[++index];
73
+ }
74
+ else if (['--teardown', '--list', '--help'].includes(arg))
75
+ options[arg.slice(2)] = 'true';
76
+ else if (arg.startsWith('--'))
77
+ throw new Error(`Unknown option: ${arg}`);
78
+ else
79
+ positional.push(arg);
80
+ }
81
+ const [command = 'help', element, field, ...content] = positional;
82
+ if (command === 'help' || options.help) {
83
+ io.write(ARCHITECTURE_HELP);
84
+ return 0;
85
+ }
86
+ const root = await fs.realpath(path.resolve(options.project ?? process.cwd()));
87
+ if (!(await fs.stat(root)).isDirectory())
88
+ throw new Error('Project root must be a directory');
89
+ const store = new ArchitectureStore(root);
90
+ const omm = options.format === 'omm' || options.file === '.omm';
91
+ if (options.format && !['native', 'omm'].includes(options.format))
92
+ throw new Error('Format must be native or omm');
93
+ const file = options.file ?? (omm ? '.omm' : ARCHITECTURE_FILE);
94
+ const instructions = async () => {
95
+ const language = options.language ?? (omm ? (await store.config()).language : 'en');
96
+ return omm ? buildOmmScanPrompt(root, language) : buildArchitecturePrompt(root, language === 'zh' ? 'zh' : 'en');
97
+ };
98
+ const input = async (values) => values[0] === '-' ? io.stdin() : values.join(' ');
99
+ const json = (value) => io.write(JSON.stringify(value, null, 2));
100
+ if (command === 'prompt' || command === 'scan') {
101
+ io.write(await instructions());
102
+ return 0;
103
+ }
104
+ if (command === 'setup') {
105
+ const platforms = { claude: '.claude/skills', codex: '.agents/skills', cursor: '.cursor/skills', openclaw: '.openclaw/skills', antigravity: '.agent/skills' };
106
+ if (options.list) {
107
+ json(Object.keys(platforms));
108
+ return 0;
109
+ }
110
+ const selected = element ? [element] : Object.keys(platforms);
111
+ if (selected.some(platform => !platforms[platform]))
112
+ throw new Error('Unknown AI platform');
113
+ const marker = '<!-- Termdock architecture skill -->';
114
+ for (const platform of selected) {
115
+ const relative = `${platforms[platform]}/termdock-architecture/SKILL.md`, destination = await store.bounded(relative, true);
116
+ let existing = '';
117
+ try {
118
+ existing = await fs.readFile(destination, 'utf8');
119
+ }
120
+ catch (error) {
121
+ if (error.code !== 'ENOENT')
122
+ throw error;
123
+ }
124
+ if (existing && !existing.includes(marker))
125
+ throw new Error(`Refusing to overwrite an unrelated skill: ${relative}`);
126
+ if (options.teardown) {
127
+ if (existing.includes(marker))
128
+ await fs.unlink(destination);
129
+ io.write(`Removed ${relative}`);
130
+ continue;
131
+ }
132
+ const prompt = await instructions();
133
+ await fs.writeFile(destination, `---\nname: termdock-architecture\ndescription: Recursively analyze or update this project's Termdock code architecture.\n---\n${marker}\n\n${prompt}\n`, { mode: 0o600 });
134
+ io.write(`Installed ${relative}`);
135
+ }
136
+ return 0;
137
+ }
138
+ if (command === 'config') {
139
+ if (element !== 'language')
140
+ throw new Error('Use config language [code]');
141
+ json(await store.config(field));
142
+ return 0;
143
+ }
144
+ if (command === 'init') {
145
+ await store.config();
146
+ if (omm)
147
+ await store.config(options.language ?? 'en');
148
+ io.write('Ready. Use td architecture prompt, or Generate in the Architecture panel.');
149
+ return 0;
150
+ }
151
+ if (command === 'list') {
152
+ json(await store.list());
153
+ return 0;
154
+ }
155
+ if (command === 'save' || command === 'import') {
156
+ const raw = await input(positional.slice(1));
157
+ if (!raw)
158
+ throw new Error('Supply JSON or - for stdin');
159
+ const value = JSON.parse(raw);
160
+ if (value?.format === 'termdock-omm-bundle') {
161
+ await store.importOmmBundle(value);
162
+ json(await store.read('.omm'));
163
+ }
164
+ else {
165
+ const document = parseArchitecture(raw);
166
+ json(await store.save(options.file ?? (document.analysis ? analysisFile(document.analysis) : ARCHITECTURE_FILE), document));
167
+ }
168
+ return 0;
169
+ }
170
+ if (command === 'export' && omm) {
171
+ const source = options.file && options.file !== '.omm' ? (await store.read(options.file)).document : undefined;
172
+ if (source === null)
173
+ throw new Error('Architecture not found');
174
+ json(await store.exportOmmBundle(source));
175
+ return 0;
176
+ }
177
+ if (command === 'delete' && omm) {
178
+ if (!element)
179
+ throw new Error('Supply an element path');
180
+ await store.deleteOmmElement(element);
181
+ io.write(`Deleted ${element}`);
182
+ return 0;
183
+ }
184
+ if (command === 'write' && omm) {
185
+ if (!element || !ARCHITECTURE_FIELDS.includes(field))
186
+ throw new Error('Supply an element and valid field');
187
+ await store.writeOmmField(element, field, await input(content));
188
+ io.write(`Updated ${element}/${field}`);
189
+ return 0;
190
+ }
191
+ const loaded = await store.read(file), document = loaded.document;
192
+ if (!document)
193
+ throw new Error('No saved architecture. Generate one first, or select --format omm.');
194
+ if (command === 'export') {
195
+ json(document);
196
+ return 0;
197
+ }
198
+ if (command === 'status') {
199
+ json({ file, generatedAt: document.generatedAt, meta: document.meta, perspectives: document.perspectives.map(view => ({ id: view.id, nodes: view.nodes.length, edges: view.edges.length })) });
200
+ return 0;
201
+ }
202
+ if (command === 'history') {
203
+ json(await store.history(file));
204
+ return 0;
205
+ }
206
+ if (command === 'tree' && document.origin === 'omm') {
207
+ for (const entry of await store.ommElements())
208
+ if (!element || entry === element || entry.startsWith(`${element}/`))
209
+ io.write(`${' '.repeat(entry.split('/').length - 1)}${entry.split('/').pop()}`);
210
+ return 0;
211
+ }
212
+ if (command === 'tree') {
213
+ const views = element ? [target(document, element).view] : document.perspectives;
214
+ for (const view of views) {
215
+ io.write(view.id);
216
+ const walk = (parent, prefix) => { for (const node of view.nodes.filter(node => node.parentId === parent)) {
217
+ io.write(`${prefix}${node.id} — ${node.title}`);
218
+ walk(node.id, `${prefix} `);
219
+ } };
220
+ walk(element ? target(document, element).node?.id : undefined, ' ');
221
+ }
222
+ return 0;
223
+ }
224
+ if (command === 'validate') {
225
+ const issues = [];
226
+ if (element)
227
+ target(document, element);
228
+ for (const view of document.perspectives) {
229
+ for (const item of [view, ...view.nodes]) {
230
+ const key = elementPath(view, item === view ? undefined : item);
231
+ if (element && key !== element && !key.startsWith(`${element}/`))
232
+ continue;
233
+ if (!item.description && !item.summary)
234
+ issues.push({ element: key, message: 'Missing description' });
235
+ if (item.diagram) {
236
+ const diagram = parseFlowchart(item.diagram);
237
+ for (const issue of diagram.issues)
238
+ issues.push({ element: key, message: issue });
239
+ for (const node of diagram.nodes)
240
+ if (node.ref && (!document.perspectives.some(other => other.id === node.ref) || node.ref === view.id))
241
+ issues.push({ element: key, message: `Unresolved or self-referencing perspective: ${node.ref}` });
242
+ }
243
+ }
244
+ }
245
+ json({ valid: !issues.length, issues });
246
+ return issues.length ? 1 : 0;
247
+ }
248
+ if (command === 'diff' && !element) {
249
+ json(await store.history(file));
250
+ return 0;
251
+ }
252
+ if (command === 'view') {
253
+ io.write(`Open Termdock → this project → Architecture, or https://localhost:9834/?architecture=${encodeURIComponent(JSON.stringify({ root, file }))}`);
254
+ return 0;
255
+ }
256
+ if (!element)
257
+ throw new Error('Element path is required');
258
+ const selected = target(document, element);
259
+ if (command === 'delete') {
260
+ const removed = new Set();
261
+ if (!selected.node)
262
+ document.perspectives = document.perspectives.filter(view => view.id !== selected.view.id);
263
+ else {
264
+ removed.add(selected.node.id);
265
+ for (let index = 0; index < selected.view.nodes.length; index++)
266
+ for (const node of selected.view.nodes)
267
+ if (node.parentId && removed.has(node.parentId))
268
+ removed.add(node.id);
269
+ selected.view.nodes = selected.view.nodes.filter(node => !removed.has(node.id));
270
+ selected.view.edges = selected.view.edges.filter(edge => !removed.has(edge.from) && !removed.has(edge.to));
271
+ }
272
+ // Validation refuses dangling references and an empty document.
273
+ await store.save(file, document, loaded.revision);
274
+ io.write(`Deleted ${element}`);
275
+ return 0;
276
+ }
277
+ if (command === 'show') {
278
+ json(selected.value);
279
+ return 0;
280
+ }
281
+ if (command === 'read') {
282
+ if (!ARCHITECTURE_FIELDS.includes(field))
283
+ throw new Error('Invalid field');
284
+ io.write(selected.value[field] ?? (field === 'description' ? selected.value.summary : field === 'diagram' ? architectureSourceDiagram(selected.view, selected.node?.id) : ''));
285
+ return 0;
286
+ }
287
+ if (command === 'write') {
288
+ if (!ARCHITECTURE_FIELDS.includes(field))
289
+ throw new Error('Invalid field');
290
+ const updated = updateArchitectureField(document, selected.view.id, selected.node?.id, field, await input(content));
291
+ await store.save(file, updated, loaded.revision);
292
+ io.write(`Updated ${element}/${field}`);
293
+ return 0;
294
+ }
295
+ if (command === 'refs') {
296
+ const reference = (perspective, id) => {
297
+ const view = document.perspectives.find(view => view.id === perspective);
298
+ const node = id ? view.nodes.find(node => node.id === id) : undefined;
299
+ return { perspective, ...(id ? { node: id } : {}), element: elementPath(view, node), title: node?.title ?? view.title };
300
+ };
301
+ const connections = (selected.node ? selected.view.edges.filter(edge => edge.from === selected.node.id || edge.to === selected.node.id) : selected.view.edges).map(edge => ({ ...edge, fromElement: elementPath(selected.view, selected.view.nodes.find(node => node.id === edge.from)), toElement: elementPath(selected.view, selected.view.nodes.find(node => node.id === edge.to)) }));
302
+ json({ outgoing: (selected.node?.references ?? []).map(ref => reference(ref.perspective, ref.node)), incoming: document.perspectives.flatMap(view => view.nodes.filter(node => node.references?.some(ref => ref.perspective === selected.view.id && (!ref.node || ref.node === selected.node?.id))).map(node => reference(view.id, node.id))), connections });
303
+ return 0;
304
+ }
305
+ if (command === 'diff') {
306
+ if (selected.value.meta?.previousDiagram && selected.value.diagram)
307
+ json(diffMermaid(selected.value.meta.previousDiagram, selected.value.diagram));
308
+ else {
309
+ const versions = await store.history(file);
310
+ json(versions[0] ? diffArchitecture(await store.historical(file, versions[0].id), document).filter(change => change.perspective === selected.view.id && (!selected.node || change.node === selected.node.id)) : []);
311
+ }
312
+ return 0;
313
+ }
314
+ throw new Error(`Unknown architecture command: ${command}`);
315
+ }
316
+ catch (error) {
317
+ io.write(`Error: ${error instanceof Error ? error.message : String(error)}`);
318
+ return 1;
319
+ }
320
+ }