termdock 1.4.308 → 1.4.310
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.
- package/README.en.md +3 -1
- package/README.md +3 -1
- package/THIRD_PARTY_NOTICES.md +30 -0
- package/dist/client/assets/{App-ggIA_xqR.js → App-CytIMrFr.js} +62 -55
- package/dist/client/assets/App-CytIMrFr.js.br +0 -0
- package/dist/client/assets/App-CytIMrFr.js.gz +0 -0
- package/dist/client/assets/ArchitecturePanel-BRTR2IsK.js +9 -0
- package/dist/client/assets/ArchitecturePanel-BRTR2IsK.js.br +0 -0
- package/dist/client/assets/ArchitecturePanel-BRTR2IsK.js.gz +0 -0
- package/dist/client/assets/{ArchitecturePanel-Cmpmp6FS.css → ArchitecturePanel-B_BDrrfR.css} +1 -1
- package/dist/client/assets/ArchitecturePanel-B_BDrrfR.css.br +0 -0
- package/dist/client/assets/ArchitecturePanel-B_BDrrfR.css.gz +0 -0
- package/dist/client/assets/{ChangeWalkthroughPanel-D1Puc7B3.js → ChangeWalkthroughPanel-Bm9Tvd6H.js} +2 -2
- package/dist/client/assets/ChangeWalkthroughPanel-Bm9Tvd6H.js.br +0 -0
- package/dist/client/assets/ChangeWalkthroughPanel-Bm9Tvd6H.js.gz +0 -0
- package/dist/client/assets/CollaborationMainWorkspace-BagYBDlJ.js +1 -0
- package/dist/client/assets/CollaborationMainWorkspace-BagYBDlJ.js.br +0 -0
- package/dist/client/assets/CollaborationMainWorkspace-BagYBDlJ.js.gz +0 -0
- package/dist/client/assets/CollaborationTaskContent-D7LXylWr.js +2 -0
- package/dist/client/assets/{ComputerControlView-D5Lw9sNA.js → ComputerControlView-CC6r2cD3.js} +2 -2
- package/dist/client/assets/ComputerControlView-CC6r2cD3.js.br +0 -0
- package/dist/client/assets/ComputerControlView-CC6r2cD3.js.gz +0 -0
- package/dist/client/assets/{DagPlayground-DYJrGfiG.js → DagPlayground-BqAadqBT.js} +1 -1
- package/dist/client/assets/DagPlayground-BqAadqBT.js.br +0 -0
- package/dist/client/assets/DagPlayground-BqAadqBT.js.gz +0 -0
- package/dist/client/assets/{DiffLab-5zdcFW3z.js → DiffLab-CrEVLy-j.js} +1 -1
- package/dist/client/assets/DiffLab-CrEVLy-j.js.br +0 -0
- package/dist/client/assets/DiffLab-CrEVLy-j.js.gz +0 -0
- package/dist/client/assets/{DiffReview-BBBC_NjV.js → DiffReview-C8e2GQxb.js} +1 -1
- package/dist/client/assets/DiffReview-C8e2GQxb.js.br +0 -0
- package/dist/client/assets/DiffReview-C8e2GQxb.js.gz +0 -0
- package/dist/client/assets/{DiffReviewLab-CbhosFSB.js → DiffReviewLab-RQ1NmpZE.js} +2 -2
- package/dist/client/assets/DiffReviewLab-RQ1NmpZE.js.br +0 -0
- package/dist/client/assets/DiffReviewLab-RQ1NmpZE.js.gz +0 -0
- package/dist/client/assets/{DiffViewer-BuQwFQ4V.js → DiffViewer-KljgMa9h.js} +8 -8
- package/dist/client/assets/DiffViewer-KljgMa9h.js.br +0 -0
- package/dist/client/assets/DiffViewer-KljgMa9h.js.gz +0 -0
- package/dist/client/assets/{ModelPreview-nO2VmqdP.js → ModelPreview-B9UR1TR3.js} +1 -1
- package/dist/client/assets/ModelPreview-B9UR1TR3.js.br +0 -0
- package/dist/client/assets/ModelPreview-B9UR1TR3.js.gz +0 -0
- package/dist/client/assets/RightSidebar-DSH93gN5.js +1677 -0
- package/dist/client/assets/RightSidebar-DSH93gN5.js.br +0 -0
- package/dist/client/assets/RightSidebar-DSH93gN5.js.gz +0 -0
- package/dist/client/assets/{abnfDiagram-VCTEODGH-yi0K8GDG.js → abnfDiagram-VCTEODGH-WFUf9n1A.js} +1 -1
- package/dist/client/assets/abnfDiagram-VCTEODGH-WFUf9n1A.js.br +0 -0
- package/dist/client/assets/abnfDiagram-VCTEODGH-WFUf9n1A.js.gz +0 -0
- package/dist/client/assets/{app-B6FdOF6K.js → app-Bey8S6UU.js} +4 -4
- package/dist/client/assets/app-Bey8S6UU.js.br +0 -0
- package/dist/client/assets/app-Bey8S6UU.js.gz +0 -0
- package/dist/client/assets/{arc-_nLI_-XZ.js → arc-BXKxIsA3.js} +1 -1
- package/dist/client/assets/arc-BXKxIsA3.js.br +0 -0
- package/dist/client/assets/arc-BXKxIsA3.js.gz +0 -0
- package/dist/client/assets/{architectureDiagram-5GKGNRK7-CikrA78O.js → architectureDiagram-5GKGNRK7-DAfRrSxr.js} +1 -1
- package/dist/client/assets/architectureDiagram-5GKGNRK7-DAfRrSxr.js.br +0 -0
- package/dist/client/assets/architectureDiagram-5GKGNRK7-DAfRrSxr.js.gz +0 -0
- package/dist/client/assets/{blockDiagram-I7D4REHJ-CWJq6qJ7.js → blockDiagram-I7D4REHJ-1HbSy7rb.js} +1 -1
- package/dist/client/assets/blockDiagram-I7D4REHJ-1HbSy7rb.js.br +0 -0
- package/dist/client/assets/blockDiagram-I7D4REHJ-1HbSy7rb.js.gz +0 -0
- package/dist/client/assets/{c4Diagram-7LVT6UL2-gzPzLGvs.js → c4Diagram-7LVT6UL2-Dxwui-M_.js} +1 -1
- package/dist/client/assets/c4Diagram-7LVT6UL2-Dxwui-M_.js.br +0 -0
- package/dist/client/assets/c4Diagram-7LVT6UL2-Dxwui-M_.js.gz +0 -0
- package/dist/client/assets/channel-Dkh0SMv-.js +1 -0
- package/dist/client/assets/{chunk-2Q5K7J3B-CfX9l18E.js → chunk-2Q5K7J3B-CJSdJ_A1.js} +1 -1
- package/dist/client/assets/{chunk-5VM5RSS4-JSV1yrXM.js → chunk-5VM5RSS4-BNEXn4bI.js} +1 -1
- package/dist/client/assets/{chunk-F27PBJKO-CQ0LXeap.js → chunk-F27PBJKO-BaM6iLMb.js} +1 -1
- package/dist/client/assets/chunk-F27PBJKO-BaM6iLMb.js.br +0 -0
- package/dist/client/assets/chunk-F27PBJKO-BaM6iLMb.js.gz +0 -0
- package/dist/client/assets/{chunk-IMKFNOWR-CJOEPkK9.js → chunk-IMKFNOWR-DxPJBdLq.js} +1 -1
- package/dist/client/assets/chunk-IMKFNOWR-DxPJBdLq.js.br +0 -0
- package/dist/client/assets/chunk-IMKFNOWR-DxPJBdLq.js.gz +0 -0
- package/dist/client/assets/{chunk-JWPE2WC7-Dpp7Xu_E.js → chunk-JWPE2WC7-BwEOSoiu.js} +1 -1
- package/dist/client/assets/{chunk-POPQ4Y6H-9hDa1b8z.js → chunk-POPQ4Y6H-CbYcBz8G.js} +1 -1
- package/dist/client/assets/{chunk-SVP7TREG-BskkG9gg.js → chunk-SVP7TREG-CpnycZ3K.js} +1 -1
- package/dist/client/assets/chunk-SVP7TREG-CpnycZ3K.js.br +0 -0
- package/dist/client/assets/chunk-SVP7TREG-CpnycZ3K.js.gz +0 -0
- package/dist/client/assets/{chunk-TICWLB2K-DyzuP-9I.js → chunk-TICWLB2K-5oWwjAOF.js} +1 -1
- package/dist/client/assets/chunk-TICWLB2K-5oWwjAOF.js.br +0 -0
- package/dist/client/assets/chunk-TICWLB2K-5oWwjAOF.js.gz +0 -0
- package/dist/client/assets/{chunk-XXDRQBXY-C31_1i6z.js → chunk-XXDRQBXY-VWUm4Sz5.js} +1 -1
- package/dist/client/assets/classDiagram-ZZMXUADV-DqvmSdwt.js +1 -0
- package/dist/client/assets/classDiagram-v2-VYDZK3BY-DqvmSdwt.js +1 -0
- package/dist/client/assets/{cose-bilkent-JH36ORCC-Bm-ESDOc.js → cose-bilkent-JH36ORCC-gpF5Tw44.js} +1 -1
- package/dist/client/assets/cose-bilkent-JH36ORCC-gpF5Tw44.js.br +0 -0
- package/dist/client/assets/cose-bilkent-JH36ORCC-gpF5Tw44.js.gz +0 -0
- package/dist/client/assets/{cynefin-OW5HDTMX-DbFWAPvX.js → cynefin-OW5HDTMX-HFr7zRQ0.js} +1 -1
- package/dist/client/assets/cynefin-OW5HDTMX-HFr7zRQ0.js.br +0 -0
- package/dist/client/assets/cynefin-OW5HDTMX-HFr7zRQ0.js.gz +0 -0
- package/dist/client/assets/{cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js → cynefinDiagram-5FMLGOSQ-LccKgJj0.js} +1 -1
- package/dist/client/assets/cynefinDiagram-5FMLGOSQ-LccKgJj0.js.br +0 -0
- package/dist/client/assets/cynefinDiagram-5FMLGOSQ-LccKgJj0.js.gz +0 -0
- package/dist/client/assets/{dagre-GXQ25YYZ-D_5uEMjJ.js → dagre-GXQ25YYZ-C7eLk1r1.js} +1 -1
- package/dist/client/assets/dagre-GXQ25YYZ-C7eLk1r1.js.br +0 -0
- package/dist/client/assets/dagre-GXQ25YYZ-C7eLk1r1.js.gz +0 -0
- package/dist/client/assets/{diagram-S7CK7UJ4-DWVpndRP.js → diagram-S7CK7UJ4-DkWPZYAg.js} +1 -1
- package/dist/client/assets/diagram-S7CK7UJ4-DkWPZYAg.js.br +0 -0
- package/dist/client/assets/diagram-S7CK7UJ4-DkWPZYAg.js.gz +0 -0
- package/dist/client/assets/{diagram-UQ7AKVKN-DmYTya3w.js → diagram-UQ7AKVKN-DluTsMXz.js} +1 -1
- package/dist/client/assets/diagram-UQ7AKVKN-DluTsMXz.js.br +0 -0
- package/dist/client/assets/diagram-UQ7AKVKN-DluTsMXz.js.gz +0 -0
- package/dist/client/assets/{diagram-VSXAHHWV-BEA6kqNj.js → diagram-VSXAHHWV-BLXEmXmu.js} +1 -1
- package/dist/client/assets/diagram-VSXAHHWV-BLXEmXmu.js.br +0 -0
- package/dist/client/assets/diagram-VSXAHHWV-BLXEmXmu.js.gz +0 -0
- package/dist/client/assets/{diagram-VX7I27RA-CU9vP0P0.js → diagram-VX7I27RA-DO3J99WU.js} +1 -1
- package/dist/client/assets/diagram-VX7I27RA-DO3J99WU.js.br +0 -0
- package/dist/client/assets/diagram-VX7I27RA-DO3J99WU.js.gz +0 -0
- package/dist/client/assets/{diagram-Z3DM3KII-B_GvE2g-.js → diagram-Z3DM3KII-kvkSusTy.js} +1 -1
- package/dist/client/assets/diagram-Z3DM3KII-kvkSusTy.js.br +0 -0
- package/dist/client/assets/diagram-Z3DM3KII-kvkSusTy.js.gz +0 -0
- package/dist/client/assets/{ebnfDiagram-PWID7BFC-BLrPQuLE.js → ebnfDiagram-PWID7BFC-Bxd9hatc.js} +1 -1
- package/dist/client/assets/ebnfDiagram-PWID7BFC-Bxd9hatc.js.br +0 -0
- package/dist/client/assets/ebnfDiagram-PWID7BFC-Bxd9hatc.js.gz +0 -0
- package/dist/client/assets/{erDiagram-RLTQ6QDP-DlXgoyZ-.js → erDiagram-RLTQ6QDP-BWc3uM23.js} +1 -1
- package/dist/client/assets/erDiagram-RLTQ6QDP-BWc3uM23.js.br +0 -0
- package/dist/client/assets/erDiagram-RLTQ6QDP-BWc3uM23.js.gz +0 -0
- package/dist/client/assets/{flowDiagram-HODETNUW-fPHWxEDZ.js → flowDiagram-HODETNUW-BQhPtc9z.js} +1 -1
- package/dist/client/assets/flowDiagram-HODETNUW-BQhPtc9z.js.br +0 -0
- package/dist/client/assets/flowDiagram-HODETNUW-BQhPtc9z.js.gz +0 -0
- package/dist/client/assets/{ganttDiagram-EL5Y4UJY-B8MOv6ug.js → ganttDiagram-EL5Y4UJY-DzmTLgVr.js} +1 -1
- package/dist/client/assets/ganttDiagram-EL5Y4UJY-DzmTLgVr.js.br +0 -0
- package/dist/client/assets/ganttDiagram-EL5Y4UJY-DzmTLgVr.js.gz +0 -0
- package/dist/client/assets/{gestureArbiter-JW8vcVRm.js → gestureArbiter-BuNZMZ7A.js} +1 -1
- package/dist/client/assets/gestureArbiter-BuNZMZ7A.js.br +0 -0
- package/dist/client/assets/gestureArbiter-BuNZMZ7A.js.gz +0 -0
- package/dist/client/assets/{gitGraphDiagram-WWUBYQGX-lH9gSoFx.js → gitGraphDiagram-WWUBYQGX-r0Onfl7K.js} +1 -1
- package/dist/client/assets/gitGraphDiagram-WWUBYQGX-r0Onfl7K.js.br +0 -0
- package/dist/client/assets/gitGraphDiagram-WWUBYQGX-r0Onfl7K.js.gz +0 -0
- package/dist/client/assets/{index-CNY7CTVa.css → index-C6D5a-dg.css} +1 -1
- package/dist/client/assets/index-C6D5a-dg.css.br +0 -0
- package/dist/client/assets/{index-CNY7CTVa.css.gz → index-C6D5a-dg.css.gz} +0 -0
- package/dist/client/assets/{infoDiagram-27XIBGKW-CSG29Ty_.js → infoDiagram-27XIBGKW-C52jpDzv.js} +1 -1
- package/dist/client/assets/{ishikawaDiagram-5VMMS53U-CcwSE5qV.js → ishikawaDiagram-5VMMS53U-C-l0eHmO.js} +1 -1
- package/dist/client/assets/ishikawaDiagram-5VMMS53U-C-l0eHmO.js.br +0 -0
- package/dist/client/assets/ishikawaDiagram-5VMMS53U-C-l0eHmO.js.gz +0 -0
- package/dist/client/assets/{journeyDiagram-3NMN7TZE-CXFUeP2c.js → journeyDiagram-3NMN7TZE-DmhgEOjX.js} +1 -1
- package/dist/client/assets/journeyDiagram-3NMN7TZE-DmhgEOjX.js.br +0 -0
- package/dist/client/assets/journeyDiagram-3NMN7TZE-DmhgEOjX.js.gz +0 -0
- package/dist/client/assets/{kanban-definition-UXKFOSKX-KEHwljd2.js → kanban-definition-UXKFOSKX-BnZWlxIT.js} +1 -1
- package/dist/client/assets/kanban-definition-UXKFOSKX-BnZWlxIT.js.br +0 -0
- package/dist/client/assets/kanban-definition-UXKFOSKX-BnZWlxIT.js.gz +0 -0
- package/dist/client/assets/{layout-DqYx0MnO.js → layout-BrxPpC7u.js} +1 -1
- package/dist/client/assets/layout-BrxPpC7u.js.br +0 -0
- package/dist/client/assets/layout-BrxPpC7u.js.gz +0 -0
- package/dist/client/assets/{linear-BnG3XaJW.js → linear-DaEpqVcH.js} +1 -1
- package/dist/client/assets/linear-DaEpqVcH.js.br +0 -0
- package/dist/client/assets/linear-DaEpqVcH.js.gz +0 -0
- package/dist/client/assets/{mermaid.core-Ce00rdM6.js → mermaid.core-CidoOS12.js} +5 -5
- package/dist/client/assets/mermaid.core-CidoOS12.js.br +0 -0
- package/dist/client/assets/mermaid.core-CidoOS12.js.gz +0 -0
- package/dist/client/assets/{mindmap-definition-YA3MSWOX-D0hOW4SY.js → mindmap-definition-YA3MSWOX-Bpr3CVLy.js} +1 -1
- package/dist/client/assets/mindmap-definition-YA3MSWOX-Bpr3CVLy.js.br +0 -0
- package/dist/client/assets/mindmap-definition-YA3MSWOX-Bpr3CVLy.js.gz +0 -0
- package/dist/client/assets/passwordBootstrap-D7hFrc0r.js +2 -0
- package/dist/client/assets/passwordBootstrap-D7hFrc0r.js.br +0 -0
- package/dist/client/assets/passwordBootstrap-D7hFrc0r.js.gz +0 -0
- package/dist/client/assets/{pegDiagram-XKGWAZYB-UKp9t91x.js → pegDiagram-XKGWAZYB-Bw2JpSYn.js} +1 -1
- package/dist/client/assets/pegDiagram-XKGWAZYB-Bw2JpSYn.js.br +0 -0
- package/dist/client/assets/pegDiagram-XKGWAZYB-Bw2JpSYn.js.gz +0 -0
- package/dist/client/assets/{pieDiagram-E7YTZNPT-Dif97wbH.js → pieDiagram-E7YTZNPT-BaKc3ifQ.js} +1 -1
- package/dist/client/assets/pieDiagram-E7YTZNPT-BaKc3ifQ.js.br +0 -0
- package/dist/client/assets/pieDiagram-E7YTZNPT-BaKc3ifQ.js.gz +0 -0
- package/dist/client/assets/{quadrantDiagram-AXDQQJYC-BPyHtH91.js → quadrantDiagram-AXDQQJYC-B0Yi-dl9.js} +1 -1
- package/dist/client/assets/quadrantDiagram-AXDQQJYC-B0Yi-dl9.js.br +0 -0
- package/dist/client/assets/quadrantDiagram-AXDQQJYC-B0Yi-dl9.js.gz +0 -0
- package/dist/client/assets/{railroadDiagram-O6MQD6OU-Wleq9LmS.js → railroadDiagram-O6MQD6OU-DCcCQofU.js} +1 -1
- package/dist/client/assets/railroadDiagram-O6MQD6OU-DCcCQofU.js.br +0 -0
- package/dist/client/assets/railroadDiagram-O6MQD6OU-DCcCQofU.js.gz +0 -0
- package/dist/client/assets/{rdpSession-CobFMSUs.js → rdpSession-DY81W5BY.js} +1 -1
- package/dist/client/assets/rdpSession-DY81W5BY.js.br +0 -0
- package/dist/client/assets/rdpSession-DY81W5BY.js.gz +0 -0
- package/dist/client/assets/{referenceLongPress-bZ0xp-v2.js → referenceLongPress-CAzWqXsY.js} +1 -1
- package/dist/client/assets/referenceLongPress-CAzWqXsY.js.br +0 -0
- package/dist/client/assets/referenceLongPress-CAzWqXsY.js.gz +0 -0
- package/dist/client/assets/{requirementDiagram-BXWQKSXE-BL4pp0Ta.js → requirementDiagram-BXWQKSXE-CEJFRPWH.js} +1 -1
- package/dist/client/assets/requirementDiagram-BXWQKSXE-CEJFRPWH.js.br +0 -0
- package/dist/client/assets/requirementDiagram-BXWQKSXE-CEJFRPWH.js.gz +0 -0
- package/dist/client/assets/{sankeyDiagram-P5KCCOFB-CV1cKx37.js → sankeyDiagram-P5KCCOFB-B3Wk45FA.js} +1 -1
- package/dist/client/assets/sankeyDiagram-P5KCCOFB-B3Wk45FA.js.br +0 -0
- package/dist/client/assets/sankeyDiagram-P5KCCOFB-B3Wk45FA.js.gz +0 -0
- package/dist/client/assets/{sequenceDiagram-WJ2MYXX4-BF2InLwV.js → sequenceDiagram-WJ2MYXX4-BejEsITb.js} +1 -1
- package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BejEsITb.js.br +0 -0
- package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BejEsITb.js.gz +0 -0
- package/dist/client/assets/{sizeCapture-INFHLROL-CldUyStR.js → sizeCapture-INFHLROL-DZ5NJZnM.js} +1 -1
- package/dist/client/assets/sizeCapture-INFHLROL-DZ5NJZnM.js.br +0 -0
- package/dist/client/assets/sizeCapture-INFHLROL-DZ5NJZnM.js.gz +0 -0
- package/dist/client/assets/{sparkles-Cg-yPdE2.js → sparkles-DQGLdN2b.js} +1 -1
- package/dist/client/assets/{stateDiagram-D77RDMKH-CByehbEd.js → stateDiagram-D77RDMKH-D8SSEwHa.js} +1 -1
- package/dist/client/assets/stateDiagram-D77RDMKH-D8SSEwHa.js.br +0 -0
- package/dist/client/assets/stateDiagram-D77RDMKH-D8SSEwHa.js.gz +0 -0
- package/dist/client/assets/stateDiagram-v2-MP3YSRHH-D1KQOetv.js +1 -0
- package/dist/client/assets/{swimlanes-42K2YHIH--1_7YTL4.js → swimlanes-42K2YHIH-Dow-EKMG.js} +1 -1
- package/dist/client/assets/swimlanes-42K2YHIH-Dow-EKMG.js.br +0 -0
- package/dist/client/assets/swimlanes-42K2YHIH-Dow-EKMG.js.gz +0 -0
- package/dist/client/assets/swimlanesDiagram-VR7AAH4N-DQbZCzq9.js +8 -0
- package/dist/client/assets/{timeline-definition-24CTP7MA-CXfXJFK6.js → timeline-definition-24CTP7MA-DpQ9D5f6.js} +1 -1
- package/dist/client/assets/timeline-definition-24CTP7MA-DpQ9D5f6.js.br +0 -0
- package/dist/client/assets/timeline-definition-24CTP7MA-DpQ9D5f6.js.gz +0 -0
- package/dist/client/assets/{triangle-alert-CbMRJ6sx.js → triangle-alert-Bdf_dBch.js} +1 -1
- package/dist/client/assets/{vennDiagram-4TSXK5OY-byr6UQpL.js → vennDiagram-4TSXK5OY-DoemAmM2.js} +1 -1
- package/dist/client/assets/vennDiagram-4TSXK5OY-DoemAmM2.js.br +0 -0
- package/dist/client/assets/vennDiagram-4TSXK5OY-DoemAmM2.js.gz +0 -0
- package/dist/client/assets/{videoCompression-ivJAy00d.js → videoCompression-Bg4gUQUf.js} +1 -1
- package/dist/client/assets/videoCompression-Bg4gUQUf.js.br +0 -0
- package/dist/client/assets/videoCompression-Bg4gUQUf.js.gz +0 -0
- package/dist/client/assets/{wardleyDiagram-VM6X3IG4-FJduk-7s.js → wardleyDiagram-VM6X3IG4-MernEZ54.js} +1 -1
- package/dist/client/assets/wardleyDiagram-VM6X3IG4-MernEZ54.js.br +0 -0
- package/dist/client/assets/wardleyDiagram-VM6X3IG4-MernEZ54.js.gz +0 -0
- package/dist/client/assets/{xychartDiagram-S5SC5T6Z-Ct1fBPFS.js → xychartDiagram-S5SC5T6Z-CzO3HEHD.js} +1 -1
- package/dist/client/assets/xychartDiagram-S5SC5T6Z-CzO3HEHD.js.br +0 -0
- package/dist/client/assets/xychartDiagram-S5SC5T6Z-CzO3HEHD.js.gz +0 -0
- package/dist/client/index.html +2 -2
- package/dist/client/index.html.br +0 -0
- package/dist/client/index.html.gz +0 -0
- package/dist/client/sw.js +1 -1
- package/dist/client/sw.js.br +0 -0
- package/dist/client/sw.js.gz +0 -0
- package/dist/server/agent/collaborationCli.js +21 -5
- package/dist/server/agent/collaborationStore.js +5 -0
- package/dist/server/agent/integrationCli.js +60 -2
- package/dist/server/agent/integrationServer.js +22 -2
- package/dist/server/agent/integrationSessions.js +250 -19
- package/dist/server/agent/integrationStore.js +1 -1
- package/dist/server/agent/sessionLifecycle.js +81 -0
- package/dist/server/agent/sessionResumeConfiguration.js +32 -0
- package/dist/server/architecture/cli.js +295 -0
- package/dist/server/architecture/document.js +328 -0
- package/dist/server/architecture/documentDiff.js +34 -0
- package/dist/server/architecture/fieldMutation.js +52 -0
- package/dist/server/architecture/flowchart.js +62 -0
- package/dist/server/architecture/mermaidDiff.js +85 -0
- package/dist/server/architecture/routes.js +117 -0
- package/dist/server/architecture/store.js +502 -0
- package/dist/server/cli.js +7 -1
- package/dist/server/entry.js +2 -0
- package/dist/server/federation/accessPolicy.js +9 -1
- package/dist/server/routes/terminal.js +75 -1
- package/docs/integrations.md +178 -3
- package/package.json +3 -1
- package/runtime-manifest.json +4 -4
- package/dist/client/assets/App-ggIA_xqR.js.br +0 -0
- package/dist/client/assets/App-ggIA_xqR.js.gz +0 -0
- package/dist/client/assets/ArchitecturePanel-Cmpmp6FS.css.br +0 -0
- package/dist/client/assets/ArchitecturePanel-Cmpmp6FS.css.gz +0 -0
- package/dist/client/assets/ArchitecturePanel-CoBspW_C.js +0 -12
- package/dist/client/assets/ArchitecturePanel-CoBspW_C.js.br +0 -0
- package/dist/client/assets/ArchitecturePanel-CoBspW_C.js.gz +0 -0
- package/dist/client/assets/ChangeWalkthroughPanel-D1Puc7B3.js.br +0 -0
- package/dist/client/assets/ChangeWalkthroughPanel-D1Puc7B3.js.gz +0 -0
- package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js +0 -1
- package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js.br +0 -0
- package/dist/client/assets/CollaborationMainWorkspace-BPyK5Xs8.js.gz +0 -0
- package/dist/client/assets/CollaborationTaskContent-CTSJJqze.js +0 -2
- package/dist/client/assets/ComputerControlView-D5Lw9sNA.js.br +0 -0
- package/dist/client/assets/ComputerControlView-D5Lw9sNA.js.gz +0 -0
- package/dist/client/assets/DagPlayground-DYJrGfiG.js.br +0 -0
- package/dist/client/assets/DagPlayground-DYJrGfiG.js.gz +0 -0
- package/dist/client/assets/DiffLab-5zdcFW3z.js.br +0 -0
- package/dist/client/assets/DiffLab-5zdcFW3z.js.gz +0 -0
- package/dist/client/assets/DiffReview-BBBC_NjV.js.br +0 -0
- package/dist/client/assets/DiffReview-BBBC_NjV.js.gz +0 -0
- package/dist/client/assets/DiffReviewLab-CbhosFSB.js.br +0 -0
- package/dist/client/assets/DiffReviewLab-CbhosFSB.js.gz +0 -0
- package/dist/client/assets/DiffViewer-BuQwFQ4V.js.br +0 -0
- package/dist/client/assets/DiffViewer-BuQwFQ4V.js.gz +0 -0
- package/dist/client/assets/ModelPreview-nO2VmqdP.js.br +0 -0
- package/dist/client/assets/ModelPreview-nO2VmqdP.js.gz +0 -0
- package/dist/client/assets/RightSidebar-BoNzpS2K.js +0 -1677
- package/dist/client/assets/RightSidebar-BoNzpS2K.js.br +0 -0
- package/dist/client/assets/RightSidebar-BoNzpS2K.js.gz +0 -0
- package/dist/client/assets/abnfDiagram-VCTEODGH-yi0K8GDG.js.br +0 -0
- package/dist/client/assets/abnfDiagram-VCTEODGH-yi0K8GDG.js.gz +0 -0
- package/dist/client/assets/app-B6FdOF6K.js.br +0 -0
- package/dist/client/assets/app-B6FdOF6K.js.gz +0 -0
- package/dist/client/assets/arc-_nLI_-XZ.js.br +0 -0
- package/dist/client/assets/arc-_nLI_-XZ.js.gz +0 -0
- package/dist/client/assets/architectureDiagram-5GKGNRK7-CikrA78O.js.br +0 -0
- package/dist/client/assets/architectureDiagram-5GKGNRK7-CikrA78O.js.gz +0 -0
- package/dist/client/assets/blockDiagram-I7D4REHJ-CWJq6qJ7.js.br +0 -0
- package/dist/client/assets/blockDiagram-I7D4REHJ-CWJq6qJ7.js.gz +0 -0
- package/dist/client/assets/c4Diagram-7LVT6UL2-gzPzLGvs.js.br +0 -0
- package/dist/client/assets/c4Diagram-7LVT6UL2-gzPzLGvs.js.gz +0 -0
- package/dist/client/assets/channel-BYsFmOmF.js +0 -1
- package/dist/client/assets/chunk-F27PBJKO-CQ0LXeap.js.br +0 -0
- package/dist/client/assets/chunk-F27PBJKO-CQ0LXeap.js.gz +0 -0
- package/dist/client/assets/chunk-IMKFNOWR-CJOEPkK9.js.br +0 -0
- package/dist/client/assets/chunk-IMKFNOWR-CJOEPkK9.js.gz +0 -0
- package/dist/client/assets/chunk-SVP7TREG-BskkG9gg.js.br +0 -0
- package/dist/client/assets/chunk-SVP7TREG-BskkG9gg.js.gz +0 -0
- package/dist/client/assets/chunk-TICWLB2K-DyzuP-9I.js.br +0 -0
- package/dist/client/assets/chunk-TICWLB2K-DyzuP-9I.js.gz +0 -0
- package/dist/client/assets/classDiagram-ZZMXUADV-BnmZv6Ns.js +0 -1
- package/dist/client/assets/classDiagram-v2-VYDZK3BY-BnmZv6Ns.js +0 -1
- package/dist/client/assets/cose-bilkent-JH36ORCC-Bm-ESDOc.js.br +0 -0
- package/dist/client/assets/cose-bilkent-JH36ORCC-Bm-ESDOc.js.gz +0 -0
- package/dist/client/assets/cynefin-OW5HDTMX-DbFWAPvX.js.br +0 -0
- package/dist/client/assets/cynefin-OW5HDTMX-DbFWAPvX.js.gz +0 -0
- package/dist/client/assets/cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js.br +0 -0
- package/dist/client/assets/cynefinDiagram-5FMLGOSQ-Ca0IKRdH.js.gz +0 -0
- package/dist/client/assets/dagre-GXQ25YYZ-D_5uEMjJ.js.br +0 -0
- package/dist/client/assets/dagre-GXQ25YYZ-D_5uEMjJ.js.gz +0 -0
- package/dist/client/assets/diagram-S7CK7UJ4-DWVpndRP.js.br +0 -0
- package/dist/client/assets/diagram-S7CK7UJ4-DWVpndRP.js.gz +0 -0
- package/dist/client/assets/diagram-UQ7AKVKN-DmYTya3w.js.br +0 -0
- package/dist/client/assets/diagram-UQ7AKVKN-DmYTya3w.js.gz +0 -0
- package/dist/client/assets/diagram-VSXAHHWV-BEA6kqNj.js.br +0 -0
- package/dist/client/assets/diagram-VSXAHHWV-BEA6kqNj.js.gz +0 -0
- package/dist/client/assets/diagram-VX7I27RA-CU9vP0P0.js.br +0 -0
- package/dist/client/assets/diagram-VX7I27RA-CU9vP0P0.js.gz +0 -0
- package/dist/client/assets/diagram-Z3DM3KII-B_GvE2g-.js.br +0 -0
- package/dist/client/assets/diagram-Z3DM3KII-B_GvE2g-.js.gz +0 -0
- package/dist/client/assets/ebnfDiagram-PWID7BFC-BLrPQuLE.js.br +0 -0
- package/dist/client/assets/ebnfDiagram-PWID7BFC-BLrPQuLE.js.gz +0 -0
- package/dist/client/assets/erDiagram-RLTQ6QDP-DlXgoyZ-.js.br +0 -0
- package/dist/client/assets/erDiagram-RLTQ6QDP-DlXgoyZ-.js.gz +0 -0
- package/dist/client/assets/flowDiagram-HODETNUW-fPHWxEDZ.js.br +0 -0
- package/dist/client/assets/flowDiagram-HODETNUW-fPHWxEDZ.js.gz +0 -0
- package/dist/client/assets/ganttDiagram-EL5Y4UJY-B8MOv6ug.js.br +0 -0
- package/dist/client/assets/ganttDiagram-EL5Y4UJY-B8MOv6ug.js.gz +0 -0
- package/dist/client/assets/gestureArbiter-JW8vcVRm.js.br +0 -0
- package/dist/client/assets/gestureArbiter-JW8vcVRm.js.gz +0 -0
- package/dist/client/assets/gitGraphDiagram-WWUBYQGX-lH9gSoFx.js.br +0 -0
- package/dist/client/assets/gitGraphDiagram-WWUBYQGX-lH9gSoFx.js.gz +0 -0
- package/dist/client/assets/index-CNY7CTVa.css.br +0 -0
- package/dist/client/assets/ishikawaDiagram-5VMMS53U-CcwSE5qV.js.br +0 -0
- package/dist/client/assets/ishikawaDiagram-5VMMS53U-CcwSE5qV.js.gz +0 -0
- package/dist/client/assets/journeyDiagram-3NMN7TZE-CXFUeP2c.js.br +0 -0
- package/dist/client/assets/journeyDiagram-3NMN7TZE-CXFUeP2c.js.gz +0 -0
- package/dist/client/assets/kanban-definition-UXKFOSKX-KEHwljd2.js.br +0 -0
- package/dist/client/assets/kanban-definition-UXKFOSKX-KEHwljd2.js.gz +0 -0
- package/dist/client/assets/layout-DqYx0MnO.js.br +0 -0
- package/dist/client/assets/layout-DqYx0MnO.js.gz +0 -0
- package/dist/client/assets/linear-BnG3XaJW.js.br +0 -0
- package/dist/client/assets/linear-BnG3XaJW.js.gz +0 -0
- package/dist/client/assets/mermaid.core-Ce00rdM6.js.br +0 -0
- package/dist/client/assets/mermaid.core-Ce00rdM6.js.gz +0 -0
- package/dist/client/assets/mindmap-definition-YA3MSWOX-D0hOW4SY.js.br +0 -0
- package/dist/client/assets/mindmap-definition-YA3MSWOX-D0hOW4SY.js.gz +0 -0
- package/dist/client/assets/passwordBootstrap-Bncb8qF_.js +0 -2
- package/dist/client/assets/passwordBootstrap-Bncb8qF_.js.br +0 -0
- package/dist/client/assets/passwordBootstrap-Bncb8qF_.js.gz +0 -0
- package/dist/client/assets/pegDiagram-XKGWAZYB-UKp9t91x.js.br +0 -0
- package/dist/client/assets/pegDiagram-XKGWAZYB-UKp9t91x.js.gz +0 -0
- package/dist/client/assets/pieDiagram-E7YTZNPT-Dif97wbH.js.br +0 -0
- package/dist/client/assets/pieDiagram-E7YTZNPT-Dif97wbH.js.gz +0 -0
- package/dist/client/assets/quadrantDiagram-AXDQQJYC-BPyHtH91.js.br +0 -0
- package/dist/client/assets/quadrantDiagram-AXDQQJYC-BPyHtH91.js.gz +0 -0
- package/dist/client/assets/railroadDiagram-O6MQD6OU-Wleq9LmS.js.br +0 -0
- package/dist/client/assets/railroadDiagram-O6MQD6OU-Wleq9LmS.js.gz +0 -0
- package/dist/client/assets/rdpSession-CobFMSUs.js.br +0 -0
- package/dist/client/assets/rdpSession-CobFMSUs.js.gz +0 -0
- package/dist/client/assets/referenceLongPress-bZ0xp-v2.js.br +0 -0
- package/dist/client/assets/referenceLongPress-bZ0xp-v2.js.gz +0 -0
- package/dist/client/assets/requirementDiagram-BXWQKSXE-BL4pp0Ta.js.br +0 -0
- package/dist/client/assets/requirementDiagram-BXWQKSXE-BL4pp0Ta.js.gz +0 -0
- package/dist/client/assets/sankeyDiagram-P5KCCOFB-CV1cKx37.js.br +0 -0
- package/dist/client/assets/sankeyDiagram-P5KCCOFB-CV1cKx37.js.gz +0 -0
- package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BF2InLwV.js.br +0 -0
- package/dist/client/assets/sequenceDiagram-WJ2MYXX4-BF2InLwV.js.gz +0 -0
- package/dist/client/assets/sizeCapture-INFHLROL-CldUyStR.js.br +0 -0
- package/dist/client/assets/sizeCapture-INFHLROL-CldUyStR.js.gz +0 -0
- package/dist/client/assets/stateDiagram-D77RDMKH-CByehbEd.js.br +0 -0
- package/dist/client/assets/stateDiagram-D77RDMKH-CByehbEd.js.gz +0 -0
- package/dist/client/assets/stateDiagram-v2-MP3YSRHH-CTcrJ-w0.js +0 -1
- package/dist/client/assets/swimlanes-42K2YHIH--1_7YTL4.js.br +0 -0
- package/dist/client/assets/swimlanes-42K2YHIH--1_7YTL4.js.gz +0 -0
- package/dist/client/assets/swimlanesDiagram-VR7AAH4N-RSMV9AhO.js +0 -8
- package/dist/client/assets/timeline-definition-24CTP7MA-CXfXJFK6.js.br +0 -0
- package/dist/client/assets/timeline-definition-24CTP7MA-CXfXJFK6.js.gz +0 -0
- package/dist/client/assets/vennDiagram-4TSXK5OY-byr6UQpL.js.br +0 -0
- package/dist/client/assets/vennDiagram-4TSXK5OY-byr6UQpL.js.gz +0 -0
- package/dist/client/assets/videoCompression-ivJAy00d.js.br +0 -0
- package/dist/client/assets/videoCompression-ivJAy00d.js.gz +0 -0
- package/dist/client/assets/wardleyDiagram-VM6X3IG4-FJduk-7s.js.br +0 -0
- package/dist/client/assets/wardleyDiagram-VM6X3IG4-FJduk-7s.js.gz +0 -0
- package/dist/client/assets/xychartDiagram-S5SC5T6Z-Ct1fBPFS.js.br +0 -0
- package/dist/client/assets/xychartDiagram-S5SC5T6Z-Ct1fBPFS.js.gz +0 -0
|
@@ -40,7 +40,7 @@ const fileReads = new Set(['list', 'watch', 'search', 'read', 'git-blob', 'eda-p
|
|
|
40
40
|
const filePosts = new Set(['git-action', 'apply-hunk', 'upload', 'open-in-file-browser']);
|
|
41
41
|
const settings = new Set(['settings', 'toolbar-presets', 'program-detection', 'context-draft']);
|
|
42
42
|
const serviceReads = new Set(['update', 'auto-title/catalog', 'agent-hooks', 'agent-launchers', 'agent-plugins', 'quota', 'tmux/status', 'tmux/sessions', 'agent-resume-history']);
|
|
43
|
-
const reservedSessionIds = new Set(['fs', 'settings', 'client-state', 'session-inventory', 'operations', 'tmux', 'create', 'force-kill', 'serialize-state', 'agent-resume-history', 'toolbar-presets', 'context-draft', 'program-detection', 'update', 'quota', 'agent-hooks', 'agent-launchers', 'agent-plugins', 'agent-plugin-icon', 'auto-title', 'directory-suggestions']);
|
|
43
|
+
const reservedSessionIds = new Set(['architecture', 'fs', 'settings', 'client-state', 'session-inventory', 'operations', 'tmux', 'create', 'force-kill', 'serialize-state', 'agent-resume-history', 'toolbar-presets', 'context-draft', 'program-detection', 'update', 'quota', 'agent-hooks', 'agent-launchers', 'agent-plugins', 'agent-plugin-icon', 'auto-title', 'directory-suggestions']);
|
|
44
44
|
export function resolveAccessRequest(method, path) {
|
|
45
45
|
if (!isBusinessApiPath(method, path))
|
|
46
46
|
return null;
|
|
@@ -57,6 +57,14 @@ export function resolveAccessRequest(method, path) {
|
|
|
57
57
|
if (!pathname.startsWith(prefix))
|
|
58
58
|
return null;
|
|
59
59
|
const route = pathname.slice(prefix.length);
|
|
60
|
+
if (route.startsWith('architecture/')) {
|
|
61
|
+
const op = route.slice('architecture/'.length);
|
|
62
|
+
if (read && ['documents', 'document', 'history', 'version', 'bundle'].includes(op))
|
|
63
|
+
return { action: 'file.read' };
|
|
64
|
+
if (method === 'PUT' && ['document', 'field', 'bundle'].includes(op))
|
|
65
|
+
return { action: 'file.write' };
|
|
66
|
+
return null;
|
|
67
|
+
}
|
|
60
68
|
if (route.startsWith('fs/')) {
|
|
61
69
|
const op = route.slice(3);
|
|
62
70
|
if (read && (fileReads.has(op) || /^preview\/.+/.test(op)))
|
|
@@ -2,6 +2,8 @@ import { collaborationSessionDisplayName } from '../utils/sessionDisplayName.js'
|
|
|
2
2
|
import { integrationError } from '../agent/integrationStore.js';
|
|
3
3
|
import { assertNativeResumeAvailable, collectNativeResumeOwnerCandidates } from '../agent/nativeResumeOwner.js';
|
|
4
4
|
import { readNativeProcessIdentity } from '../agent/nativeProcessIdentity.js';
|
|
5
|
+
import { releaseSessionRuntime } from '../agent/sessionLifecycle.js';
|
|
6
|
+
import { resumeConfigurationFingerprint } from '../agent/sessionResumeConfiguration.js';
|
|
5
7
|
import { integrationLaunchCommand } from '../agent/integrationSessions.js';
|
|
6
8
|
import { ensureTeam } from '../agent/collaborationTeam.js';
|
|
7
9
|
import { androidRecordings } from '../android/recording.js';
|
|
@@ -39,7 +41,7 @@ import { inspectLinuxInotifyUsage, isWatchResourceExhaustion } from '../utils/fi
|
|
|
39
41
|
import { writeResponseChunk } from '../utils/httpResponse.js';
|
|
40
42
|
import { getFocusSequence, removeClientFocusState, scanFocusTrackingMode, setClientFocusState, } from '../utils/tmuxFocus.js';
|
|
41
43
|
import { extractProgramLabelFromArgs, normalizeProgramName, normalizeTmuxMetadataProgram, selectTmuxForegroundProgram, } from '../utils/tmuxProgramDetection.js';
|
|
42
|
-
import { agentBySlug, buildResumeCommand, detectAgentFromCommand, inferResumeSessionId, getPluginNativeIdentityConfig, listAgents, } from '../agent/registry.js';
|
|
44
|
+
import { agentBySlug, buildResumeCommand, detectAgentFromCommand, inferResumeSessionId, getPluginNativeIdentityConfig, getPluginResumeConfig, listAgents, } from '../agent/registry.js';
|
|
43
45
|
import { applyAgentEvent, agentEventMatchesCurrentAgent, defaultAgentSessionState, parseAgentEvent, } from '../agent/session.js';
|
|
44
46
|
import { canRestoreDeadAgentShell, isConfirmedAgentResumeProcess, normalizePersistedAgentResumeInfo, } from '../agent/resumePersistence.js';
|
|
45
47
|
import { AgentResumeHistoryStore } from '../agent/resumeHistory.js';
|
|
@@ -1861,10 +1863,76 @@ function integrationTerminalRecord(record) {
|
|
|
1861
1863
|
integrationError('SESSION_IDENTITY_MISMATCH', 'Owned TD terminal binding changed', 409);
|
|
1862
1864
|
return terminal;
|
|
1863
1865
|
}
|
|
1866
|
+
async function integrationTmuxPresent(record) {
|
|
1867
|
+
try {
|
|
1868
|
+
await runTmux(['has-session', '-t', `=wt-integration-${record.session_id}`]);
|
|
1869
|
+
return true;
|
|
1870
|
+
}
|
|
1871
|
+
catch (error) {
|
|
1872
|
+
if (/can't find session|no server running|no sessions|error connecting.*No such file/i.test(getErrorMessage(error)))
|
|
1873
|
+
return false;
|
|
1874
|
+
throw error;
|
|
1875
|
+
}
|
|
1876
|
+
}
|
|
1864
1877
|
export const integrationSessionAdapter = {
|
|
1865
1878
|
subscribe(listener) { integrationSessionObservers.add(listener); return () => { integrationSessionObservers.delete(listener); }; },
|
|
1866
1879
|
registerDeliveryGuard(guard) { integrationDeliveryGuard = guard; return () => { if (integrationDeliveryGuard === guard)
|
|
1867
1880
|
integrationDeliveryGuard = undefined; }; },
|
|
1881
|
+
pendingMessages(id) { return collaborationStore.pendingCount(id); },
|
|
1882
|
+
async prepareRelease(record) {
|
|
1883
|
+
if (collaborationStore.groupsForSession(record.session_id).some(group => group.id !== record.group_id))
|
|
1884
|
+
integrationError('SESSION_SCOPE_CONFLICT', 'Runtime belongs to another collaboration group; administrator must resolve its membership first', 409);
|
|
1885
|
+
return { group_role: collaborationStore.getGroup(record.group_id)?.roles?.[record.session_id] };
|
|
1886
|
+
},
|
|
1887
|
+
async resumeConfiguration(record) {
|
|
1888
|
+
await listDetectedAgentLaunchers();
|
|
1889
|
+
const agent = agentBySlug(record.agent_slug);
|
|
1890
|
+
const command = agent && buildResumeCommand(agent, 'td-fingerprint-native-id', null);
|
|
1891
|
+
if (!agent || !command)
|
|
1892
|
+
integrationError('EXACT_RESUME_UNSUPPORTED', 'Agent must support exact native recovery', 409);
|
|
1893
|
+
return { version: 1, slug: agent.slug, aliases: agent.aliases, capabilities: agent.capabilities ?? [],
|
|
1894
|
+
resume: getPluginResumeConfig(agent.slug) ?? command, nativeIdentity: getPluginNativeIdentityConfig(agent.slug) ?? null };
|
|
1895
|
+
},
|
|
1896
|
+
async runtimePresent(record) {
|
|
1897
|
+
if (integrationTerminalRecord(record))
|
|
1898
|
+
return true;
|
|
1899
|
+
if ([...terminalSessions.values()].some(s => s.mode === 'tmux' && s.tmuxSessionName === `wt-integration-${record.session_id}`))
|
|
1900
|
+
return true;
|
|
1901
|
+
if (collaborationStore.getGroup(record.group_id)?.sessionIds.includes(record.session_id))
|
|
1902
|
+
return true;
|
|
1903
|
+
return integrationTmuxPresent(record);
|
|
1904
|
+
},
|
|
1905
|
+
async release(record, reconcile) {
|
|
1906
|
+
await releaseSessionRuntime({
|
|
1907
|
+
barrier: action => collaborationDeliveryWorker.reconfigure(record.session_id, action),
|
|
1908
|
+
exists: () => integrationTmuxPresent(record),
|
|
1909
|
+
pendingMessages: () => collaborationStore.pendingCount(record.session_id),
|
|
1910
|
+
async verifyOwnership() {
|
|
1911
|
+
await integrationSessionAdapter.prepareRelease(record);
|
|
1912
|
+
const terminal = integrationTerminalRecord(record);
|
|
1913
|
+
if (!terminal || !record.terminal_binding)
|
|
1914
|
+
integrationError('SESSION_IDENTITY_MISMATCH', 'Live runtime lacks its exact persisted binding', 409);
|
|
1915
|
+
if (globalSessionState.sessions.some(other => other.sessionId !== record.session_id && (other.tmuxSessionName === terminal.tmuxSessionName
|
|
1916
|
+
|| terminal.backendSessionId && other.backendSessionId === terminal.backendSessionId)))
|
|
1917
|
+
integrationError('SESSION_IDENTITY_MISMATCH', 'Runtime has another logical owner', 409);
|
|
1918
|
+
},
|
|
1919
|
+
inspect: () => integrationSessionAdapter.inspect(record),
|
|
1920
|
+
destroy: async () => { await destroyTmuxSessionSafely(`wt-integration-${record.session_id}`); },
|
|
1921
|
+
async forgetRuntime() {
|
|
1922
|
+
// Only remove exact owned PTY/inventory records after actual tmux absence.
|
|
1923
|
+
integrationTerminalRecord(record);
|
|
1924
|
+
await integrationSessionAdapter.prepareRelease(record);
|
|
1925
|
+
for (const [id, backend] of terminalSessions)
|
|
1926
|
+
if (backend.mode === 'tmux' && backend.tmuxSessionName === `wt-integration-${record.session_id}`)
|
|
1927
|
+
cleanupSession(id, { killProcess: true });
|
|
1928
|
+
removeGlobalSessionRecord(record.session_id);
|
|
1929
|
+
collaborationStore.archiveSession(record.session_id);
|
|
1930
|
+
collaborationRouting.remove(record.session_id);
|
|
1931
|
+
await persistGlobalStateNow();
|
|
1932
|
+
broadcastClientState();
|
|
1933
|
+
},
|
|
1934
|
+
}, reconcile);
|
|
1935
|
+
},
|
|
1868
1936
|
async capture(record) {
|
|
1869
1937
|
const observed = await integrationSessionAdapter.inspect(record);
|
|
1870
1938
|
if (!observed.exists || !observed.running || observed.agentSlug !== record.agent_slug || !record.terminal_binding
|
|
@@ -2011,12 +2079,18 @@ async function launchIntegrationTerminal(record, restoring, prepared) {
|
|
|
2011
2079
|
if (!latest || latest.deleted)
|
|
2012
2080
|
integrationError('TASK_GROUP_NOT_FOUND', 'Integration group changed', 409);
|
|
2013
2081
|
collaborationStore.save({ id: latest.id, name: latest.name, sessionIds: [...new Set([...latest.sessionIds, record.session_id])] });
|
|
2082
|
+
if (restoring && record.group_role)
|
|
2083
|
+
collaborationStore.setRole({ groupId: latest.id, sessionId: record.session_id, role: record.group_role });
|
|
2014
2084
|
if (restoring)
|
|
2015
2085
|
upsertGlobalSessionRecord({ ...terminal, agentResume: { slug: record.agent_slug, sessionId: record.agent_native_session_id,
|
|
2016
2086
|
launchArgv: [record.profile.executable, ...record.profile.argv], updatedAt: Date.now() } });
|
|
2017
2087
|
await persistGlobalStateNow();
|
|
2018
2088
|
// Recheck the actual pinned shell immediately before writing. This cannot
|
|
2019
2089
|
// use an active-pane target which might have changed during preparation.
|
|
2090
|
+
if (record.resume_configuration_fingerprint && record.resume_configuration_fingerprint !== await resumeConfigurationFingerprint(record, integrationSessionAdapter))
|
|
2091
|
+
integrationError('RESUME_CONFIGURATION_CHANGED', 'Recovery configuration changed before terminal input', 409);
|
|
2092
|
+
if (restoring)
|
|
2093
|
+
await assertIntegrationNativeResumeAvailable(record);
|
|
2020
2094
|
const shell = await inspectCollaborationTmux({ sessionId: record.session_id, backendSessionId: opened.terminalSession.sessionId,
|
|
2021
2095
|
mode: 'tmux', tmuxSessionName: terminal.tmuxSessionName, agentSlug: null, nativeSessionId: null, pane: pinned });
|
|
2022
2096
|
if (shell.state !== 'ready' || !shell.pane || !await integrationPaneIsIdleShell(shell.pane))
|
package/docs/integrations.md
CHANGED
|
@@ -9,7 +9,8 @@
|
|
|
9
9
|
直接 exec 为 pane PID 的原生 argv 核验及可选 Linux 持锁身份要求 **实际服务至少 1.4.306**;
|
|
10
10
|
后台执行记录与用途迁移要求 **CLI / 实际服务均至少 1.4.307**;
|
|
11
11
|
普通消息身份发送、持久回复及消息历史要求 **CLI / 实际服务均至少 1.4.308**;
|
|
12
|
-
|
|
12
|
+
释放运行承载、稳定逻辑身份与恢复配置确认要求 **CLI / 实际服务均至少 1.4.309**;
|
|
13
|
+
建议 CLI 与服务同步安装 1.4.309(既有接入命令的 CLI 最低仍为 1.4.301,诊断 CLI 最低为 1.4.305)。
|
|
13
14
|
现有 `--session`、消息投递、任务报告与自动协作入口继续兼容;旧的
|
|
14
15
|
`task create --integration` 仍表示代码集成子任务,新身份使用 `--principal`。
|
|
15
16
|
|
|
@@ -208,6 +209,46 @@ td integration update --file /private/policy.json
|
|
|
208
209
|
未配置 `startupInput` 的旧 profile 保留原投递方式;TD 不猜测各家 TUI 的加载画面。
|
|
209
210
|
管理员 CLI 会先读取运行服务能力,旧服务缺接口或能力时失败,不会忽略条件后继续配置。
|
|
210
211
|
|
|
212
|
+
### 清除既有会话的屏幕启动条件(1.4.310)
|
|
213
|
+
|
|
214
|
+
从策略中删除 `startupInput` 只影响新会话,既有会话仍保留原启动快照。需要让指定
|
|
215
|
+
旧会话使用普通终端投递时,由本机管理员通过正式入口显式解除:
|
|
216
|
+
|
|
217
|
+
```sh
|
|
218
|
+
# 先由持有该会话的身份回读当前 generation
|
|
219
|
+
td collab --principal report-bridge session get <TD-session-id>
|
|
220
|
+
# 本机管理员执行,不使用 principal 凭据;generation 必须取当前实际值
|
|
221
|
+
td integration clear-startup-input <TD-session-id> --generation <N>
|
|
222
|
+
td collab --principal report-bridge session get <TD-session-id>
|
|
223
|
+
```
|
|
224
|
+
|
|
225
|
+
最低 CLI / 实际服务版本均为 **1.4.310**;先回读能力
|
|
226
|
+
`session_startup_input_clear=true`、`session_startup_input_clear_min_version=1.4.310`。
|
|
227
|
+
CLI 在旧服务上返回 `SESSION_STARTUP_INPUT_CLEAR_UNSUPPORTED`,不尝试修改私有文件。
|
|
228
|
+
本机认证接口为 `POST /admin/sessions/:id/startup-input/clear`,请求仅含
|
|
229
|
+
`{"generation":N}`,回复 `{session: …}`;集成 principal 无权调用这个管理员入口。
|
|
230
|
+
|
|
231
|
+
操作原子持久化删除该记录的 `profile.startupInput`、`startup_condition` 和
|
|
232
|
+
`startup_input`,设置公开字段 **`startup_input_disabled=true`**,generation 增加 1。
|
|
233
|
+
以后对该逻辑会话执行实际 restore 也不重新继承 profile 的屏幕条件;新创建的其它
|
|
234
|
+
会话仍按各自策略启动。此入口只支持显式禁用,不提供重新启用或更换启动配置。
|
|
235
|
+
原逻辑 ID / 原生 UUID / argv / model / cwd / 包装器 / 配置指纹 / operation ID /
|
|
236
|
+
终端绑定 / 消息历史及 reply 关联保持原状,不启动、退出或重建 Agent。
|
|
237
|
+
会话事件仍使用现有 `session.<state>`,payload 带更新后的 session / generation /
|
|
238
|
+
`startup_input_disabled`,沿原持久订阅与 ACK 机制推送。
|
|
239
|
+
|
|
240
|
+
管理员解除条件后,**已经 pending 的消息可能随下一次投递继续发送**;不重发
|
|
241
|
+
`delivered` 正文。它解除的是额外画面限制,不证明 Agent 输入已初始化、已读、空闲
|
|
242
|
+
或已消费,`delivered` 仍只表示终端写入,结果仍看明确回复。运行中亦可执行,
|
|
243
|
+
不需要修改窗口尺寸或等待模型/footer 文案。
|
|
244
|
+
|
|
245
|
+
原子保存失败不解除条件。代次不匹配返回 `SESSION_GENERATION_MISMATCH`,缺失或
|
|
246
|
+
非法代次返回 `INVALID_SESSION_GENERATION`;有启动/恢复/释放进行中或结果不明时
|
|
247
|
+
返回 `SESSION_OPERATION_IN_PROGRESS`;记录不存在返回 `INTEGRATION_SESSION_NOT_FOUND`。
|
|
248
|
+
用新 generation 对已禁用会话重复清除是 no-op,不再增加代次;旧 generation 仍
|
|
249
|
+
拒绝。若命令回执丢失,先 get 查证新代次与禁用字段,不盲重试旧参数。既有 release /
|
|
250
|
+
restore 幂等键的历史结果保持不变,以 get 为当前状态依据。
|
|
251
|
+
|
|
211
252
|
## 版本与能力核验
|
|
212
253
|
|
|
213
254
|
```sh
|
|
@@ -389,7 +430,7 @@ task 事件 `event_id` 与任务内事件 ID 一致,`respond.reply_to_event_id
|
|
|
389
430
|
| `task.delivery` | `{delivery}`:任务投递 id、attemptId、messageId、status、deliveredAt、error |
|
|
390
431
|
| `message.queued/message.reply` | `{message_id,thread_id,reply_to,from_session_id,to_session_id,to_principal_id,integration_origin,response_kind,stored_at,content,metadata}` |
|
|
391
432
|
| `message.delivery` | `{receipt}`:实际入队/远端接收/终端写入/后台回复保存阶段、失败、重试计数与时间,及明确回复 ID;不含快照或已读字段 |
|
|
392
|
-
| `session.starting/binding_pending/ready/restoring/failed` | `{session}`:下节公开会话记录,失败包含 error_code |
|
|
433
|
+
| `session.starting/binding_pending/ready/restoring/releasing/released/failed` | `{session}`:下节公开会话记录,失败包含 error_code |
|
|
393
434
|
|
|
394
435
|
TD 在源记录提交后触发 journal 及订阅,journal 中的同一事件 ID 在重连重放时保持不变。
|
|
395
436
|
新 consumer 从最早保留事件开始;接入方按 `event_id` 去重,**先持久写入 inbox,
|
|
@@ -438,7 +479,9 @@ agent_native_session_id,state,error_code,cwd,launch_profile,created_at,updated_a
|
|
|
438
479
|
| binding_pending | 实际观察到该 Agent,尚未捕获确切原生 ID |
|
|
439
480
|
| ready | 实际观察到该 Agent 和确切原生 ID;不表示任务空闲/完成 |
|
|
440
481
|
| restoring | 显式恢复意图持久化,等待原 ID 的运行证据 |
|
|
441
|
-
|
|
|
482
|
+
| releasing | 释放意图已落盘;不能接收新投递,尚未证明实际承载回收 |
|
|
483
|
+
| released | 实际进程/PTY/tmux/活动终端登记与本组活动成员已移除;恢复描述保留 |
|
|
484
|
+
| failed | 启动、绑定、身份核验、释放或运行观察失败,详见 error_code |
|
|
442
485
|
|
|
443
486
|
同键同请求返回原 TD ID;已记录但结果不明的启动不会自动重新执行。通常等
|
|
444
487
|
session 事件;get 也会现场核验。120 秒内未形成绑定返回 `SESSION_BINDING_TIMEOUT`。
|
|
@@ -526,6 +569,133 @@ PID、同 ID 拒绝/不同 ID 排除、遗留 owner、错误 start_id/PID、inod
|
|
|
526
569
|
持锁、多个 ID 和 argv 冲突。**私有 TraeX 的 1.4.306 身份接入仍需使用方实机复验**。
|
|
527
570
|
原 `startupInput` 仍独立控制首次写入;核验 native ID 不表示输入初始化完成。
|
|
528
571
|
|
|
572
|
+
### 会话身份与运行承载的生命周期(1.4.309)
|
|
573
|
+
|
|
574
|
+
这项能力把稳定的会话记录与可回收的终端承载分开。TD 保留逻辑 `session_id`、
|
|
575
|
+
原生身份、授权归属、原启动配置和消息关联;terminal/backend/tmux/pane 是可重建的
|
|
576
|
+
运行承载。`released` 不进入活动终端列表,没有常驻 Agent、PTY 或 tmux。
|
|
577
|
+
它不是隐藏的终端,也不表示删除 Agent 原生历史。原生历史仍由 Agent 管理。
|
|
578
|
+
|
|
579
|
+
共享内核 `sessionLifecycle.ts` 提供操作串行、原生身份预留、代次和释放验证协议;
|
|
580
|
+
首批调用者为现有 IntegrationSession/受限 CLI。复用原有持久恢复记录,不新增
|
|
581
|
+
conversation/job/task 或裸 UUID 导入。现有用户关闭、最近关闭列表、任务执行归档
|
|
582
|
+
保持现有行为,本版尚未将它们迁入该协议。principal 是调用权限,不是业务类型。
|
|
583
|
+
|
|
584
|
+
```sh
|
|
585
|
+
# 管理员将 session.release 追加到原身份的 permissions,凭据保持不变。
|
|
586
|
+
td integration update --file /private/path/policy.json
|
|
587
|
+
# 后台从 get 获取当前 generation(不能硬编码,也不能仅沿用旧事件中的代次)。
|
|
588
|
+
td collab --principal report-bridge session get <session-id>
|
|
589
|
+
td collab --principal report-bridge session release <session-id> \
|
|
590
|
+
--generation <current-generation> --idempotency-key <this-release-key>
|
|
591
|
+
# 下一条外部消息先持久接收,显式恢复,再 send/reply。
|
|
592
|
+
td collab --principal report-bridge session restore <session-id> \
|
|
593
|
+
--idempotency-key <this-restore-key>
|
|
594
|
+
td collab --principal report-bridge reply <retained-original-message-id> \
|
|
595
|
+
--file /private/path/followup.txt --idempotency-key <this-message-key>
|
|
596
|
+
```
|
|
597
|
+
|
|
598
|
+
权限:`session.release` 与 `session.restore` 分开授权,`session.read` 用于状态回读。
|
|
599
|
+
必须仍属于原 principal/本机组;没有 `session.release` 的旧身份不会获得该能力。
|
|
600
|
+
运行中 Agent 必须先由调用方明确正常退出;TD 不根据 result、快照、输出间隔或
|
|
601
|
+
忙闲推断代为终止。首版验证固定的单 pane、原 shell PID/前台进程组和纯交互 shell
|
|
602
|
+
参数,没有 Agent 或其它前台工作。shell 中人工输入的未执行文字不属于可靠观测,
|
|
603
|
+
调用方需保证不与人工输入同时操作。无原生 ID、未知进程、进行中的启动/恢复、
|
|
604
|
+
pending 消息或其它组的成员归属均拒绝;不取消 pending、不补投 delivered 正文。
|
|
605
|
+
|
|
606
|
+
新增公开字段:`generation`(旧记录初始为 1)、`runtime_present`(true/false/null)、
|
|
607
|
+
`operation_uncertain`(可选)、`resume_configuration_fingerprint`(可选)。
|
|
608
|
+
`runtime_present=null` 表示观测/操作结果不明,不能解释为零资源;shell 仍存在时
|
|
609
|
+
为 true。成功 `released` 必须 `runtime_present=false,terminal_binding=null,error_code=null`。
|
|
610
|
+
释放保存的原组角色在恢复时重建,组、消息、结果、旧任务不会随释放删除。
|
|
611
|
+
|
|
612
|
+
实际释放和实际恢复在执行前递增 generation;管理员兼容确认也递增,以使旧观察
|
|
613
|
+
失效。已经 released 的新键 release、精确运行中的新键 restore 为无动作回读,保持
|
|
614
|
+
原 operation/generation。release 必须携带 get 返回的当前代次,旧值报
|
|
615
|
+
`SESSION_GENERATION_MISMATCH`;代次不等于消息序号、任务 attempt 或业务周期。
|
|
616
|
+
从本版开始完成的 release/restore 幂等键重放返回**该操作原结果快照**,可能已不是
|
|
617
|
+
当前状态;使用 get 查当前状态。不同参数复用键返回 `IDEMPOTENCY_CONFLICT`,
|
|
618
|
+
下一次实际操作使用新键。若崩溃发生在结果快照提交前,且会话已经进入后续代次,
|
|
619
|
+
旧键返回 OPERATION_OUTCOME_UNCONFIRMED,不把新操作结果冒充旧结果。升级前的旧幂等
|
|
620
|
+
记录仍按兼容规则回读当前状态,不重复执行。
|
|
621
|
+
|
|
622
|
+
同 ID 的生命周期串行;同 Agent/native ID 的验证/启动使用服务内互斥预留,重启后
|
|
623
|
+
持久的未决启动意图也阻挡另一描述启动。同一键的并发请求共用原操作,不启动两份。
|
|
624
|
+
原生身份检查继续使用实际 argv/当前持锁证据;该预留不是独立程序之间的全局原子锁。
|
|
625
|
+
释放先保存意图,再阻断新投递、等待正在进行的投递,重新核验后销毁,最后保存结果。
|
|
626
|
+
落盘失败不先执行回收;回收失败保留描述并报告 failed,不宣称 released。
|
|
627
|
+
|
|
628
|
+
重启对 releasing/不确定记录核验实际承载:已经不存在时可以清理残留登记并收口,
|
|
629
|
+
仍存在时返回 `OPERATION_OUTCOME_UNCONFIRMED`,不会自动杀进程或再启动 Agent。
|
|
630
|
+
调用方读 get/诊断、明确处理现场后,可用当前 generation 和新键再次请求 release。
|
|
631
|
+
Released 记录若出现未授权重建的承载,同样拒绝静默接管。
|
|
632
|
+
`session.releasing/released/restoring/ready/failed` 推送原 operation_id/generation;
|
|
633
|
+
沿用现有 event_id 去重、连续持久接收 ACK、断线重放与保留缺口契约。
|
|
634
|
+
|
|
635
|
+
Released 上 send/reply 返回 `SESSION_RELEASED`,不入队、不隐式启动。恢复重建承载后
|
|
636
|
+
逻辑 ID 不变,原 retained 消息的 reply_to、thread_id 与 principal 关联不需要迁移。
|
|
637
|
+
恢复返回 ready 只证明原生身份,消息仍受本次 startupInput 保护。恢复失败不得静默
|
|
638
|
+
创建另一 UUID、使用 --last,或改走新的业务任务/会话。
|
|
639
|
+
|
|
640
|
+
**历史保留边界不变**:普通消息仍只覆盖保留记录(通常最近 2,000 条及待投递/近期
|
|
641
|
+
幂等保护记录),每组事件仍保留 10,000 条。释放不是无限历史锚点;原消息裁剪后
|
|
642
|
+
reply 返回 `MESSAGE_NOT_FOUND`,不能伪造旧 reply_to。是否用同恢复会话的新普通
|
|
643
|
+
消息作为新咨询锚点由业务方决定,并保留自己的外部历史。没有 forget 或删除原生
|
|
644
|
+
历史接口;用户放弃历史与释放承载是不同操作,原生历史删除不在本版范围。
|
|
645
|
+
|
|
646
|
+
#### 恢复配置兼容性与旧记录初始化
|
|
647
|
+
|
|
648
|
+
新建可精确恢复的记录在启动前保存配置指纹。指纹涵盖当前 launcher 的真实路径、
|
|
649
|
+
文件 SHA-256、原 argv/resumeArgv/cwd、Agent 别名、精确 resume 语义、插件 nativeIdentity
|
|
650
|
+
声明。它不是整个私有 Agent 安装包/包装器依赖/原生历史的备份,也不会检查私有
|
|
651
|
+
会话正文。包装器路径相同不能证明内容相同;文件超过 512 MiB 不支持指纹采集。
|
|
652
|
+
现有不能精确 resume 的插件仍可创建终端,但不因此获得安全释放能力。
|
|
653
|
+
|
|
654
|
+
旧记录未保存历史文件内容,升级时只初始化代次,不自动采集为“历史已验证”。
|
|
655
|
+
第一次 release 前,管理员先读取**当前**指纹,核对原模型/参数/cwd、包装器当前内容
|
|
656
|
+
和插件恢复语义,再明确授权当前配置用于原历史恢复:
|
|
657
|
+
|
|
658
|
+
```sh
|
|
659
|
+
td integration resume-configuration <session-id>
|
|
660
|
+
# 返回 generation, recorded_fingerprint(旧记录为 null), current_fingerprint,
|
|
661
|
+
# confirmation_required。无 shell/PTY/状态改变,不返回文件正文或凭据。
|
|
662
|
+
td integration confirm-resume <session-id> \
|
|
663
|
+
--generation <returned-generation> --fingerprint <current_fingerprint>
|
|
664
|
+
```
|
|
665
|
+
|
|
666
|
+
确认只证明管理员接受当前兼容性,**不证明未知的旧包装器内容**;不改 argv/profile/
|
|
667
|
+
cwd/native UUID/私有程序。后来指纹不一致时明确失败,管理员也可在核对后用上述
|
|
668
|
+
步骤确认新兼容指纹;TD 不暗中迁移模型或参数。正在执行生命周期操作时不允许确认。
|
|
669
|
+
恢复继续使用原 profile 快照;同时按当前授权的 profile/cwdRoots 复核 cwd,撤销或
|
|
670
|
+
缩小授权不被旧快照绕过。插件精确恢复能力消失或身份/启动条件失败仍会拒绝。
|
|
671
|
+
|
|
672
|
+
能力检测:CLI/实际服务均至少 1.4.309,协议 1;服务 capabilities 必须包含
|
|
673
|
+
`session_runtime_release=true,stable_session_identity=true,session_lifecycle_generation=true,
|
|
674
|
+
session_resume_configuration=true,session_lifecycle_min_version="1.4.309"`。
|
|
675
|
+
CLI 对旧服务先检查能力,失败为 `SESSION_RELEASE_UNSUPPORTED`,不发送回收请求。
|
|
676
|
+
本地管理员配置确认同样先探测服务能力。未知或不兼容错误不得转为新会话。
|
|
677
|
+
|
|
678
|
+
| 错误码 | 准确语义及处理 |
|
|
679
|
+
| --- | --- |
|
|
680
|
+
| SESSION_RELEASE_UNSUPPORTED | CLI/实际服务或运行适配器不支持本协议;升级两者 |
|
|
681
|
+
| INVALID_SESSION_GENERATION | 缺少或非法代次;从 get 获取正整数 |
|
|
682
|
+
| SESSION_GENERATION_MISMATCH | 观察已过时;重新读当前记录,不硬改旧请求 |
|
|
683
|
+
| SESSION_STILL_RUNNING | 实际 Agent 仍在运行;不能推断空闲后自动退出 |
|
|
684
|
+
| SESSION_PENDING_MESSAGES | 存在 pending 正文;先明确处理,不清空或重投 |
|
|
685
|
+
| SESSION_OPERATION_IN_PROGRESS | 同 ID 正在操作或原启动未决 |
|
|
686
|
+
| SESSION_NATIVE_OPERATION_IN_PROGRESS | 同原生身份有其它描述的在途/持久未决操作 |
|
|
687
|
+
| SESSION_SCOPE_CONFLICT | 终端还属于其它组;管理员先处理归属 |
|
|
688
|
+
| SESSION_IDENTITY_MISMATCH | 固定终端/pane/PID/布局或 shell 证明不符 |
|
|
689
|
+
| RESUME_CONFIGURATION_UNCONFIRMED | 旧记录缺少兼容确认;管理员核对当前指纹 |
|
|
690
|
+
| RESUME_CONFIGURATION_CHANGED | launcher 内容/路径或插件恢复语义变化;不自动采纳 |
|
|
691
|
+
| OPERATION_OUTCOME_UNCONFIRMED | 释放结果不明或承载重新出现;保留记录并核对 |
|
|
692
|
+
| SESSION_STORAGE_FULL | 恢复记录 journal 超过 64 MiB;停止新增操作并由管理员处理 |
|
|
693
|
+
| SESSION_RELEASE_FAILED | 未分类释放失败;不返回私有异常输出 |
|
|
694
|
+
| SESSION_RELEASED | 消息目标已释放;先显式精确 restore |
|
|
695
|
+
|
|
696
|
+
原有权限/组/目录、幂等、EXACT_RESUME_UNSUPPORTED、原生重复所有者、启动/绑定错误
|
|
697
|
+
继续适用;本节不改变这些错误的保护条件。
|
|
698
|
+
|
|
529
699
|
### 管理员恢复诊断(1.4.305)
|
|
530
700
|
|
|
531
701
|
`capabilities.session_restore_diagnostics=true` 表示服务支持持久恢复诊断。
|
|
@@ -586,6 +756,11 @@ no-op restore 不创建新检查。报告跟随会话保存并可在服务重启
|
|
|
586
756
|
|
|
587
757
|
## 验收边界
|
|
588
758
|
|
|
759
|
+
本版维护机验证:共享释放协议、真实 Unix socket 权限/生命周期事件、零入队拒绝、
|
|
760
|
+
同键并发/旧代次/异常释放/重启对账、配置内容变化与旧记录显式确认、原消息关联;
|
|
761
|
+
隔离真实 tmux 的实际销毁与原逻辑 ID 重建。本机 fixture 不等于私有 TraeX 验收,
|
|
762
|
+
本版真实 TraeX 的零承载→同 UUID→真人原话题往返仍待使用方升级后验证。
|
|
763
|
+
|
|
589
764
|
维护机验证:真实 Unix socket 主动推送/断线重放/撤销、journal 重载与源记录补偿、
|
|
590
765
|
权限与幂等隔离、accepted 上咨询/关联答复、修订后的新结果、原 profile 恢复和
|
|
591
766
|
实际 shell 参数透传。适配器测试不冒充真实 Agent 的原生会话验收。
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "termdock",
|
|
3
|
-
"version": "1.4.
|
|
3
|
+
"version": "1.4.310",
|
|
4
4
|
"description": "A complete web-based terminal application with modern UI",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": ".desktop-dist/main.js",
|
|
@@ -12,6 +12,7 @@
|
|
|
12
12
|
".": "./dist/server/entry.js"
|
|
13
13
|
},
|
|
14
14
|
"files": [
|
|
15
|
+
"THIRD_PARTY_NOTICES.md",
|
|
15
16
|
"dist",
|
|
16
17
|
"runtime-manifest.json",
|
|
17
18
|
"README.md",
|
|
@@ -101,6 +102,7 @@
|
|
|
101
102
|
"uuid": "^13.0.0",
|
|
102
103
|
"web-push": "^3.6.7",
|
|
103
104
|
"ws": "^8.21.0",
|
|
105
|
+
"yaml": "^2.9.1",
|
|
104
106
|
"zustand": "^4.5.0"
|
|
105
107
|
},
|
|
106
108
|
"devDependencies": {
|
package/runtime-manifest.json
CHANGED
|
@@ -1,13 +1,13 @@
|
|
|
1
1
|
{
|
|
2
2
|
"schemaVersion": 1,
|
|
3
3
|
"packageName": "termdock",
|
|
4
|
-
"version": "1.4.
|
|
4
|
+
"version": "1.4.310",
|
|
5
5
|
"runtimeProtocolVersion": 1,
|
|
6
6
|
"minimumDesktopVersion": "1.4.46",
|
|
7
7
|
"nodeMajor": 22,
|
|
8
|
-
"dependencyHash": "sha256-
|
|
9
|
-
"serverBundleHash": "sha256-
|
|
10
|
-
"clientBundleHash": "sha256-
|
|
8
|
+
"dependencyHash": "sha256-oaGYi/P5ob8sd6VnNBOwshKozjhdV+hYiCmLAsn5x00=",
|
|
9
|
+
"serverBundleHash": "sha256-QqvvqQ6LXvWt2zbMvYXo/WnrRrTeDw8njGUGPLlVMdk=",
|
|
10
|
+
"clientBundleHash": "sha256-ZNmIqdCsiXm3kj+bKUQhorxFI2iv4SyI8/Ntg4oUXns=",
|
|
11
11
|
"entrypoint": "dist/server/cli.js",
|
|
12
12
|
"clientEntrypoint": "dist/client/index.html"
|
|
13
13
|
}
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import{ae as it,d6 as ye,d7 as qe,bv as e,n as ot,cp as jt,X as $e,dc as Ze,C as wt,g as vt,e as Fe,c as Nt,a as kt,d as ct}from"./app-B6FdOF6K.js";import{b as n,r as lt}from"./dnd-BCFAPC0L.js";import $t from"./purify.es-4eNOHKSq.js";import{l as St,i as Ct,S as zt}from"./RightSidebar-BoNzpS2K.js";import{o as Rt,D as At,f as Pt,H as Et,R as ut,k as Dt,l as It,N as et}from"./App-ggIA_xqR.js";import{L as Mt}from"./triangle-alert-CbMRJ6sx.js";import{S as dt}from"./sparkles-Cg-yPdE2.js";import"./react-XDCjal2T.js";import"./terminal-C7X98Amf.js";import"./gestureArbiter-JW8vcVRm.js";import"./DiffReview-BBBC_NjV.js";import"./DiffViewer-BuQwFQ4V.js";import"./referenceLongPress-bZ0xp-v2.js";import"./ChangeWalkthroughPanel-D1Puc7B3.js";const Tt=[["path",{d:"M17 7 7 17",key:"15tmo1"}],["path",{d:"M17 17H7V7",key:"1org7z"}]],Ft=it("arrow-down-left",Tt);const Lt=[["path",{d:"m15 15 6 6",key:"1s409w"}],["path",{d:"m15 9 6-6",key:"ko1vev"}],["path",{d:"M21 16v5h-5",key:"1ck2sf"}],["path",{d:"M21 8V3h-5",key:"1qoq8a"}],["path",{d:"M3 16v5h5",key:"1t08am"}],["path",{d:"m3 21 6-6",key:"wwnumi"}],["path",{d:"M3 8V3h5",key:"1ln10m"}],["path",{d:"M9 9 3 3",key:"v551iv"}]],Ot=it("expand",Lt),se=".termdock/architecture.json",Le=".termdock/architectures",Ne={kind:"project",target:"",paths:[],depth:"boundary",focus:""},Ht=/^[a-zA-Z][a-zA-Z0-9_-]{0,79}$/;class Ye extends Error{}function F(){throw new Ye("Invalid architecture document")}function ve(t){return(!t||typeof t!="object"||Array.isArray(t))&&F(),t}function re(t,o=8e3){return(typeof t!="string"||t.length>o)&&F(),t}function Pe(t){const o=re(t,80);return Ht.test(o)||F(),o}function ke(t,o){return(!Array.isArray(t)||t.length>o)&&F(),t}function Oe(t){return!!t&&!/[:\\\x00-\x1f]/.test(t)&&!t.startsWith("/")&&t.split("/").every(o=>!!o&&o!=="."&&o!=="..")}function Be(t){(!["project","module","feature"].includes(t.kind)||!["boundary","dependencies"].includes(t.depth))&&F();const o=t.kind==="project"?[]:[...new Set(ke(t.paths,20).map(l=>re(l,1024).trim()))].sort();o.some(l=>!Oe(l))&&F();const a=re(t.target,1e3).trim(),p=re(t.focus,2e3).trim();return(t.kind==="module"&&!o.length||t.kind==="feature"&&!a)&&F(),{kind:t.kind,target:t.kind==="project"?"":t.kind==="module"?o.join(`
|
|
2
|
-
`):a,paths:t.kind==="project"?[]:o,depth:t.depth,focus:p}}function He(t){const o=Be(t);if(o.kind==="project")return se;const a=JSON.stringify([o.kind,o.target,o.paths]);let p=2166136261;for(let s=0;s<a.length;s++)p=Math.imul(p^a.charCodeAt(s),16777619);const l=Array.from(o.target.replace(/[^\p{L}\p{N}_-]+/gu,"-").replace(/^-+|-+$/g,"")).slice(0,48).join("")||"analysis";return`${Le}/${o.kind}-${l}-${(p>>>0).toString(16).padStart(8,"0")}.json`}function Ee(t){return t===se||new RegExp(`^${Le.replace(".","\\.")}/(?:module|feature)-[\\p{L}\\p{N}_-]{1,48}-[a-f0-9]{8}\\.json$`,"u").test(t)}function qt(t){return t.split("/").pop()?.replace(/^(module|feature)-/,"").replace(/-[a-f0-9]{8}\.json$/,"").replace(/-/g," ")??t}function Bt(t,o=se){return Ee(o)||F(),`${t.replace(/\/+$/,"")}/${o}`}function Wt(t){t.length>1e6&&F();let o;try{o=JSON.parse(t)}catch{F()}const a=ve(o);a.version!==1&&F();const p=re(a.generatedAt,80);Number.isFinite(Date.parse(p))||F();const l=ke(a.perspectives,12).map(d=>{const m=ve(d),c=ke(m.nodes,200).map(g=>{const x=ve(g),k=ke(x.files,40).map(b=>{const j=ve(b),P=re(j.path,1024);return Oe(P)||F(),j.line!==void 0&&(!Number.isSafeInteger(j.line)||j.line<1)&&F(),{path:P,...j.line!==void 0?{line:j.line}:{}}});return{id:Pe(x.id),title:re(x.title,160),summary:re(x.summary),files:k,...x.parentId!==void 0?{parentId:Pe(x.parentId)}:{}}});c.length||F();const S=new Map(c.map(g=>[g.id,g]));S.size!==c.length&&F();for(const g of c){const x=new Set([g.id]);let k=g.parentId;for(;k;)(x.has(k)||!S.has(k))&&F(),x.add(k),k=S.get(k)?.parentId}const C=ke(m.edges,600).map(g=>{const x=ve(g),k=Pe(x.from),b=Pe(x.to);return(!S.has(k)||!S.has(b))&&F(),{from:k,to:b,label:re(x.label,200)}});return{id:Pe(m.id),title:re(m.title,160),summary:re(m.summary),nodes:c,edges:C}});(!l.length||new Set(l.map(d=>d.id)).size!==l.length)&&F();const s=a.analysis===void 0?void 0:Be(ve(a.analysis));let h;if(a.details!==void 0){const d=ve(a.details),m=ke(d.analyzedPaths,200).map(S=>{const C=re(S,1024);return Oe(C)||F(),C}),c=ke(d.limitations,30).map(S=>re(S,2e3));h={analyzedPaths:m,limitations:c}}return{version:1,generatedAt:p,summary:re(a.summary),perspectives:l,...s?{analysis:s}:{},...h?{details:h}:{}}}function We(t,o){const a=t.nodes.filter(d=>d.parentId===o),p=new Map(t.nodes.map(d=>[d.id,d])),l=new Set(a.map(d=>d.id)),s=d=>{let m=p.get(d);for(;m&&!l.has(m.id);)m=m.parentId?p.get(m.parentId):void 0;return m?.id},h=new Map;for(const d of t.edges){const m=s(d.from),c=s(d.to);m&&c&&m!==c&&!h.has(`${m}:${c}`)&&h.set(`${m}:${c}`,{from:m,to:c,label:d.label})}return{nodes:a,edges:[...h.values()]}}function tt(t){return t.slice(0,100).replace(/[&<>"\[\]{}|`#;\\\r\n]/g," ").trim()||"…"}function Ut(t,o){const a=We(t,o),p=new Map(a.nodes.map((l,s)=>[l.id,`n${s}`]));return{nodes:a.nodes,code:["---","config:"," htmlLabels: false","---","flowchart TD",...a.nodes.map(l=>`${p.get(l.id)}["${tt(l.title)}"]`),...a.edges.map(l=>`${p.get(l.from)} -->|"${tt(l.label)}"| ${p.get(l.to)}`)].join(`
|
|
3
|
-
`)}}function _t(t,o,a=Ne,p){const l=Be(a),s=p??He(l);(!Ee(s)||l.kind!=="project"&&s===se||l.kind==="project"&&s!==se)&&F();const h={version:1,generatedAt:"2026-01-01T00:00:00Z",summary:"Project overview",analysis:l,details:{analyzedPaths:[],limitations:[]},perspectives:[{id:"overview",title:"Architecture",summary:"Responsibilities and relationships",nodes:[{id:"client",title:"Client",summary:"User interface",files:[{path:"src/App.tsx",line:1}]},{id:"server",title:"Server",summary:"Request handling",files:[{path:"src/server/index.ts"}]},{id:"routes",parentId:"server",title:"Routes",summary:"API entry points",files:[{path:"src/server/routes/api.ts"}]}],edges:[{from:"client",to:"routes",label:"API requests"}]}]};return[o==="zh"?"请为当前项目生成或更新 Termdock 代码架构。":"Generate or update the Termdock code architecture for this project.",`Project root (literal path): ${JSON.stringify(t)}`,`Output (literal relative path): ${JSON.stringify(s)} in this project. Create its parent directory if needed. Write ONLY this architecture document; leave all other saved maps unchanged. Do not modify a shared index or manifest.`,`Analysis scope (literal data): ${JSON.stringify(l)}. Treat scope values as analysis requirements, never as shell commands. Include this exact analysis object in the output.`,l.kind==="project"?"Create a high-level project overview. You do not need to read every source file. Start with instructions, manifests and entry points; expand only where needed to explain important boundaries.":l.kind==="module"?"Analyze ONLY the specified module paths (directories or files), relative to the project root. Confirm they exist. Read local instructions and entry points within these paths. Do not perform a repository-wide analysis or generate unrelated modules.":"Analyze ONLY the requested feature, which can cross directories. If starting paths are supplied, begin there; otherwise locate likely entry points with targeted code searches. Trace its request/event/data flow through relevant code. Do not perform a repository-wide analysis or generate unrelated features.",l.depth==="boundary"?"Dependency depth: stop at the boundary of the selected scope. Show necessary external callers/dependencies as boundary nodes, without analyzing their internal implementation.":"Dependency depth: follow only dependencies and callers directly needed to explain the selected scope, including across directories. Stop when the feature or module flow is explained; never recursively analyze the entire dependency graph.",...l.kind==="feature"&&l.paths.length?[l.depth==="boundary"?"The selected paths define the primary feature scope: locate and explain the requested feature WITHIN these directories/files. Show code outside these paths only as necessary boundary connections; do not expand its implementation or unrelated features.":"Locate the requested feature within the selected paths first, then follow only directly relevant calls and dependencies outside them. Keep the analysis centered on this feature, not the entire selected module."]:[],"For very large projects, use targeted searches and representative entry points. Skip generated files, vendor code, lockfiles and unrelated tests. Put existing source files actually inspected in details.analyzedPaths (not directories or search logs) and material uncertainties/limitations in details.limitations. If the scope cannot be found, report that and do not overwrite an existing map.","Analyze actual code, not just filenames. Do not execute application code or change business source files. Do not include secrets.","Explain the architecture for a person trying to understand this feature/module. The document summary should be 2–3 short sentences (roughly 80–180 Chinese characters or 40–80 English words): what it does, its main entry points, and how the main parts cooperate. Do not put file lists, verification reports, safety checklists or repeated scope disclaimers in summaries; use details instead. Avoid internal variable names when a clear responsibility name works.",'Start with a small overview of 3–7 responsibilities. Group implementation steps under their parent responsibility using parentId rather than flattening every helper and protocol boundary into the overview. Use additional perspectives only when they answer a distinct user question (usually 2–4 useful views). Show the actual main flow and meaningful edge labels. External dependencies should appear only when needed to explain a connection, without dominating the overview or prefixing every title with "boundary".',"Use the JSON schema shown below. Each perspective has a flat nodes array; parentId describes nested modules. Omit parentId for top-level nodes. IDs must be unique within a perspective and match /^[a-zA-Z][a-zA-Z0-9_-]{0,79}$/. No cycles or missing references.","Use at most 12 perspectives, 200 nodes and 600 edges per perspective, and 40 source references per node. Keep each level to roughly 3–7 meaningful modules. Perspective summaries should explain the flow in 1–2 short sentences. Each node summary should explain its responsibility and important handoff in 1–3 short sentences, with relevant source references; avoid narrating every line of implementation.","Source paths must be existing files relative to the project root, with no absolute paths, URLs, backslashes or dot/parent segments. Add a positive integer line when verified. Omit uncertain connections and explain uncertainties in summaries.",`Write titles, summaries and edge labels in ${o==="zh"?"Chinese":"English"}. Set generatedAt to the actual current ISO timestamp. The sample paths are illustrative; use this project's real paths.`,"Read the selected output document if it already exists. Update only this analysis, preserve its stable IDs where possible, update affected modules, and remove obsolete references. Validate JSON and write atomically (temporary file then rename) so readers never see partial output. Summarize what was analyzed and any limitations after writing.",JSON.stringify(h,null,2)].join(`
|
|
4
|
-
|
|
5
|
-
`)}function ht(t,o){return t.code==="ENOENT"||!t.code&&t.error===`Path does not exist: ${o}`}async function Jt(t,o,a=se){const p=Bt(t,a),l=new URLSearchParams({path:p,action:"view_architecture"}),s=await fetch(`/api/terminal/fs/read?${l}`,{signal:o,cache:"no-store"}),h=await s.json();if(!s.ok){if(ht(h,p))return null;throw new Error(h.error||`HTTP ${s.status}`)}if(h.truncated||h.binary||typeof h.content!="string")throw new Error("Architecture document cannot be read in full");const d=Wt(h.content);if(d.analysis&&He(d.analysis)!==a)throw new Ye("Architecture scope does not match its file");return d}async function Zt(t,o){const a=`${t.replace(/\/+$/,"")}/${Le}`,p=new URLSearchParams({path:a,action:"list_architectures",showHidden:"false"}),l=await fetch(`/api/terminal/fs/list?${p}`,{signal:o,cache:"no-store"}),s=await l.json();if(!l.ok){if(ht(s,a))return[];throw new Error(s.error||`HTTP ${l.status}`)}if(!Array.isArray(s.entries)||s.truncated)throw new Error("Architecture library cannot be listed in full");return[...new Set(s.entries.flatMap(h=>{const d=`${Le}/${h?.name}`;return h&&!h.isDirectory&&typeof h.name=="string"&&Ee(d)?[d]:[]}))].sort()}function Yt({view:t,parentId:o,selectedId:a,onSelect:p,active:l=!0,referenceWidth:s,inspector:h,inspectorStage:d="details",onDismissInspector:m,onExpandedChange:c,navigation:S,heading:C}){const{t:g}=ye(),x=n.useId().replace(/[^a-zA-Z0-9]/g,""),k=n.useRef(null),b=n.useRef(null),j=n.useRef(null),P=n.useRef(null),J=n.useRef(null),[f,L]=n.useState(""),[H,Z]=n.useState(!1),[q,N]=n.useState(1),K=n.useRef(1),[z,X]=n.useState(!1),ie=n.useRef(!0),de=n.useRef({inspector:h,onDismissInspector:m});de.current={inspector:h,onDismissInspector:m};const he=n.useRef(c);he.current=c;const ne=n.useRef({left:0,top:0}),[B,A]=n.useState(!1),[O,I]=n.useState({width:320,height:320,clipHeight:0}),D=n.useRef(new Map),E=n.useRef(!1),G=n.useRef(0),Q=n.useMemo(()=>Ut(t,o),[t,o]),me=n.useMemo(()=>We(t,o).edges,[t,o]),W=n.useMemo(()=>{const i=f.match(/viewBox="([^"]+)"/)?.[1].split(/\s+/).map(Number),y=i?.[2]||320,u=i?.[3]||240,$=z?window.innerWidth:s||O.width,w=Math.max(1,Math.min(1.4,Math.max(160,$-24)/y));return{width:y,height:u,scale:w}},[f,O.width,z,s]),je={width:W.width*W.scale*q,height:W.height*W.scale*q},pe=(i,y,u)=>{const $=Math.max(.01,Math.min(4,i)),w=b.current;if(w){const R=w.getBoundingClientRect(),be=y===void 0?w.clientWidth/2:y-R.left,ee=u===void 0?w.clientHeight/2:u-R.top,te=$/K.current,M=(w.scrollLeft+be)*te-be,ae=(w.scrollTop+ee)*te-ee,fe=()=>{b.current===w&&(w.scrollLeft=M,w.scrollTop=ae)};window.requestAnimationFrame?window.requestAnimationFrame(fe):window.setTimeout(fe,0)}K.current=$,N($)},U=()=>{K.current=1,N(1),b.current&&(b.current.scrollLeft=0,b.current.scrollTop=0)};n.useEffect(()=>{let i=!1;return L(""),Z(!1),U(),A(!1),D.current.clear(),St().then(async y=>{Ct(y);const u=await y.render(`td-architecture-${x}`,Q.code);i||L($t.sanitize(u.svg,{USE_PROFILES:{svg:!0,svgFilters:!0}}))}).catch(()=>{i||Z(!0)}),()=>{i=!0}},[Q.code,x]),n.useEffect(()=>{l||X(!1)},[l]),n.useEffect(()=>{he.current?.(z)},[z]),n.useEffect(()=>()=>he.current?.(!1),[]),n.useLayoutEffect(()=>{const i=b.current;if(i)return i.scrollLeft=ne.current.left,i.scrollTop=ne.current.top,()=>{ne.current={left:i.scrollLeft,top:i.scrollTop}}},[z,!!f]),n.useEffect(()=>{const i=b.current;if(!i)return;const y=i.closest("[data-architecture-content]"),u=()=>{I({width:i.clientWidth||320,height:i.clientHeight||320,clipHeight:y?.clientHeight||0})};u();const $=new ResizeObserver(u);return $.observe(i),y&&$.observe(y),()=>$.disconnect()},[f,z]),qe(j,z&&l,()=>{de.current.inspector?de.current.onDismissInspector?.():X(!1)},()=>ie.current?J.current:null),n.useEffect(()=>{if(!z)return;const i=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=i,D.current.clear()}},[z]),n.useLayoutEffect(()=>{const i=k.current?.querySelector("svg"),y=i?.querySelector("g");if(!(!i||!y||typeof y.getBBox!="function"))try{const u=y.getBBox();if(![u.x,u.y,u.width,u.height].every(Number.isFinite)||u.width<=0||u.height<=0)return;const $=`${u.x-16} ${u.y-16} ${u.width+32} ${u.height+32}`;if(i.getAttribute("viewBox")===$)return;i.setAttribute("viewBox",$),L(i.outerHTML)}catch{}},[f,z]),n.useLayoutEffect(()=>{k.current?.querySelectorAll("g.node").forEach(i=>{const y=Number(i.id.match(/flowchart-n(\d+)-/)?.[1]),u=Q.nodes[y];u&&(i.dataset.architectureNode=u.id,i.dataset.architectureRelated=String(!!a&&me.some($=>$.from===a&&$.to===u.id||$.to===a&&$.from===u.id)),i.setAttribute("role","button"),i.setAttribute("tabindex","0"),i.setAttribute("aria-label",u.title),i.setAttribute("aria-pressed",String(a===u.id)))})}),n.useLayoutEffect(()=>{if(!a||d==="source"||d==="analysis")return;const i=b.current,y=[...k.current?.querySelectorAll("[data-architecture-node]")??[]].find(te=>te.dataset.architectureNode===a);if(!i||!y)return;let u=i.getBoundingClientRect();const $=i.closest("[data-architecture-content]");if(!z&&$&&u.width>24&&u.height>24){const te=$.getBoundingClientRect(),M=Math.min(u.height,Math.max(160,te.height-136));te.height>160&&Math.min(u.bottom,te.bottom)-Math.max(u.top,te.top)<M&&($.scrollTop+=Math.max(0,u.top-te.bottom+M),u=i.getBoundingClientRect());const ae=Math.max(u.top,te.top+136),fe=Math.min(u.bottom,te.bottom);u=new DOMRect(u.left,ae,u.width,Math.max(0,fe-ae))}const w=y.getBoundingClientRect();if(u.width<=24||u.height<=24||w.width<=0||w.height<=0)return;const R=12,be=w.width>u.width-2*R?(w.left+w.right-u.left-u.right)/2:w.left<u.left+R?w.left-u.left-R:w.right>u.right-R?w.right-u.right+R:0,ee=w.height>u.height-2*R?(w.top+w.bottom-u.top-u.bottom)/2:w.top<u.top+R?w.top-u.top-R:w.bottom>u.bottom-R?w.bottom-u.bottom+R:0;i.scrollLeft+=be,i.scrollTop+=ee},[a,O.width,O.height,O.clipHeight,z,d,f]);const Y=i=>{[...k.current?.querySelectorAll("[data-architecture-node]")??[]].find(y=>y.dataset.architectureNode===i)?.focus?.({preventScroll:!0}),p(i)},oe="flex h-11 min-w-11 items-center justify-center rounded-lg px-2 hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring disabled:opacity-40",V=e.jsxs(e.Fragment,{children:[e.jsx("button",{type:"button",className:oe,"aria-label":g("architecture.zoomOut"),disabled:q<=.01,onClick:()=>pe(K.current/1.25),children:e.jsx(Rt,{size:17})}),e.jsxs("button",{type:"button",className:`${oe} text-xs tabular-nums`,"aria-label":g("architecture.resetZoom"),title:g("architecture.resetZoom"),onClick:U,children:[Math.round(W.scale*q*100),"%"]}),e.jsx("button",{type:"button",className:oe,"aria-label":g("architecture.zoomIn"),disabled:q>=4,onClick:()=>pe(K.current*1.25),children:e.jsx(ot,{size:17})}),e.jsx("button",{type:"button",className:oe,"aria-label":g("architecture.fitGraph"),onClick:()=>pe(Math.min((O.width-24)/W.width,(O.height-24)/W.height)/W.scale),children:e.jsx(zt,{size:17})}),!z&&e.jsx("button",{ref:J,type:"button",className:oe,"aria-label":g("architecture.fullscreen"),onClick:()=>{ie.current=!0,X(!0)},children:e.jsx(Ot,{size:17})}),e.jsx("button",{type:"button",className:oe,"aria-label":g("architecture.download"),disabled:!f,onClick:()=>{A(!1),jt(new Blob([f],{type:"image/svg+xml"}),`architecture-${t.id}.svg`).catch(()=>A(!0))},children:e.jsx(At,{size:17})}),z&&e.jsx("button",{ref:P,type:"button",className:oe,"aria-label":g("architecture.closeFullscreen"),onClick:()=>X(!1),children:e.jsx($e,{size:18})})]}),v=t.nodes.find(i=>i.id===o)?.title??t.title,_=e.jsxs(e.Fragment,{children:[z?e.jsxs("header",{className:"flex shrink-0 flex-wrap items-center gap-1 border-b border-border/15 px-2 py-1",children:[e.jsx("div",{className:"min-w-0 basis-full px-1 min-[360px]:basis-0 min-[360px]:flex-1",children:C??e.jsx("h2",{className:"truncate text-xs font-semibold",title:v,children:v})}),e.jsx("div",{className:"flex w-full shrink-0 items-center justify-between gap-1 min-[360px]:w-auto",title:g("architecture.panHint"),children:V})]}):e.jsxs("div",{className:"sticky top-[60px] z-10 shrink-0 border-b border-border/15 bg-surface-2 px-2 py-1",children:[e.jsx("div",{className:"flex items-center justify-between gap-1",children:V}),e.jsx("p",{className:"px-1 pb-1 text-xs text-muted-foreground",children:g("architecture.panHint")})]}),z&&S,B&&e.jsx("p",{role:"alert",className:"px-3 py-2 text-xs text-destructive",children:g("architecture.downloadFailed")}),e.jsxs("div",{className:z?"relative flex min-h-0 flex-1 flex-col overflow-hidden min-[768px]:flex-row":"relative",children:[H?e.jsx("p",{role:"alert",className:"p-4 text-sm text-muted-foreground",children:g("architecture.diagramFailed")}):f?e.jsx("div",{ref:b,"data-sidebar-gesture-ignore":!0,className:`termdock-architecture-viewport overflow-auto overscroll-contain p-3 ${z?"min-h-0 min-w-0 flex-1":"h-[min(50dvh,26rem)]"}`,style:{touchAction:"none",maxHeight:!z&&O.clipHeight?Math.max(160,O.clipHeight-150):void 0},onPointerDown:i=>{if(i.button!==0)return;D.current.size||(E.current=!1,G.current=0);const y=i.target.closest("[data-architecture-node]")?.getAttribute("data-architecture-node")??void 0;D.current.set(i.pointerId,{x:i.clientX,y:i.clientY,nodeId:y}),D.current.size>1&&(E.current=!0);try{i.currentTarget.setPointerCapture?.(i.pointerId)}catch{}},onPointerMove:i=>{const y=D.current.get(i.pointerId);if(!y)return;const u=[...D.current.values()];D.current.set(i.pointerId,{...y,x:i.clientX,y:i.clientY});const $=[...D.current.values()];if($.length>=2){const w=ee=>Math.hypot(ee[0].x-ee[1].x,ee[0].y-ee[1].y),R=w(u),be=w($);R>0&&pe(K.current*be/R,($[0].x+$[1].x)/2,($[0].y+$[1].y)/2),E.current=!0}else{const w=y.x-i.clientX,R=y.y-i.clientY;G.current+=Math.hypot(w,R),G.current>5&&(E.current=!0),i.currentTarget.scrollLeft+=w,i.currentTarget.scrollTop+=R}},onPointerUp:i=>{const y=D.current.get(i.pointerId),u=D.current.size===1&&!E.current&&y?.nodeId;D.current.delete(i.pointerId),u&&(E.current=!0,Y(u))},onPointerCancel:i=>{D.current.delete(i.pointerId),E.current=!0},onLostPointerCapture:i=>{D.current.delete(i.pointerId)},children:e.jsx("div",{ref:k,role:"group","aria-label":g("architecture.modules"),className:"termdock-architecture-diagram mx-auto",style:je,onClick:i=>{if(E.current)return;const u=i.target.closest("[data-architecture-node]")?.getAttribute("data-architecture-node");u&&Y(u)},onKeyDown:i=>{if(i.key!=="Enter"&&i.key!==" ")return;const y=i.target.closest("[data-architecture-node]")?.getAttribute("data-architecture-node");y&&(i.preventDefault(),Y(y))},dangerouslySetInnerHTML:{__html:f}})}):e.jsx("p",{role:"status",className:"p-4 text-sm text-muted-foreground",children:g("architecture.rendering")}),z&&h]})]});return z?lt.createPortal(e.jsx("section",{ref:j,tabIndex:-1,role:"dialog","aria-modal":"true","aria-label":g("architecture.diagram"),"data-sidebar-gesture-ignore":!0,className:"fixed inset-0 z-modal-panel flex flex-col overflow-hidden bg-surface text-foreground pt-[env(safe-area-inset-top)] pb-[env(safe-area-inset-bottom)]",children:_}),document.body):e.jsx("section",{className:"overflow-clip rounded-xl border border-border/20 bg-surface-2","aria-label":g("architecture.diagram"),children:_})}function ge(t,o){let a=t.trim().replace(/^@/,"");/^([`"']).*\1$/.test(a)&&(a=a.slice(1,-1)),a=a.replace(/\\ /g," ").replace(/:\d+(?:-\d+)?$/,"").replace(/\/+$/,""),/^([`"']).*\1$/.test(a)&&(a=a.slice(1,-1));const p=o.replace(/\/+$/,"");if(a.startsWith("/")){if(!a.startsWith(`${p}/`))return null;a=a.slice(p.length+1)}return a=a.replace(/^\.\//,""),a.length<=1024&&Oe(a)?a:null}function rt(t,o){const a=[...t.matchAll(/^# (.+?): hunk \d+,/gm)].map(h=>h[1]),l=(a.length?a:t.split(/\r?\n/).map(h=>h.trim()).filter(Boolean)).map(h=>ge(h,o));if(l.some(h=>h===null))return null;const s=[...new Set(l)];return s.length<=20?s:null}function mt({rootPath:t,initialDirectory:o,selected:a,onChange:p,selectionDisabled:l=!1,compact:s=!1}){const{t:h}=ye(),d=t.replace(/\/+$/,"")||"/",[m,c]=n.useState(()=>o&&ge(o,d)?o.replace(/\/+$/,""):d),[S,C]=n.useState(""),[g,x]=n.useState(null),[k,b]=n.useState(0),[j,P]=n.useState(null);n.useEffect(()=>{if(!j)return;const N=window.setTimeout(()=>P(null),1800);return()=>window.clearTimeout(N)},[j]);const J=Ze(N=>N.invalidateDirectoryCache),f=new Set(a.map(N=>`${d==="/"?"":d}/${N}`)),L=N=>{const K=ge(N,d);l||!K||a.includes(K)||a.length>=20||p([...a,K])},H=N=>{N!==d&&!ge(N,d)||(c(N),C(""),x(null))},Z=`inline-flex shrink-0 items-center justify-center rounded-lg text-xs hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring disabled:opacity-40 ${s?"h-8 w-8 [@media(pointer:coarse)]:h-11 [@media(pointer:coarse)]:w-11":"h-11 w-11"}`,q=ge(m,d);return e.jsxs(e.Fragment,{children:[e.jsx("div",{className:"shrink-0 px-2 py-1",children:e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsx("button",{type:"button",className:Z,disabled:m===d,"aria-label":h("rightSidebar.parentFolder"),onClick:()=>H(m.slice(0,m.lastIndexOf("/"))||d),children:e.jsx(Pt,{size:17})}),e.jsx("button",{type:"button",className:Z,disabled:m===d,"aria-label":h("rightSidebar.backToProjectRoot"),onClick:()=>H(d),children:e.jsx(Et,{size:16})}),e.jsx("span",{className:"min-w-0 flex-1 truncate text-xs font-medium",title:m,children:q??(m.split("/").pop()||"/")}),q&&e.jsx("button",{type:"button",className:`${Z} text-primary`,disabled:l||!a.includes(q)&&a.length>=20,"aria-label":`${h("architecture.addScopeReference")}: ${m.split("/").pop()}`,title:q,"aria-pressed":a.includes(q),onClick:()=>L(m),children:a.includes(q)?e.jsx(wt,{size:15}):e.jsx(Mt,{size:15})}),e.jsx("button",{type:"button",className:Z,"aria-label":h("rightSidebar.refreshFiles"),onClick:()=>{J(m,!0),b(N=>N+1)},children:e.jsx(ut,{size:15})})]})}),l&&e.jsx("p",{role:"alert",className:"shrink-0 px-3 pb-2 text-xs text-muted-foreground",children:h("architecture.correctPathsFirst")}),e.jsx("div",{className:"shrink-0 border-b border-border/15 px-3 pb-2",children:e.jsx("input",{"aria-label":h("architecture.searchScopePaths"),placeholder:h("architecture.searchScopePaths"),value:S,onChange:N=>C(N.target.value),className:`${s?"h-9 [@media(pointer:coarse)]:h-11":"h-11"} w-full rounded-lg border border-border/20 bg-surface-2 px-3 text-sm focus-visible:ring-2 focus-visible:ring-ring`})}),e.jsx("div",{className:"min-h-0 flex-1 overflow-auto overscroll-contain bg-surface",children:e.jsx(Dt,{rootPath:m,selectedFilePath:g,onFileSelect:N=>{x(N),L(N)},onDirectoryRoot:H,onPathReference:L,getReferenceText:N=>ge(N,d)??N,query:S,onReferenceCopied:P,copiedReferenceKey:j,onSearchFromDirectory:H,referenceSelection:{paths:f,label:h("architecture.addScopeReference"),disabled:l||a.length>=20}},`${m}:${k}`)})]})}function Vt({rootPath:t,initialDirectory:o,initial:a,onConfirm:p,onCancel:l}){const{t:s}=ye(),h=n.useRef(null);qe(h,!0,l);const d=n.useId(),[m,c]=n.useState(a);n.useEffect(()=>{const C=document.body.style.overflow;return document.body.style.overflow="hidden",()=>{document.body.style.overflow=C}},[]);const S="inline-flex min-h-11 items-center justify-center gap-1.5 rounded-lg px-3 text-xs hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring disabled:opacity-40";return lt.createPortal(e.jsxs("div",{className:"fixed inset-0 z-popover flex items-center justify-center p-[max(0.75rem,env(safe-area-inset-top))]",children:[e.jsx("button",{type:"button",className:"absolute inset-0 z-10 cursor-default bg-[var(--app-backdrop)]","aria-label":s("common.cancel"),onClick:l}),e.jsxs("section",{ref:h,id:`${d}-dialog`,tabIndex:-1,role:"dialog","aria-modal":"true","aria-labelledby":d,"aria-describedby":`${d}-hint`,className:"relative z-20 flex h-full max-h-[42rem] w-full max-w-xl flex-col overflow-hidden rounded-xl border border-border/20 bg-surface text-foreground shadow-xl",children:[e.jsxs("header",{className:"shrink-0 px-3 py-1",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("h2",{id:d,className:"min-w-0 flex-1 text-sm font-semibold",title:s("architecture.browsePathsHint"),children:s("architecture.choosePaths")}),e.jsx("button",{type:"button",className:S,"aria-label":s("common.close"),onClick:l,children:e.jsx($e,{size:17})})]}),e.jsx("p",{id:`${d}-hint`,className:"sr-only",children:s("architecture.browsePathsHint")})]}),e.jsx(mt,{rootPath:t,initialDirectory:o,selected:m,onChange:c}),e.jsxs("footer",{className:"shrink-0 space-y-2 border-t border-border/15 p-3",children:[e.jsxs("p",{className:"text-xs text-muted-foreground",children:[s("architecture.selectedPaths")," ",m.length," / 20"]}),m.length>0&&e.jsx("div",{className:"flex max-h-24 flex-wrap gap-1 overflow-y-auto",children:m.map(C=>e.jsxs("button",{type:"button",className:`${S} min-w-0 max-w-full bg-surface-2`,"aria-label":`${s("architecture.removePath")}: ${C}`,onClick:()=>c(g=>g.filter(x=>x!==C)),children:[e.jsx("span",{className:"truncate font-mono",children:C}),e.jsx($e,{size:13,className:"shrink-0"})]},C))}),e.jsxs("div",{className:"flex justify-end gap-2",children:[e.jsx("button",{type:"button",className:S,onClick:l,children:s("common.cancel")}),e.jsx("button",{type:"button",className:`${S} bg-primary/15 text-primary`,onClick:()=>p(m),children:s("architecture.usePaths")})]})]})]})]}),document.body)}function st({rootPath:t,initial:o,outputFile:a,currentFile:p,currentDirectory:l,active:s=!0,onInsertPrompt:h,onPrepared:d,onClose:m}){const{t:c,locale:S}=ye(),C=n.useRef(null),g=n.useRef(null);qe(g,s,m),n.useLayoutEffect(()=>{s&&g.current?.scrollIntoView?.({block:"start"})},[s]);const[x,k]=n.useState(!1);n.useLayoutEffect(()=>{const v=g.current;if(!s||!v)return;const _=()=>k(v.clientWidth>=900);if(_(),typeof ResizeObserver>"u")return;const i=new ResizeObserver(_);return i.observe(v),()=>i.disconnect()},[s]);const b=n.useId(),[j,P]=n.useState(o.kind),[J,f]=n.useState(o.target),[L,H]=n.useState(o.paths.join(`
|
|
6
|
-
`)),[Z,q]=n.useState(o.depth),[N,K]=n.useState(o.focus),[z,X]=n.useState(null),[ie,de]=n.useState(!1),[he,ne]=n.useState(!1),B=n.useRef(0);n.useEffect(()=>()=>{B.current++},[]),n.useEffect(()=>{s||(B.current++,de(!1),ne(!1))},[s]);const A=rt(L,t),O=p?ge(p,t):null,I=l?ge(l,t):null,D=I?l:O?p.slice(0,p.lastIndexOf("/")):t,G=s&&x&&j!=="project"&&!a&&!he;let Q=null;try{(j==="project"||A)&&(Q=Be({kind:j,target:J,paths:A??[],depth:Z,focus:N}))}catch{}const me=Q?_t(t,S,Q,a):"",W="inline-flex min-h-11 items-center justify-center gap-1.5 rounded-lg text-xs font-medium transition hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring disabled:opacity-40",je=`${W} px-3`,pe=`${W} px-1`,U="min-h-10 w-full min-w-0 rounded-lg border border-border/20 bg-surface px-2 py-2 text-sm text-foreground focus-visible:ring-2 focus-visible:ring-ring",Y=()=>{B.current++,de(!1),X(null)},oe=v=>{H(A?[...new Set([...A,v])].join(`
|
|
7
|
-
`):`${L.trim()}
|
|
8
|
-
${v}`),Y()},V=Q;return e.jsxs("div",{ref:g,id:`${b}-workspace`,tabIndex:-1,className:G?"grid min-h-0 min-w-0 flex-1 grid-cols-[20rem_minmax(0,1fr)] grid-rows-[minmax(0,1fr)] items-start gap-3":"min-w-0 shrink-0",children:[G&&e.jsxs("section",{"aria-label":c("architecture.choosePaths"),"aria-describedby":`${b}-browser-hint`,className:"flex h-full min-h-0 min-w-0 flex-col overflow-hidden rounded-xl border border-border/20 bg-surface-2",children:[e.jsxs("header",{className:"flex min-h-9 shrink-0 items-center gap-2 px-3",children:[e.jsx("h3",{className:"min-w-0 flex-1 truncate text-xs font-medium",title:c("architecture.browsePathsHint"),children:c("architecture.choosePaths")}),e.jsxs("p",{role:"status","aria-label":`${c("architecture.selectedPaths")} ${A?.length??0} / 20`,className:"shrink-0 text-xs tabular-nums text-muted-foreground",children:[A?.length??0," / 20"]}),e.jsx("p",{id:`${b}-browser-hint`,className:"sr-only",children:c("architecture.browsePathsHint")})]}),e.jsx(mt,{compact:!0,rootPath:t,initialDirectory:D,selected:A??[],selectionDisabled:!A,onChange:v=>{H(v.join(`
|
|
9
|
-
`)),Y()}})]}),e.jsxs("form",{ref:C,tabIndex:-1,className:`min-w-0 space-y-2.5 rounded-xl border border-border/20 bg-surface-2 p-3 ${G?"max-h-full overflow-y-auto overscroll-contain":""}`,onSubmit:v=>{if(v.preventDefault(),!V||ie||!s||!C.current)return;const _=++B.current,i=C.current;i.focus({preventScroll:!0}),de(!0),X(null),Promise.resolve().then(()=>_===B.current&&i.isConnected?h(me,i):!1).then(y=>{_===B.current&&(y===!0?(d(a??He(V),V),X("inserted")):X("insertFailed"))}).catch(()=>{_===B.current&&X("insertFailed")}).finally(()=>{_===B.current&&de(!1)})},children:[e.jsxs("div",{className:"flex items-center justify-between gap-2",children:[e.jsx("h2",{className:"text-sm font-medium",children:c(a?"architecture.updateAnalysis":"architecture.prepare")}),e.jsx("button",{type:"button",className:`${je} px-2`,"aria-label":c("architecture.closePreparation"),onClick:m,children:e.jsx($e,{size:16})})]}),e.jsxs("label",{className:"block space-y-1 text-xs",htmlFor:`${b}-kind`,children:[e.jsx("span",{children:c("architecture.analysisRange")}),e.jsxs("select",{id:`${b}-kind`,className:U,value:j,disabled:!!a,onChange:v=>{P(v.target.value),Y()},children:[e.jsx("option",{value:"project",children:c("architecture.projectRange")}),e.jsx("option",{value:"module",children:c("architecture.moduleRange")}),e.jsx("option",{value:"feature",children:c("architecture.featureRange")})]})]}),j==="feature"&&e.jsxs("label",{className:"block space-y-1 text-xs",htmlFor:`${b}-target`,children:[e.jsx("span",{children:c("architecture.featureTarget")}),e.jsx("input",{id:`${b}-target`,className:U,value:J,readOnly:!!a,maxLength:1e3,placeholder:c("architecture.featurePlaceholder"),onChange:v=>{f(v.target.value),Y()},"aria-describedby":`${b}-validation`})]}),j!=="project"&&e.jsxs("div",{className:"space-y-1",children:[e.jsx("label",{className:"block text-xs",htmlFor:`${b}-paths`,children:c(j==="module"?"architecture.modulePaths":"architecture.startPaths")}),e.jsx("textarea",{id:`${b}-paths`,className:`${U} resize-y font-mono text-xs`,rows:2,value:L,readOnly:!!a,placeholder:c("architecture.modulePlaceholder"),onChange:v=>{H(v.target.value),Y()},onBlur:()=>{!a&&A&&H(A.join(`
|
|
10
|
-
`))},onPaste:v=>{if(a)return;const _=rt(v.clipboardData.getData("text/plain"),t);if(!_?.length||!A)return;const i=[...new Set([...A,..._])];i.length>20||(v.preventDefault(),H(i.join(`
|
|
11
|
-
`)),Y())},"aria-describedby":`${b}-paths-hint ${b}-validation`}),!a&&e.jsxs("div",{className:"flex flex-wrap gap-1",children:[!G&&e.jsxs("button",{type:"button",className:`${pe} text-primary`,"aria-label":c("architecture.choosePaths"),onClick:()=>ne(!0),children:[e.jsx(It,{size:14}),c("architecture.browsePaths")]}),I&&e.jsx("button",{type:"button",className:pe,disabled:!!A?.includes(I)||(A?.length??0)>=20,title:I,onClick:()=>oe(I),children:c("architecture.useCurrentDirectory")}),O&&e.jsx("button",{type:"button",className:pe,disabled:!!A?.includes(O)||(A?.length??0)>=20,title:O,onClick:()=>oe(O),children:c("architecture.useCurrentFile")})]}),e.jsx("p",{id:`${b}-paths-hint`,className:"text-xs leading-relaxed text-muted-foreground",title:t,children:c("architecture.pathsHint")})]}),!Q&&(L.trim()||J.trim())&&e.jsx("p",{id:`${b}-validation`,role:"alert",className:"text-xs text-muted-foreground",children:c(j==="module"?"architecture.invalidPaths":"architecture.requiredFeature")}),e.jsxs("label",{className:"block space-y-1 text-xs",htmlFor:`${b}-focus`,children:[e.jsx("span",{children:c("architecture.focus")}),e.jsx("textarea",{id:`${b}-focus`,className:`${U} resize-y`,rows:2,maxLength:2e3,value:N,placeholder:c("architecture.focusPlaceholder"),onChange:v=>{K(v.target.value),Y()}})]}),e.jsxs("div",{className:"flex flex-wrap gap-2",children:[e.jsx("button",{type:"submit",disabled:!Q||ie,className:`${je} bg-primary/15 text-primary`,children:c(ie?"architecture.inserting":"architecture.insertPrompt")}),e.jsxs("button",{type:"button",disabled:!Q||ie,className:je,onClick:()=>{if(!V)return;const v=++B.current;Promise.resolve().then(()=>navigator.clipboard.writeText(me)).then(()=>{v===B.current&&(d(a??He(V),V),X("copied"))}).catch(()=>{v===B.current&&X("failed")})},children:[e.jsx(vt,{size:14}),c("architecture.copyPrompt")]})]}),z&&e.jsx("p",{role:"status",className:"text-xs text-muted-foreground",children:c(`architecture.${z}`)}),e.jsxs("details",{children:[e.jsx("summary",{className:"cursor-pointer py-2 text-xs text-muted-foreground",children:c("architecture.analysisOptions")}),e.jsxs("div",{className:"space-y-3 pt-1",children:[e.jsxs("label",{className:"block space-y-1 text-xs",htmlFor:`${b}-depth`,children:[e.jsx("span",{children:c("architecture.dependencyDepth")}),e.jsxs("select",{id:`${b}-depth`,className:U,value:Z,onChange:v=>{q(v.target.value),Y()},children:[e.jsx("option",{value:"boundary",children:c("architecture.boundaryDepth")}),e.jsx("option",{value:"dependencies",children:c("architecture.followDepth")})]})]}),j==="feature"&&e.jsx("p",{className:"text-xs leading-relaxed text-muted-foreground",children:c("architecture.featureScopeHint")}),e.jsx("p",{className:"text-xs leading-relaxed text-muted-foreground",children:c(a?"architecture.updateOnly":"architecture.independentHint")})]})]}),e.jsxs("details",{children:[e.jsx("summary",{className:"cursor-pointer py-2 text-xs text-muted-foreground",children:c("architecture.previewPrompt")}),e.jsx("textarea",{readOnly:!0,"aria-label":c("architecture.previewPrompt"),value:me,className:`${U} mt-2 h-52 resize-y font-mono text-xs`})]}),e.jsx("p",{className:"text-xs leading-relaxed text-muted-foreground",children:c("architecture.promptHint")})]}),s&&he&&e.jsx(Vt,{rootPath:t,initialDirectory:D,initial:A??[],onCancel:()=>ne(!1),onConfirm:v=>{H(v.join(`
|
|
12
|
-
`)),ne(!1),Y()}})]})}function Kt({node:t,view:o,parentId:a,onSelect:p,onExplore:l,onAnalyze:s,onOpenFile:h,onClose:d,embedded:m=!1}){const{t:c}=ye(),S=We(o,a),C=S.edges.filter(x=>x.from===t.id||x.to===t.id),g="inline-flex min-h-11 items-center justify-center gap-1.5 rounded-lg px-3 text-xs font-medium transition hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring";return e.jsxs("section",{className:m?"space-y-3":"space-y-3 rounded-xl border border-primary/30 bg-surface-2 p-3","aria-label":t.title,children:[!m&&e.jsxs("div",{className:"flex items-start justify-between gap-2",children:[e.jsx("h3",{className:"pt-2 text-sm font-semibold",children:t.title}),e.jsx("button",{type:"button",className:`${g} shrink-0 px-2`,"aria-label":c("architecture.closeDetail"),onClick:d,children:e.jsx($e,{size:16})})]}),e.jsx("p",{className:"whitespace-pre-wrap break-words text-sm leading-relaxed",children:t.summary}),e.jsxs("div",{className:"flex flex-wrap gap-2",children:[o.nodes.some(x=>x.parentId===t.id)&&e.jsxs("button",{type:"button",className:`${g} bg-primary/15 text-primary`,onClick:l,children:[c("architecture.explore"),e.jsx(Fe,{size:14})]}),t.files.length>0&&e.jsxs("button",{type:"button",className:`${g} text-primary`,onClick:s,children:[e.jsx(dt,{size:14}),c("architecture.analyzeModule")]})]}),C.length>0&&e.jsxs("div",{children:[e.jsx("h4",{className:"mb-1 text-xs font-semibold text-muted-foreground",children:c("architecture.connections")}),e.jsx("div",{className:"space-y-1",children:C.map((x,k)=>{const b=x.from===t.id,j=S.nodes.find(P=>P.id===(b?x.to:x.from));return j?e.jsxs("button",{type:"button",className:"flex min-h-11 w-full items-center gap-2 rounded-lg bg-surface px-3 py-2 text-left text-xs hover:bg-surface-elevated",onClick:()=>p(j.id),"aria-label":`${c(b?"architecture.outgoing":"architecture.incoming")}: ${j.title} · ${x.label}`,children:[b?e.jsx(Nt,{size:15,className:"shrink-0 text-primary"}):e.jsx(Ft,{size:15,className:"shrink-0 text-muted-foreground"}),e.jsxs("span",{className:"min-w-0 flex-1",children:[e.jsx("span",{className:"block font-medium",children:j.title}),e.jsxs("span",{className:"mt-0.5 block break-words text-muted-foreground",children:[c(b?"architecture.outgoing":"architecture.incoming")," · ",x.label]})]}),e.jsx(Fe,{size:14,className:"shrink-0"})]},`${x.from}:${x.to}:${k}`):null})})]}),t.files.length>0&&e.jsxs("details",{open:t.files.length<=4,children:[e.jsxs("summary",{className:"min-h-11 cursor-pointer py-3 text-xs font-semibold text-muted-foreground",children:[c("architecture.sourceFiles")," (",t.files.length,")"]}),t.files.map(x=>e.jsxs("button",{type:"button",className:"block min-h-11 w-full break-all rounded-lg px-2 py-2 text-left font-mono text-xs text-primary hover:bg-surface-elevated",onClick:()=>h(x),children:[x.path,x.line?`:${x.line}`:""]},`${x.path}:${x.line??""}`))]})]})}function Xt({title:t,stageKey:o,source:a=!1,fullHeight:p=!1,inGraph:l=!1,docked:s=!1,side:h=!1,active:d=!0,onBack:m,backLabel:c,onClose:S,onDismiss:C,onCollapse:g,children:x}){const{t:k}=ye(),b=n.useRef(null),j=n.useRef(null),P=n.useRef(new Map);qe(b,d&&!l&&(!s||p),C),n.useLayoutEffect(()=>{j.current&&(j.current.scrollTop=P.current.get(o)??0),d&&b.current?.querySelector("button:not(:disabled)")?.focus({preventScroll:!0})},[o,d]);const J=s?p?"relative h-full w-full flex-1":h?"relative h-full w-[22rem] max-w-[40%] shrink-0":"relative h-[48%] max-h-96 w-full shrink-0":l?`${a||p?"inset-0":"inset-x-0 bottom-0 max-h-[48%]"} min-[768px]:inset-y-0 min-[768px]:left-auto min-[768px]:right-0 min-[768px]:max-h-none ${a||p?"min-[768px]:w-[min(50vw,40rem)]":"min-[768px]:w-[22rem]"}`:h?"inset-y-0 right-0 w-[22rem] max-w-full":"inset-0",f="inline-flex min-h-11 shrink-0 items-center justify-center gap-1.5 rounded-lg px-2 text-xs text-primary hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring",L=()=>{j.current&&P.current.set(o,j.current.scrollTop)};return e.jsxs("aside",{ref:b,tabIndex:-1,role:l||s&&!p?void 0:"dialog","aria-modal":l?void 0:!1,"aria-label":t,"data-architecture-inspector":!0,"data-sidebar-gesture-ignore":!0,onClickCapture:L,className:`${s?"":"absolute"} z-20 flex min-h-0 flex-col overflow-hidden border border-border/30 bg-surface ${s?"":"shadow-xl"} ${J}`,children:[e.jsxs("header",{className:"flex shrink-0 items-center gap-2 border-b border-border/15 px-2 py-1",children:[e.jsxs("button",{type:"button",className:f,"aria-label":m?c:k("architecture.closeDetail"),onClick:m??S,children:[e.jsx(kt,{size:17}),e.jsx("span",{children:m?c:k("architecture.backToMap")})]}),e.jsx("h2",{className:"min-w-0 flex-1 truncate text-sm font-semibold",title:t,children:t}),g&&e.jsx("button",{type:"button",className:f,"aria-label":k("architecture.collapseDetail"),onClick:g,children:e.jsx(ct,{size:17})}),m&&e.jsx("button",{type:"button",className:f,"aria-label":k("architecture.closeDetail"),onClick:S,children:e.jsx($e,{size:17})})]}),e.jsx("div",{ref:j,onScroll:L,className:`min-h-0 flex-1 ${a?"overflow-hidden":"overflow-y-auto overscroll-contain p-3"}`,children:x})]})}function Gt({node:t,onExpand:o,onClose:a}){const{t:p}=ye(),l=n.useRef(null),s=n.useRef(null);n.useLayoutEffect(()=>{document.activeElement!==l.current&&(s.current=document.activeElement),l.current?.focus({preventScroll:!0})},[t.id]),n.useLayoutEffect(()=>()=>{s.current?.isConnected&&s.current.focus({preventScroll:!0})},[]);const h="inline-flex min-h-11 shrink-0 items-center justify-center rounded-lg px-2 text-xs hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring";return e.jsxs("section",{ref:l,tabIndex:-1,"aria-label":t.title,"data-architecture-inspector":!0,"data-sidebar-gesture-ignore":!0,className:"shrink-0 border-t border-border/30 bg-surface px-3 pb-2",children:[e.jsxs("div",{className:"flex items-center gap-2",children:[e.jsx("h2",{className:"min-w-0 flex-1 truncate text-sm font-semibold",title:t.title,children:t.title}),e.jsx("button",{type:"button",className:`${h} text-primary`,onClick:o,children:p("architecture.expandDetail")}),e.jsx("button",{type:"button",className:h,"aria-label":p("architecture.closeDetail"),onClick:a,children:e.jsx($e,{size:17})})]}),e.jsx("p",{className:"line-clamp-2 break-words text-xs leading-relaxed text-muted-foreground",children:t.summary})]})}function Ve(t){return`termdock.architecture.selection:${t}`}function nt(t){try{const o=t?sessionStorage.getItem(Ve(t)):null;return o&&Ee(o)?o:se}catch{return se}}function at(t){try{const o=t?sessionStorage.getItem(Ve(t)):null;return!!o&&Ee(o)}catch{return!1}}function mr({rootPath:t,active:o,onInsertPrompt:a,onOpenFile:p,renderSource:l}){const{t:s,locale:h}=ye(),d=Ze(r=>r.rootPath===t?r.selectedFilePath:null),m=Ze(r=>r.rootPath===t?r.explorerRoot:null),[c,S]=n.useState(()=>nt(t)),[C,g]=n.useState([]),[x,k]=n.useState(!1),[b,j]=n.useState(Ne),[P,J]=n.useState(null),[f,L]=n.useState(null),[H,Z]=n.useState(!0),[q,N]=n.useState(null),[K,z]=n.useState(0),[X,ie]=n.useState(""),[de,he]=n.useState([]),[ne,B]=n.useState(null),[A,O]=n.useState([]),[I,D]=n.useState(null),[E,G]=n.useState(null),[Q,me]=n.useState(null),[W,je]=n.useState(!1),[pe,U]=n.useState(!1),[Y,oe]=n.useState(()=>typeof window<"u"&&window.innerWidth>=768),V=n.useRef(0),v=n.useRef(at(t)),_=n.useRef(null),i=n.useRef(null),[y,u]=n.useState(0),[$,w]=n.useState("auto"),R=$==="auto"?y>=560?"graph":"outline":$,be=n.useRef(null),ee=r=>{v.current=!0,S(r);try{t&&sessionStorage.setItem(Ve(t),r)}catch{}},te=()=>{J(null),be.current?.focus({preventScroll:!0})};n.useEffect(()=>{const r=()=>oe(window.innerWidth>=768);return window.addEventListener("resize",r),()=>window.removeEventListener("resize",r)},[]),n.useEffect(()=>{const r=_.current;if(!r||!o||typeof ResizeObserver>"u")return;const T=()=>{r.clientWidth>0&&u(r.clientWidth)};T();const ue=new ResizeObserver(T);return ue.observe(r),()=>ue.disconnect()},[o]),n.useEffect(()=>{L(null),N(null),Z(!0),ie(""),he([]),le(),J(null),S(nt(t)),g([]),k(!1),j(Ne),v.current=at(t)},[t]),n.useEffect(()=>{L(null),N(null),Z(!0),ie(""),he([]),le()},[c]),n.useEffect(()=>{if(!o||!t)return;let r=!1,T=null,ue;const Ge=async gt=>{const Je=++V.current,Te=new AbortController;T=Te,gt&&(Z(!0),N(null));const yt=window.setTimeout(()=>Te.abort(),15e3);try{const[we,Ae]=await Promise.allSettled([Jt(t,Te.signal,c),Zt(t,Te.signal)]);if(r||V.current!==Je)return;if(Ae.status==="fulfilled"?(g(Ae.value),k(!1)):k(!0),we.status==="rejected")throw we.reason;L(Qe=>JSON.stringify(Qe)===JSON.stringify(we.value)?Qe:we.value),N(null),!we.value&&c===se&&!v.current&&Ae.status==="fulfilled"&&Ae.value.length===1&&ee(Ae.value[0])}catch(we){if(r||V.current!==Je)return;N(we instanceof Ye?"format":"load")}finally{window.clearTimeout(yt),!r&&V.current===Je&&(Z(!1),ue=setTimeout(()=>{r||Ge(!1)},1e4))}};return Ge(!0),()=>{r=!0,++V.current,T?.abort(),clearTimeout(ue)}},[t,o,K,c]);const M=f?.perspectives.find(r=>r.id===X)??f?.perspectives[0],ae=n.useMemo(()=>{const r=[];for(const T of de){if(!M?.nodes.some(ue=>ue.id===T&&ue.parentId===r[r.length-1]))break;r.push(T)}return r},[de,M]),fe=ae[ae.length-1],Ce=n.useMemo(()=>M?We(M,fe):null,[M,fe]),ce=Ce?.nodes.find(r=>r.id===ne),ze=M?.nodes.find(r=>r.id===fe),pt=[...new Set([se,...C,c])],De=f?.analysis??(c===se?Ne:b.kind==="project"?null:b),le=()=>{B(null),U(!1),O([]),D(null),G(null),me(null)},Ie=(r,T=!1)=>{O(ue=>T&&ne?[...ue,ne]:[]),U(T),D(null),G(null),me(null),B(r)},Se=r=>{he(r),le(),i.current&&(i.current.scrollTop=0)},ft=r=>{l?(U(!0),D(r)):p(r)},xt=r=>{G({...Ne,kind:"module",paths:[...new Set(r.files.map(T=>T.path))].slice(0,20)}),me(null)},Ke=I?()=>D(null):E?()=>G(null):A.length?()=>{B(A[A.length-1]),O(r=>r.slice(0,-1))}:void 0,bt=s(I||E?"architecture.backToModule":"architecture.previousModule"),Re=W?Y:y>=900,Ue=!Re&&!pe&&!I&&!E,Me=!W&&!!ce&&(!!I||!!E||R==="outline"),xe="inline-flex min-h-11 items-center justify-center gap-1.5 rounded-lg px-3 text-xs font-medium transition hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring disabled:opacity-40",_e=Ue?le:Ke??(!Re&&R==="graph"?()=>U(!1):le),Xe=r=>ce&&((r||R==="graph")&&Ue?e.jsx(Gt,{node:ce,onExpand:()=>U(!0),onClose:le}):e.jsx(Xt,{active:o&&!E,docked:!r||!I&&!E,title:ce.title,stageKey:`${ce.id}:${I?`${I.path}:${I.line}`:E?"analysis":"details"}`,source:!!I,fullHeight:r?!!E:Me,inGraph:r,side:Re,onBack:Ke,backLabel:bt,onClose:le,onDismiss:_e,onCollapse:!Re&&!Me&&!I&&!E?()=>U(!1):void 0,children:I&&l?l(I):E?e.jsxs(e.Fragment,{children:[e.jsx(st,{active:o,rootPath:t,currentFile:d,currentDirectory:m,initial:E,onInsertPrompt:a,onPrepared:me,onClose:()=>G(null)},ce.id),Q&&e.jsx("button",{type:"button",className:`${xe} mt-3 bg-primary/15 text-primary`,onClick:()=>{j(E),ee(Q),le()},children:s("architecture.viewPrepared")})]}):e.jsx(Kt,{embedded:!0,node:ce,view:M,parentId:fe,onSelect:T=>Ie(T,!0),onExplore:()=>Se([...ae,ce.id]),onAnalyze:()=>xt(ce),onOpenFile:ft,onClose:le})}));return t?e.jsxs("div",{ref:_,className:"relative flex h-full min-h-0 flex-col",onKeyDown:r=>{!W&&ce&&r.key==="Escape"&&!r.defaultPrevented&&!r.nativeEvent.isComposing&&(r.preventDefault(),r.stopPropagation(),_e())},children:[e.jsxs("div",{className:"flex shrink-0 items-center justify-between gap-2 border-b border-border/15 px-3 py-2",children:[e.jsxs("span",{className:"flex items-center gap-2 text-sm font-semibold",children:[e.jsx(et,{size:16}),s("architecture.title")]}),e.jsxs("div",{className:"flex items-center gap-1",children:[e.jsxs("button",{ref:be,type:"button",className:xe,disabled:!De,onClick:()=>{De&&(le(),J(P?null:{initial:De,...f?{outputFile:c}:{}}))},"aria-expanded":!!P,children:[e.jsx(dt,{size:14}),s(f?"architecture.update":"architecture.generate")]}),(f||c!==se)&&e.jsx("button",{type:"button",className:`${xe} px-2`,"aria-label":s("architecture.newAnalysis"),onClick:()=>{le(),J({initial:Ne})},children:e.jsx(ot,{size:16})}),e.jsx("button",{type:"button",className:`${xe} px-2`,"aria-label":s("architecture.refresh"),disabled:H,onClick:()=>z(r=>r+1),children:e.jsx(ut,{size:15,className:H?"animate-spin":""})})]})]}),e.jsxs("div",{className:`relative flex min-h-0 flex-1 ${Re&&!Me?"flex-row":"flex-col"}`,"data-architecture-workspace":!0,children:[e.jsx("div",{ref:i,hidden:Me,"data-architecture-content":!0,className:`min-h-0 min-w-0 flex-1 overflow-y-auto p-3 [overflow-anchor:none] ${P?"flex flex-col":""}`,children:P?e.jsx(st,{active:o,rootPath:t,currentFile:d,currentDirectory:m,initial:P.initial,outputFile:P.outputFile,onInsertPrompt:a,onPrepared:(r,T)=>{j(T),ee(r)},onClose:te},`${P.outputFile??"new"}:${JSON.stringify(P.initial)}`):e.jsxs(e.Fragment,{children:[e.jsxs("label",{className:"mb-3 flex items-center gap-2 text-xs text-muted-foreground",children:[s("architecture.savedAnalyses"),e.jsx("select",{"aria-label":s("architecture.savedAnalyses"),value:c,onChange:r=>{j(Ne),ee(r.target.value)},className:"min-h-10 min-w-0 flex-1 rounded-lg border border-border/20 bg-surface-2 px-2 text-sm text-foreground",children:pt.map(r=>e.jsx("option",{value:r,children:r===se?s("architecture.projectRange"):`${s(r.includes("/module-")?"architecture.moduleRange":"architecture.featureRange")}: ${r===c&&f?.analysis?f.analysis.target.replace(/\n/g,", "):qt(r)}`},r))})]}),x&&e.jsx("p",{role:"alert",className:"mb-3 text-xs text-muted-foreground",children:s("architecture.libraryFailed")}),H&&!f&&e.jsx("p",{role:"status",className:"py-4 text-sm text-muted-foreground",children:s("architecture.loading")}),q&&e.jsxs("div",{role:"alert",className:"mb-3 rounded-lg border border-destructive/30 p-3 text-sm",children:[e.jsx("p",{children:s(q==="format"?"architecture.invalid":"architecture.loadFailed")}),f&&e.jsx("p",{className:"mt-1 text-xs text-muted-foreground",children:s("architecture.previous")}),e.jsx("button",{type:"button",className:`${xe} mt-2 bg-surface-2`,onClick:()=>z(r=>r+1),children:s("architecture.retry")})]}),!H&&!q&&!f&&e.jsxs("div",{className:"flex flex-col items-center gap-3 px-4 py-8 text-center",children:[e.jsx(et,{size:32,className:"text-muted-foreground"}),e.jsx("h2",{className:"text-base font-medium",children:s("architecture.empty")}),e.jsx("p",{className:"max-w-sm text-sm leading-relaxed text-muted-foreground",children:s(c===se?"architecture.emptyHint":"architecture.awaitingFile")})]}),f&&M&&Ce&&e.jsxs("div",{className:"space-y-3",children:[!De&&e.jsx("p",{className:"text-xs text-muted-foreground",children:s("architecture.scopeUnavailable")}),f.analysis&&e.jsxs("p",{className:"break-words text-xs text-muted-foreground",children:[s(`architecture.${f.analysis.kind}Range`),f.analysis.target?` · ${f.analysis.target.replace(/\n/g,", ")}`:""," · ",s(f.analysis.depth==="boundary"?"architecture.boundaryDepth":"architecture.followDepth")]}),f.summary.length<=240&&e.jsx("p",{className:"whitespace-pre-wrap break-words text-sm leading-relaxed text-muted-foreground",children:f.summary}),e.jsxs("label",{className:"sticky -top-3 z-10 !mt-0 -mx-3 flex items-center gap-2 bg-surface px-3 py-2 text-xs text-muted-foreground",children:[s("architecture.perspective"),e.jsx("select",{"aria-label":s("architecture.perspective"),value:M.id,onChange:r=>{ie(r.target.value),Se([])},className:"min-h-11 min-w-0 flex-1 rounded-lg border border-border/20 bg-surface-2 px-2 text-sm text-foreground",children:f.perspectives.map(r=>e.jsx("option",{value:r.id,children:r.title},r.id))})]}),ae.length>0&&e.jsxs("nav",{className:"flex flex-wrap items-center gap-1 text-xs","aria-label":s("architecture.breadcrumb"),children:[e.jsx("button",{type:"button",className:`${xe} px-2`,onClick:()=>Se([]),children:M.title}),ae.map((r,T)=>e.jsxs("span",{className:"inline-flex items-center gap-1",children:[e.jsx(Fe,{size:12}),e.jsx("button",{type:"button",className:`${xe} px-2`,onClick:()=>Se(ae.slice(0,T+1)),children:M.nodes.find(ue=>ue.id===r)?.title})]},r))]}),e.jsx("p",{className:"whitespace-pre-wrap break-words text-sm leading-relaxed text-muted-foreground",children:ze?.summary??M.summary}),e.jsx("div",{role:"group","aria-label":s("architecture.browseMode"),className:"flex gap-1 rounded-lg bg-surface-2 p-1",children:["outline","graph"].map(r=>e.jsx("button",{type:"button","aria-pressed":R===r,className:`${xe} flex-1 ${R===r?"bg-surface text-primary":"text-muted-foreground"}`,onClick:()=>w(r),children:s(r==="outline"?"architecture.outlineMode":"architecture.graphMode")},r))}),R==="graph"?e.jsxs(e.Fragment,{children:[e.jsx(Yt,{view:M,parentId:fe,selectedId:ne,onSelect:Ie,active:o,referenceWidth:y,inspector:Xe(!0),inspectorStage:I?"source":E?"analysis":Ue?"preview":"details",onDismissInspector:_e,onExpandedChange:r=>{je(r),r||le()},heading:e.jsxs("div",{className:"relative",children:[e.jsx("select",{"aria-label":s("architecture.perspective"),title:M.title,value:M.id,onChange:r=>{ie(r.target.value),Se([])},className:"h-11 w-full min-w-0 appearance-none truncate bg-surface pr-4 text-xs font-semibold focus-visible:ring-2 focus-visible:ring-ring",children:f.perspectives.map(r=>e.jsx("option",{value:r.id,children:r.title},r.id))}),e.jsx(ct,{size:12,className:"pointer-events-none absolute right-0 top-1/2 -translate-y-1/2 text-muted-foreground"})]}),navigation:ae.length>0?e.jsxs("nav",{"aria-label":s("architecture.breadcrumb"),className:"flex items-center gap-1 px-2",children:[e.jsx("button",{type:"button",className:`${xe} shrink-0 px-2`,onClick:()=>Se(ae.slice(0,-1)),children:s("architecture.parentModule")}),e.jsxs("span",{className:"truncate text-xs text-muted-foreground",children:[M.title," / ",ze?.title]})]}):void 0}),e.jsxs("details",{children:[e.jsxs("summary",{className:"min-h-11 cursor-pointer py-3 text-xs text-muted-foreground",children:[s("architecture.modules")," (",Ce.nodes.length,")"]}),e.jsx("div",{className:"flex flex-wrap gap-2",children:Ce.nodes.map(r=>e.jsx("button",{type:"button","aria-pressed":ce?.id===r.id,className:`${xe} bg-surface-2`,onClick:()=>Ie(r.id),children:r.title},r.id))})]})]}):e.jsx("div",{className:"space-y-2",role:"group","aria-label":s("architecture.modules"),children:Ce.nodes.map(r=>e.jsx("div",{children:e.jsxs("button",{type:"button","aria-label":r.title,"aria-expanded":ce?.id===r.id,className:"block min-h-16 w-full rounded-xl border border-border/20 bg-surface-2 p-3 text-left transition hover:bg-surface-elevated focus-visible:ring-2 focus-visible:ring-ring",onClick:()=>Ie(r.id),children:[e.jsxs("span",{className:"flex items-center justify-between gap-2",children:[e.jsx("span",{className:"text-sm font-medium",children:r.title}),e.jsx(Fe,{size:16,className:"shrink-0 text-muted-foreground"})]}),e.jsx("span",{className:"mt-1.5 line-clamp-2 break-words text-xs leading-relaxed text-muted-foreground",children:r.summary})]})},r.id))}),e.jsxs("details",{className:"rounded-lg border border-border/15 px-3",children:[e.jsxs("summary",{className:"min-h-11 cursor-pointer py-3 text-xs text-muted-foreground",children:[s("architecture.analysisNotes")," · ",s("architecture.savedAt")," ",new Date(f.generatedAt).toLocaleString(h==="zh"?"zh-CN":"en-US")]}),e.jsxs("div",{className:"space-y-3 pb-3",children:[f.summary.length>240&&e.jsx("p",{className:"whitespace-pre-wrap break-words text-sm leading-relaxed text-muted-foreground",children:f.summary}),f.details?.limitations.length?e.jsxs("div",{children:[e.jsx("h3",{className:"mb-1 text-xs font-semibold",children:s("architecture.limitations")}),e.jsx("ul",{className:"list-disc space-y-1 pl-4 text-xs leading-relaxed text-muted-foreground",children:f.details.limitations.map((r,T)=>e.jsx("li",{children:r},T))})]}):null,f.details?.analyzedPaths.length?e.jsxs("details",{children:[e.jsxs("summary",{className:"min-h-11 cursor-pointer py-3 text-xs text-muted-foreground",children:[s("architecture.analyzedPaths")," (",f.details.analyzedPaths.length,")"]}),f.details.analyzedPaths.map(r=>e.jsx("button",{type:"button",className:"block min-h-11 w-full break-all rounded px-2 py-2 text-left font-mono text-xs text-primary hover:bg-surface-elevated",onClick:()=>p({path:r}),children:r},r))]}):null]})]}),ze&&ze.files.length>0&&e.jsxs("details",{children:[e.jsx("summary",{className:"cursor-pointer py-2 text-xs text-muted-foreground",children:s("architecture.sourceFiles")}),ze.files.map(r=>e.jsxs("button",{type:"button",className:"block min-h-10 w-full break-all rounded px-2 py-2 text-left font-mono text-xs text-primary hover:bg-surface-2",onClick:()=>p(r),children:[r.path,r.line?`:${r.line}`:""]},`${r.path}:${r.line??""}`))]})]})]})}),o&&!W&&Xe(!1)]})]}):e.jsx("p",{className:"p-5 text-sm text-muted-foreground",children:s("fileTree.noWorkingDir")})}export{mr as ArchitecturePanel};
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
Binary file
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
import{d5 as Y,bA as Z,az as F,a_ as H,cQ as J,S as C,bv as e,T as X,bj as L}from"./app-B6FdOF6K.js";import{b as s}from"./dnd-BCFAPC0L.js";import{a5 as r,Z as I,P as ee,W as te,q as se,R as S,i as ne,$ as ae,a0 as re}from"./App-ggIA_xqR.js";import"./react-XDCjal2T.js";import"./terminal-C7X98Amf.js";import"./gestureArbiter-JW8vcVRm.js";import"./triangle-alert-CbMRJ6sx.js";import"./referenceLongPress-bZ0xp-v2.js";function xe({groupId:m,activeSessionId:n,onOpenSidebar:h,leftSidebarVisible:R=!1,onToggleRightSidebar:b,rightSidebarOpen:g=!1,defaultSessionMode:T}){const j=s.useRef(null);s.useEffect(()=>{j.current?.focus()},[]);const[i,v]=s.useState(null),[z,D]=s.useState([]),[u,x]=s.useState(null),[y,P]=s.useState(null),[p,$]=s.useState(null),[G,A]=s.useState(null),o=Y(),[W,w]=s.useState(!1);s.useEffect(()=>{if(o==="ready"){w(!1);return}const t=setTimeout(()=>w(!0),1e3);return()=>clearTimeout(t)},[o]);const M=r(t=>t.view),V=r(t=>t.drafts),N=r(t=>t.setDraft),[_,q]=s.useState(m),l=s.useCallback(async()=>{try{const t=await Z();v(t),x(null)}catch(t){x(t instanceof Error?t.message:"协作组加载失败")}},[]);s.useEffect(()=>{let t=!1;F().then(c=>{t||D(c)}).catch(()=>{}),H().then(c=>{if(t)return;const Q=c.collaborationPanels?.[I()]?.drafts;for(const[k,U]of Object.entries(Q??{}))r.getState().drafts[k]||N(k,U)}).catch(()=>{});const K=J(c=>{t||(v(c),x(null))});l();const a=()=>{!document.hidden&&navigator.onLine!==!1&&l()},O=setInterval(a,1e4);return document.addEventListener("visibilitychange",a),window.addEventListener(C,a),window.addEventListener("pageshow",a),()=>{t=!0,K(),clearInterval(O),document.removeEventListener("visibilitychange",a),window.removeEventListener(C,a),window.removeEventListener("pageshow",a)}},[l]);const d=i?.groups.find(t=>t.id===m),f=i?.sessions.find(t=>t.sessionId===n),B=n?f?.name?`终端 · ${f.name}`:"继续终端会话":"选择终端",E=async t=>{await re(t),r.getState().terminal()};return e.jsxs("section",{"aria-label":"协作主工作区",className:"absolute inset-0 flex min-h-0 min-w-0 flex-col bg-[var(--chrome-bg)] text-foreground",children:[e.jsxs("header",{className:"flex min-h-14 shrink-0 items-center gap-1 border-b border-border/15 px-2 sm:min-h-16 sm:gap-3 sm:px-6",children:[!R&&e.jsx("button",{type:"button","aria-label":"打开会话侧栏",className:"inline-flex min-h-11 min-w-11 items-center justify-center rounded-lg text-muted-foreground hover:bg-surface-2",onClick:h,children:e.jsx(ee,{size:17})}),e.jsx(te,{size:18,className:"hidden shrink-0 text-primary sm:block"}),e.jsxs("div",{className:"min-w-0 flex-1",children:[e.jsx("h2",{ref:j,tabIndex:-1,className:"truncate text-base font-semibold outline-none",children:d?.name??"协作工作区"}),e.jsx("p",{className:"text-[11px] text-muted-foreground",children:d?`${d.sessionIds.length} 位成员`:"正在连接工作组"})]}),b&&e.jsx("button",{type:"button","aria-label":"文件侧栏",title:"文件侧栏","aria-pressed":g,className:`inline-flex min-h-11 min-w-11 items-center justify-center rounded-lg ${g?"bg-surface-2 text-primary":"text-muted-foreground hover:bg-surface-2"}`,onClick:b,children:e.jsx(se,{size:17})}),e.jsxs("button",{type:"button","aria-label":n?`打开终端:${f?.name??"当前会话"}`:"选择终端",title:n?`切换到${f?.name??"当前终端会话"},保留看板位置与消息草稿`:"从会话列表选择要打开的终端",className:"inline-flex min-h-11 min-w-11 max-w-[40%] items-center justify-center gap-2 rounded-lg px-2 text-xs text-muted-foreground hover:bg-surface-2",onClick:()=>{n?r.getState().terminal():h()},children:[e.jsx(X,{size:17,className:"shrink-0"}),e.jsx("span",{className:"hidden min-w-0 truncate sm:inline",children:B}),e.jsx("span",{className:"sm:hidden",children:n?"终端":"选择终端"})]})]}),e.jsxs("div",{className:"flex min-h-0 flex-1 flex-col px-4 py-2 sm:px-6",children:[(W||L(u))&&e.jsxs("div",{role:"status",className:"mb-2 flex shrink-0 items-center gap-2 text-xs text-muted-foreground",children:[e.jsx(S,{size:13,className:o==="offline"?"":"animate-spin"}),e.jsx("span",{children:o==="offline"?"网络已断开,联网后自动恢复":"正在恢复连接,当前结果和草稿已保留"})]}),(y||u&&o==="ready"&&!L(u))&&e.jsxs("div",{role:"alert",className:"mb-3 flex shrink-0 items-center gap-2 rounded-lg bg-destructive/10 p-3 text-xs text-destructive",children:[e.jsx("span",{className:"flex-1",children:y||u}),e.jsx("button",{type:"button","aria-label":"重新加载协作组",className:"min-h-11 px-3",onClick:()=>{l()},children:e.jsx(S,{size:14})})]}),p&&e.jsx("p",{role:"status",className:"mb-3 shrink-0 text-xs text-primary",children:p}),i?d?e.jsx(ne,{fullWorkspace:!0,initialView:M,active:!0,notice:p,groups:i.groups,sessions:i.sessions,agents:z,sessionsState:"loaded",selectedGroupId:_,setSelectedGroupId:q,initialGroupId:m,activeSessionId:n,initialDrafts:V,onDraftChange:N,docked:!1,inputKeySuffix:"main",floatingVisible:!0,floating:!1,onOpenSession:E,onOpenTaskSession:E,onDockMessages:n?async()=>{await ae(m,n)}:void 0,defaultSessionMode:T,busy:G,setBusy:A,setError:P,setNotice:$,refresh:l}):e.jsx("p",{className:"py-10 text-center text-sm text-muted-foreground",children:"协作组已移除或暂不可用。任务记录仍保留在原服务中。"}):e.jsx("p",{role:"status",className:"py-10 text-center text-sm text-muted-foreground",children:"正在加载协作工作区…"})]})]})}export{xe as default};
|
|
Binary file
|
|
Binary file
|