@zubriq/code 0.19.8-1 → 0.19.9-1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/bundled/qc-helper/docs/features/channels/_meta.ts +1 -0
- package/dist/bundled/qc-helper/docs/features/channels/overview.md +23 -12
- package/dist/bundled/qc-helper/docs/features/channels/plugins.md +1 -0
- package/dist/bundled/qc-helper/docs/features/channels/wecom.md +111 -0
- package/dist/bundled/qc-helper/docs/features/hooks.md +36 -34
- package/dist/bundled/qc-helper/docs/features/memory.md +1 -1
- package/dist/bundled/qc-helper/docs/qwen-serve.md +17 -10
- package/dist/bundled/review/SKILL.md +6 -2
- package/dist/chunks/{MaxSizedBox-OWTCJQNO.js → MaxSizedBox-W6SAJMJC.js} +13 -11
- package/dist/chunks/{StandaloneSessionPicker-6NGEQFBH.js → StandaloneSessionPicker-YBKZZKIA.js} +28 -23
- package/dist/chunks/{acpAgent-XPRWSNOW.js → acpAgent-SQJQBOTS.js} +110 -80
- package/dist/chunks/{agent-TB6S4VXU.js → agent-QU7Q2RZN.js} +8 -8
- package/dist/chunks/{agent-headless-R3XYK5TT.js → agent-headless-PBHLWHND.js} +8 -8
- package/dist/chunks/{anthropicContentGenerator-FZQAEMYK.js → anthropicContentGenerator-52G6ZA3D.js} +31 -4
- package/dist/chunks/{artifact-tool-H2TNPNP5.js → artifact-tool-D233YJFH.js} +25 -6
- package/dist/chunks/{bridge-HVRG6SMU.js → bridge-LJLLDUMW.js} +17 -14
- package/dist/chunks/{ca-HCMB2I54.js → ca-MKD32FQL.js} +26 -1
- package/dist/chunks/{channel-worker-supervisor-B7MSMB5K.js → channel-worker-supervisor-NZQUOEFJ.js} +3 -3
- package/dist/chunks/{chunk-YRM6BC6H.js → chunk-27AYMAL6.js} +506 -63
- package/dist/chunks/{chunk-536GZ6UF.js → chunk-2MDC5WDB.js} +17 -111
- package/dist/chunks/{chunk-H3D6XAOL.js → chunk-2PRSBVPI.js} +3 -3
- package/dist/chunks/chunk-332PWN27.js +19 -0
- package/dist/chunks/{chunk-FVMWEHWU.js → chunk-3B26UVCX.js} +114 -12
- package/dist/chunks/{chunk-ZM5BPDXV.js → chunk-3F22JT4E.js} +1 -1
- package/dist/chunks/{chunk-W6RH6KHR.js → chunk-3GPVYALM.js} +4 -2
- package/dist/chunks/{chunk-G7ZG7CA6.js → chunk-3UP777ZS.js} +8 -7
- package/dist/chunks/{chunk-PA7QS4X5.js → chunk-43W4YSO6.js} +1 -12
- package/dist/chunks/{chunk-5EB2HK3X.js → chunk-4IK56VLC.js} +1 -1
- package/dist/chunks/{chunk-UE5TCZE6.js → chunk-5FAUIGXH.js} +5 -13
- package/dist/chunks/{chunk-VEB3NYSO.js → chunk-5MBO76SL.js} +5 -0
- package/dist/chunks/{chunk-PDITONOB.js → chunk-5MRUKUOG.js} +5347 -4132
- package/dist/chunks/{chunk-4UC3U66K.js → chunk-6EUMFVPJ.js} +5 -5
- package/dist/chunks/{chunk-YOGGIAGF.js → chunk-6JL5OVLX.js} +1 -1
- package/dist/chunks/{chunk-QG4ZO2EB.js → chunk-74E6VVF6.js} +11 -11
- package/dist/chunks/chunk-A2X3KLC3.js +3807 -0
- package/dist/chunks/{chunk-BA4HLTG2.js → chunk-B6B2MUUF.js} +5 -5
- package/dist/chunks/{chunk-XKYOIERV.js → chunk-BN5VYAOZ.js} +681 -1239
- package/dist/chunks/{chunk-IO76BGJ3.js → chunk-BYUA6YYS.js} +15 -9
- package/dist/chunks/{chunk-NCFY7PWS.js → chunk-CCGOFQV3.js} +51 -2
- package/dist/chunks/{chunk-66KNL43D.js → chunk-CD6USWHZ.js} +1 -1
- package/dist/chunks/{chunk-ZWSTIPSW.js → chunk-CEITMQ62.js} +2 -2
- package/dist/chunks/{chunk-7AQTBTVY.js → chunk-EJP6Z7NU.js} +4 -3
- package/dist/chunks/{chunk-RTW5ZXHO.js → chunk-EZTNYRHH.js} +6 -5
- package/dist/chunks/{chunk-MJQFA66Z.js → chunk-FAATDXYS.js} +308 -81
- package/dist/chunks/{chunk-DNV4FSN5.js → chunk-FBET5XZ2.js} +6 -4
- package/dist/chunks/{chunk-HTC4R67V.js → chunk-FES4YXJ3.js} +9 -9
- package/dist/chunks/{chunk-NBKE6QRZ.js → chunk-FHTUTVIQ.js} +10 -5
- package/dist/chunks/chunk-FII3C4E7.js +168 -0
- package/dist/chunks/{chunk-2NL7ED5Q.js → chunk-FV7425LN.js} +22 -1
- package/dist/chunks/{chunk-J6OET6C3.js → chunk-GAI76CFX.js} +4 -4
- package/dist/chunks/{chunk-B34OV7K2.js → chunk-GGQQA4JW.js} +13 -0
- package/dist/chunks/chunk-GLE2YUPU.js +34 -0
- package/dist/chunks/{chunk-X265R5C6.js → chunk-GN3F6PIU.js} +1 -1
- package/dist/chunks/{chunk-SM624MOZ.js → chunk-GWUN54UD.js} +1 -1
- package/dist/chunks/chunk-H3TELH3H.js +942 -0
- package/dist/chunks/{chunk-XZULYFIX.js → chunk-HD4DZI2L.js} +2 -2
- package/dist/chunks/{chunk-KLLLWQM2.js → chunk-HPQIVXSP.js} +1 -1
- package/dist/chunks/{chunk-WSVZFWN4.js → chunk-IBY3Q3HG.js} +693 -104
- package/dist/chunks/{chunk-JSEOX4CM.js → chunk-JGR6W4IX.js} +14 -8
- package/dist/chunks/chunk-K652V4NH.js +283 -0
- package/dist/chunks/{chunk-OCBJKHF2.js → chunk-KH2CZZDD.js} +2 -2
- package/dist/chunks/chunk-LGFAYIKX.js +115 -0
- package/dist/chunks/{chunk-QG5KDB6X.js → chunk-LZDW5TDV.js} +5 -5
- package/dist/chunks/{chunk-ENKWIF75.js → chunk-MA4AZNP7.js} +10 -10
- package/dist/chunks/{chunk-4RQIB5UZ.js → chunk-O2YT7VB4.js} +0 -34
- package/dist/chunks/{chunk-4KJ2BPIT.js → chunk-OACJLMLD.js} +2 -38
- package/dist/chunks/{chunk-ML2ZWH2K.js → chunk-PCWYMX57.js} +14 -153
- package/dist/chunks/{chunk-NHFBLJOI.js → chunk-Q3PQ5VGJ.js} +1 -1
- package/dist/chunks/{chunk-LGXBB2R2.js → chunk-QK3I36QG.js} +1 -1
- package/dist/chunks/chunk-RA7TR75G.js +8223 -0
- package/dist/chunks/{chunk-KSPVDFE4.js → chunk-SAIILPQ3.js} +0 -3
- package/dist/chunks/{chunk-DHKDK57Q.js → chunk-SNZPA74J.js} +146 -54
- package/dist/chunks/{chunk-PWR5MVM3.js → chunk-SSP3UT5C.js} +4 -4
- package/dist/chunks/{chunk-4LETJLG2.js → chunk-SUCRVT5L.js} +1 -1
- package/dist/chunks/{chunk-5YLZHETW.js → chunk-TRR5KGDN.js} +1 -1
- package/dist/chunks/chunk-UIDXQNMV.js +13 -0
- package/dist/chunks/{chunk-PIORL4OD.js → chunk-UKV3D7WB.js} +0 -44
- package/dist/chunks/chunk-UYNUIGUR.js +167 -0
- package/dist/chunks/chunk-V2TYBEWU.js +28 -0
- package/dist/chunks/chunk-V35MD7KN.js +13 -0
- package/dist/chunks/{chunk-N4HTVZDZ.js → chunk-VR3KCBHH.js} +1 -1
- package/dist/chunks/{chunk-APYUOROB.js → chunk-W4CTWW7M.js} +423 -61
- package/dist/chunks/{chunk-ABANKQYY.js → chunk-WJAW2O5H.js} +92 -465
- package/dist/chunks/{chunk-6RSBRKF5.js → chunk-WN4YJJGH.js} +2 -2
- package/dist/chunks/chunk-XNXVCNAT.js +88 -0
- package/dist/chunks/{chunk-TDGF35EN.js → chunk-XOHNA2S6.js} +1 -1
- package/dist/chunks/chunk-XQPMKWSV.js +487 -0
- package/dist/chunks/{chunk-4FQL7KUS.js → chunk-XWDHZP7P.js} +8 -8
- package/dist/chunks/{chunk-REPRY4F7.js → chunk-YCKKP4QA.js} +10 -10
- package/dist/chunks/{chunk-YNWQ3PUQ.js → chunk-YJWMOGGZ.js} +3 -3
- package/dist/chunks/{chunk-RFIL6REB.js → chunk-YKZIAK7C.js} +119 -29
- package/dist/chunks/{chunk-45YCXM2H.js → chunk-YZDBUH6S.js} +45 -9
- package/dist/chunks/chunk-Z3I3QJK3.js +47 -0
- package/dist/chunks/{chunk-G23FFNLT.js → chunk-ZDGPPCTW.js} +20 -8
- package/dist/chunks/chunk-ZL5HN75Q.js +61 -0
- package/dist/chunks/{chunk-IQX5S2RS.js → chunk-ZL7JCYWM.js} +66 -7
- package/dist/chunks/{computer-use-A72BECH4.js → computer-use-4B45EG2F.js} +8 -8
- package/dist/chunks/{contextCommand-RREXA4B7.js → contextCommand-GIVRWNTS.js} +12 -11
- package/dist/chunks/{cron-create-DDYU4DIR.js → cron-create-JSXEIPVS.js} +1 -1
- package/dist/chunks/{cron-delete-DFKOUZWN.js → cron-delete-OIFVEPGU.js} +1 -1
- package/dist/chunks/{cron-list-ME5QGAR5.js → cron-list-D4ZX4IOE.js} +1 -1
- package/dist/chunks/{daemon-XWG2EGFX.js → daemon-WPAENEBW.js} +71 -3
- package/dist/chunks/{daemon-status-provider-Y6AFXTET.js → daemon-status-provider-WBOAMCHE.js} +20 -17
- package/dist/chunks/{de-PLLFDERI.js → de-ZFPPQVSF.js} +26 -1
- package/dist/chunks/{dist-LPVU3L2M.js → dist-BEXOZXLQ.js} +6 -3792
- package/dist/chunks/{dist-7GU63KI5.js → dist-E6UANPIM.js} +1 -1
- package/dist/chunks/{dist-VHBP2PIG.js → dist-H2AEJCZ5.js} +2 -2
- package/dist/chunks/{dist-3UDX5T4T.js → dist-O2IRTRPP.js} +1 -1
- package/dist/chunks/dist-SCFLLYMK.js +3217 -0
- package/dist/chunks/{dist-H4HHZYCI.js → dist-Z34QPAQW.js} +2 -2
- package/dist/chunks/{earlyInputCapture-OAHBOGOO.js → earlyInputCapture-JWMCAJZR.js} +8 -8
- package/dist/chunks/{edit-SFYW3FOV.js → edit-O5FUVHBE.js} +9 -9
- package/dist/chunks/{en-AXARKOWO.js → en-N4EPZAQI.js} +31 -2
- package/dist/chunks/{enter-worktree-LUPPQ2NH.js → enter-worktree-LOJFRC3D.js} +8 -8
- package/dist/chunks/{enterPlanMode-44GEN5U6.js → enterPlanMode-VS3FAUPX.js} +8 -8
- package/dist/chunks/environment-WKW5TLSH.js +90 -0
- package/dist/chunks/{errors-H3Q3W3DL.js → errors-LEZXHJMR.js} +10 -10
- package/dist/chunks/{exit-worktree-34CVVWT4.js → exit-worktree-RN2NXRMP.js} +8 -8
- package/dist/chunks/{exitPlanMode-5G5BHNUP.js → exitPlanMode-EPC424I4.js} +8 -8
- package/dist/chunks/{fast-path-7PKGFBRM.js → fast-path-UUPAFOSQ.js} +12 -3
- package/dist/chunks/{fast-path-settings-RCRXH2JG.js → fast-path-settings-7RIFI3PK.js} +3 -2
- package/dist/chunks/{fr-MBMNQSQ6.js → fr-5WWMY53B.js} +30 -1
- package/dist/chunks/{gemini-2II6JH4H.js → gemini-QCKK4XNU.js} +438 -265
- package/dist/chunks/{geminiContentGenerator-SWEJVOC4.js → geminiContentGenerator-DX4SRXJA.js} +1 -1
- package/dist/chunks/{glob-5DFC7DXW.js → glob-4URMJWRX.js} +8 -8
- package/dist/chunks/{grep-QYVXGRRJ.js → grep-AEQB5KED.js} +8 -8
- package/dist/chunks/handleAutoUpdate-Y4YNG34Y.js +65 -0
- package/dist/chunks/{initializer-XX3UGUHE.js → initializer-NDEBMSOG.js} +17 -13
- package/dist/chunks/{ja-HFV5QCHR.js → ja-CUHZOLEJ.js} +30 -1
- package/dist/chunks/{list-AX5FWBVC.js → list-VSCBNOWT.js} +17 -15
- package/dist/chunks/{loadedSettingsAdapter-ISOM6GJ7.js → loadedSettingsAdapter-FDO752BA.js} +15 -13
- package/dist/chunks/{loop-wakeup-ZW5P6VPY.js → loop-wakeup-OHWEMFP5.js} +2 -2
- package/dist/chunks/{ls-L654WOAT.js → ls-7MFU2QYW.js} +1 -1
- package/dist/chunks/{lsp-M35KE54Y.js → lsp-XHDTPTGV.js} +2 -4
- package/dist/chunks/{mcp-74F6725E.js → mcp-MLPWTHUV.js} +15 -13
- package/dist/chunks/{monitor-W4WRSC2C.js → monitor-WCVHIJUJ.js} +16 -11
- package/dist/chunks/{nonInteractiveCli-4QMV6C4J.js → nonInteractiveCli-32HZK274.js} +52 -44
- package/dist/chunks/{notebook-edit-XBZEIP42.js → notebook-edit-NPOMPKS4.js} +9 -9
- package/dist/chunks/{openaiContentGenerator-RTUJDESE.js → openaiContentGenerator-6AIBSRQK.js} +6 -6
- package/dist/chunks/{pidfile-YWSGNTPK.js → pidfile-7Y3QEDSZ.js} +8 -8
- package/dist/chunks/{pt-2THT3YHA.js → pt-OLYN42DS.js} +26 -1
- package/dist/chunks/{qwenContentGenerator-4ZFYAZLY.js → qwenContentGenerator-OUYOAYT4.js} +10 -10
- package/dist/chunks/{read-file-D7DKDIAC.js → read-file-EESFA24L.js} +3 -3
- package/dist/chunks/{record-artifact-PP3LKHTS.js → record-artifact-SQ2OKRJW.js} +3 -3
- package/dist/chunks/{ripGrep-KG7JYNER.js → ripGrep-DLYV7ZZG.js} +8 -8
- package/dist/chunks/{ru-PER5I4OI.js → ru-MKM2HFDS.js} +26 -1
- package/dist/chunks/{run-qwen-serve-XGJSNF6S.js → run-qwen-serve-WUEHQROF.js} +602 -143
- package/dist/chunks/{scheduler-MOLWOE4G.js → scheduler-SK4Y66V4.js} +8 -8
- package/dist/chunks/{send-message-OA6MV4EU.js → send-message-76GT3JMC.js} +1 -1
- package/dist/chunks/{serve-4ZNVPYND.js → serve-UCDGVZFI.js} +17 -14
- package/dist/chunks/{server-ACWDFHIF.js → server-FVGFFVZ4.js} +1394 -328
- package/dist/chunks/{session-VYO2GRO2.js → session-RIGKDMGR.js} +53 -45
- package/dist/chunks/{settings-4J2O3K22.js → settings-LVFFGXGE.js} +24 -20
- package/dist/chunks/{shell-RKERJYXR.js → shell-PAWNAFYN.js} +8 -8
- package/dist/chunks/{skill-JYACZJ5V.js → skill-5YIN3Z6Y.js} +15 -5
- package/dist/chunks/{spawnChannel-BA3U3RGX.js → spawnChannel-KIMZHWNR.js} +10 -10
- package/dist/chunks/{src-3P337V4P.js → src-BIWCD3VX.js} +21 -9
- package/dist/chunks/{startInteractiveUI-SUSZ6FWB.js → startInteractiveUI-AFXLGUFI.js} +33759 -41620
- package/dist/chunks/{task-create-RPFZNB4B.js → task-create-WCHTB435.js} +2 -2
- package/dist/chunks/{task-update-5WUG5MVQ.js → task-update-XYWMHJGJ.js} +2 -2
- package/dist/chunks/{team-create-YVWGRZEA.js → team-create-26WOMISV.js} +8 -8
- package/dist/chunks/{team-plan-approval-VRF54TTI.js → team-plan-approval-B5XB6UQC.js} +8 -8
- package/dist/chunks/{theme-manager-JW2KOACL.js → theme-manager-4TJ5TEFD.js} +8 -8
- package/dist/chunks/{tool-search-KUSMAZBN.js → tool-search-FFU63E6M.js} +6 -23
- package/dist/chunks/total-session-admission-JOD7SMPJ.js +72 -0
- package/dist/chunks/{trustedFolders-ERGSUCDK.js → trustedFolders-IJ2QHXSC.js} +9 -9
- package/dist/chunks/updateCheck-5Z25DCBP.js +65 -0
- package/dist/chunks/{validateNonInterActiveAuth-DDI62H5X.js → validateNonInterActiveAuth-G5EY47DE.js} +49 -41
- package/dist/chunks/{version-VB3AHVUF.js → version-LGO3GOKQ.js} +2 -1
- package/dist/chunks/{workflow-WINKRCI4.js → workflow-ZTK3WT3D.js} +9 -9
- package/dist/chunks/{workspace-providers-status-ZVZPXKSO.js → workspace-providers-status-YMPTRKW2.js} +18 -15
- package/dist/chunks/workspace-registry-NBUL6LBH.js +74 -0
- package/dist/chunks/{workspace-service-GAS2LV2P.js → workspace-service-V6G2RCD4.js} +21 -19
- package/dist/chunks/{workspace-skills-status-4WGKYJVA.js → workspace-skills-status-ZCW44BCH.js} +16 -14
- package/dist/chunks/{write-file-UTLKVZNN.js → write-file-4FUTAEW6.js} +9 -9
- package/dist/chunks/{zh-RS3HZHFH.js → zh-J4F6QWQV.js} +31 -2
- package/dist/chunks/{zh-TW-L5GRQ4S4.js → zh-TW-XVDWOLSW.js} +31 -2
- package/dist/cli.js +11 -11
- package/dist/locales/ca.js +30 -0
- package/dist/locales/de.js +30 -0
- package/dist/locales/en.js +38 -2
- package/dist/locales/fr.js +36 -0
- package/dist/locales/ja.js +36 -0
- package/dist/locales/pt.js +30 -0
- package/dist/locales/ru.js +30 -0
- package/dist/locales/zh-TW.js +38 -2
- package/dist/locales/zh.js +38 -2
- package/dist/package.json +3 -3
- package/dist/web-shell/assets/{arc-C6tzvtOa.js → arc-BWyoJpY2.js} +1 -1
- package/dist/web-shell/assets/{architectureDiagram-3BPJPVTR-DSYQFGn9.js → architectureDiagram-3BPJPVTR-BT0mGrz2.js} +1 -1
- package/dist/web-shell/assets/{blockDiagram-GPEHLZMM-CHjBdXAD.js → blockDiagram-GPEHLZMM-BLgUWvyf.js} +1 -1
- package/dist/web-shell/assets/{c4Diagram-AAUBKEIU-BQzK6Yyb.js → c4Diagram-AAUBKEIU-DYx9M7oU.js} +1 -1
- package/dist/web-shell/assets/channel-wmPUGHtg.js +1 -0
- package/dist/web-shell/assets/{chunk-2J33WTMH-hpP2p3Ij.js → chunk-2J33WTMH-CfMHWbuZ.js} +1 -1
- package/dist/web-shell/assets/{chunk-4BX2VUAB-B5KtK1JJ.js → chunk-4BX2VUAB-B1URoqEV.js} +1 -1
- package/dist/web-shell/assets/{chunk-55IACEB6-BDv6Mfr2.js → chunk-55IACEB6-DAIaM4QF.js} +1 -1
- package/dist/web-shell/assets/{chunk-727SXJPM-BevPWfrX.js → chunk-727SXJPM-B2X34knw.js} +1 -1
- package/dist/web-shell/assets/{chunk-AQP2D5EJ-ChDrz2ad.js → chunk-AQP2D5EJ-Cif-zLTQ.js} +1 -1
- package/dist/web-shell/assets/{chunk-FMBD7UC4-ClMdVSDs.js → chunk-FMBD7UC4-H18WCXdY.js} +1 -1
- package/dist/web-shell/assets/{chunk-ND2GUHAM-BceV8kZS.js → chunk-ND2GUHAM-YFtetHi0.js} +1 -1
- package/dist/web-shell/assets/{chunk-QZHKN3VN-DtyK2wwc.js → chunk-QZHKN3VN-By2hiH3r.js} +1 -1
- package/dist/web-shell/assets/classDiagram-4FO5ZUOK-BA2ljEjW.js +1 -0
- package/dist/web-shell/assets/classDiagram-v2-Q7XG4LA2-BA2ljEjW.js +1 -0
- package/dist/web-shell/assets/{cose-bilkent-S5V4N54A-BGMsqwmE.js → cose-bilkent-S5V4N54A-VrcnnLZu.js} +1 -1
- package/dist/web-shell/assets/{dagre-BM42HDAG-C-71clpF.js → dagre-BM42HDAG-CGo-IaVV.js} +1 -1
- package/dist/web-shell/assets/{diagram-2AECGRRQ-WIzzlkec.js → diagram-2AECGRRQ-Dl4QjzIB.js} +1 -1
- package/dist/web-shell/assets/{diagram-5GNKFQAL-CtnhZUP1.js → diagram-5GNKFQAL-qMLmsO0u.js} +1 -1
- package/dist/web-shell/assets/{diagram-KO2AKTUF-CS_IUezp.js → diagram-KO2AKTUF-CHlmuxPI.js} +1 -1
- package/dist/web-shell/assets/{diagram-LMA3HP47-BQnGRwN9.js → diagram-LMA3HP47-BUwU3GwT.js} +1 -1
- package/dist/web-shell/assets/{diagram-OG6HWLK6-By2VIocq.js → diagram-OG6HWLK6-HEhwPDUM.js} +1 -1
- package/dist/web-shell/assets/{erDiagram-TEJ5UH35-Dy8WeNkr.js → erDiagram-TEJ5UH35-1n0llBmM.js} +1 -1
- package/dist/web-shell/assets/{flowDiagram-I6XJVG4X-Diu_4y0w.js → flowDiagram-I6XJVG4X-BN74uMnt.js} +1 -1
- package/dist/web-shell/assets/{ganttDiagram-6RSMTGT7-CH8euujP.js → ganttDiagram-6RSMTGT7-BoOq78i3.js} +1 -1
- package/dist/web-shell/assets/{gitGraphDiagram-PVQCEYII-DHiObZq1.js → gitGraphDiagram-PVQCEYII-CN8b00c8.js} +1 -1
- package/dist/web-shell/assets/index-CNwoO1Cn.js +783 -0
- package/dist/web-shell/assets/index-CWQ0z6kZ.css +5 -0
- package/dist/web-shell/assets/{infoDiagram-5YYISTIA-CvC9A6fh.js → infoDiagram-5YYISTIA-CCurnIna.js} +1 -1
- package/dist/web-shell/assets/{ishikawaDiagram-YF4QCWOH-BK46kC4E.js → ishikawaDiagram-YF4QCWOH-AwuRqdUP.js} +1 -1
- package/dist/web-shell/assets/{journeyDiagram-JHISSGLW-B2TIiKq4.js → journeyDiagram-JHISSGLW-B7IICk-E.js} +1 -1
- package/dist/web-shell/assets/{kanban-definition-UN3LZRKU-Bh0WAulO.js → kanban-definition-UN3LZRKU-BYF0OKhx.js} +1 -1
- package/dist/web-shell/assets/{linear-Bxe9SHMk.js → linear-GWWguGfD.js} +1 -1
- package/dist/web-shell/assets/{mermaid.core-B1Pv6D5B.js → mermaid.core-JqtkxvCl.js} +5 -5
- package/dist/web-shell/assets/{mindmap-definition-RKZ34NQL-Bz0joLH8.js → mindmap-definition-RKZ34NQL-B0MmHsZ6.js} +1 -1
- package/dist/web-shell/assets/{pieDiagram-4H26LBE5-CnN4x-VS.js → pieDiagram-4H26LBE5-DhImUZLQ.js} +1 -1
- package/dist/web-shell/assets/{quadrantDiagram-W4KKPZXB-BYWD4xO4.js → quadrantDiagram-W4KKPZXB-DGeSC3DT.js} +1 -1
- package/dist/web-shell/assets/{requirementDiagram-4Y6WPE33-B4MEhI9h.js → requirementDiagram-4Y6WPE33-DkspY6Re.js} +1 -1
- package/dist/web-shell/assets/{sankeyDiagram-5OEKKPKP-Dk_FgKLp.js → sankeyDiagram-5OEKKPKP-CaOofS2x.js} +1 -1
- package/dist/web-shell/assets/{sequenceDiagram-3UESZ5HK-B4ksiBZQ.js → sequenceDiagram-3UESZ5HK-DFQ_kFnN.js} +1 -1
- package/dist/web-shell/assets/{stateDiagram-AJRCARHV-CYf0xSPl.js → stateDiagram-AJRCARHV-D3snw0Tz.js} +1 -1
- package/dist/web-shell/assets/stateDiagram-v2-BHNVJYJU-BbSm_9d0.js +1 -0
- package/dist/web-shell/assets/{timeline-definition-PNZ67QCA-0CXeWHNY.js → timeline-definition-PNZ67QCA-l4zH8nLM.js} +1 -1
- package/dist/web-shell/assets/{vennDiagram-CIIHVFJN-DHoYY9v2.js → vennDiagram-CIIHVFJN-BnRlA98M.js} +1 -1
- package/dist/web-shell/assets/{wardley-L42UT6IY-D_65qshr.js → wardley-L42UT6IY-BS0xUdmd.js} +1 -1
- package/dist/web-shell/assets/{wardleyDiagram-YWT4CUSO-Cv90x1sd.js → wardleyDiagram-YWT4CUSO-DKGBUWyQ.js} +1 -1
- package/dist/web-shell/assets/{xychartDiagram-2RQKCTM6-5FQCYJyh.js → xychartDiagram-2RQKCTM6-DVb2HuOB.js} +1 -1
- package/dist/web-shell/index.html +2 -2
- package/package.json +3 -2
- package/dist/web-shell/assets/channel-V-ZaJrA6.js +0 -1
- package/dist/web-shell/assets/classDiagram-4FO5ZUOK-s-H0snGT.js +0 -1
- package/dist/web-shell/assets/classDiagram-v2-Q7XG4LA2-s-H0snGT.js +0 -1
- package/dist/web-shell/assets/index-DW75jq0K.css +0 -5
- package/dist/web-shell/assets/index-tiCo0xbZ.js +0 -779
- package/dist/web-shell/assets/stateDiagram-v2-BHNVJYJU-CMtrFRUb.js +0 -1
|
@@ -7,9 +7,6 @@ import {
|
|
|
7
7
|
import {
|
|
8
8
|
findCliEntryPath
|
|
9
9
|
} from "./chunk-AHNXYU4O.js";
|
|
10
|
-
import {
|
|
11
|
-
RUNTIME_STARTUP_CANCELLED_MESSAGE
|
|
12
|
-
} from "./chunk-GHOTR7HL.js";
|
|
13
10
|
import {
|
|
14
11
|
CAPABILITIES_SCHEMA_VERSION,
|
|
15
12
|
ClientMcpSenderRegistry,
|
|
@@ -31,16 +28,29 @@ import {
|
|
|
31
28
|
positiveFiniteOrNull,
|
|
32
29
|
require_express,
|
|
33
30
|
resolveWebShellDir
|
|
34
|
-
} from "./chunk-
|
|
31
|
+
} from "./chunk-YKZIAK7C.js";
|
|
35
32
|
import {
|
|
36
33
|
isLoopbackBind
|
|
37
34
|
} from "./chunk-RNBYOUGV.js";
|
|
38
35
|
import "./chunk-3HX5LZ6R.js";
|
|
39
36
|
import "./chunk-7RYW5LQV.js";
|
|
37
|
+
import {
|
|
38
|
+
RUNTIME_STARTUP_CANCELLED_MESSAGE
|
|
39
|
+
} from "./chunk-GHOTR7HL.js";
|
|
40
|
+
import {
|
|
41
|
+
LOAD_REPLAY_META_KEY
|
|
42
|
+
} from "./chunk-AGHU5VRK.js";
|
|
43
|
+
import {
|
|
44
|
+
DEFAULT_COMPACTED_REPLAY_MAX_BYTES,
|
|
45
|
+
normalizeCompactedReplayMaxBytes
|
|
46
|
+
} from "./chunk-GLE2YUPU.js";
|
|
47
|
+
import {
|
|
48
|
+
canonicalizeWorkspace
|
|
49
|
+
} from "./chunk-ER3BKOLB.js";
|
|
40
50
|
import {
|
|
41
51
|
loadServeFastPathSettings,
|
|
42
52
|
preResolveServeFastPathHomeEnvOverrides
|
|
43
|
-
} from "./chunk-
|
|
53
|
+
} from "./chunk-FBET5XZ2.js";
|
|
44
54
|
import {
|
|
45
55
|
QWEN_SERVER_TOKEN_ENV
|
|
46
56
|
} from "./chunk-S6RLAIUR.js";
|
|
@@ -50,16 +60,12 @@ import {
|
|
|
50
60
|
import {
|
|
51
61
|
getGlobalQwenDirLite,
|
|
52
62
|
resolveConfigPathLite
|
|
53
|
-
} from "./chunk-
|
|
54
|
-
import
|
|
55
|
-
LOAD_REPLAY_META_KEY
|
|
56
|
-
} from "./chunk-AGHU5VRK.js";
|
|
57
|
-
import {
|
|
58
|
-
canonicalizeWorkspace
|
|
59
|
-
} from "./chunk-ER3BKOLB.js";
|
|
63
|
+
} from "./chunk-O2YT7VB4.js";
|
|
64
|
+
import "./chunk-Z3I3QJK3.js";
|
|
60
65
|
import {
|
|
61
66
|
getCliVersion
|
|
62
|
-
} from "./chunk-
|
|
67
|
+
} from "./chunk-V2TYBEWU.js";
|
|
68
|
+
import "./chunk-43W4YSO6.js";
|
|
63
69
|
import {
|
|
64
70
|
writeStderrLine,
|
|
65
71
|
writeStdoutLine
|
|
@@ -104,7 +110,7 @@ var DuplicateWorkspaceInputError = class extends Error {
|
|
|
104
110
|
}
|
|
105
111
|
constructor(workspace) {
|
|
106
112
|
super(
|
|
107
|
-
`Duplicate --workspace value resolves to ${JSON.stringify(workspace)}.
|
|
113
|
+
`Duplicate --workspace value resolves to ${JSON.stringify(workspace)}. Pass distinct --workspace values.`
|
|
108
114
|
);
|
|
109
115
|
this.name = "DuplicateWorkspaceInputError";
|
|
110
116
|
}
|
|
@@ -115,22 +121,11 @@ var NestedWorkspaceInputError = class extends Error {
|
|
|
115
121
|
}
|
|
116
122
|
constructor(parent, child) {
|
|
117
123
|
super(
|
|
118
|
-
`Nested --workspace values are not supported yet: ${JSON.stringify(child)} is inside ${JSON.stringify(parent)}.
|
|
124
|
+
`Nested --workspace values are not supported yet: ${JSON.stringify(child)} is inside ${JSON.stringify(parent)}. Pass non-nested --workspace values.`
|
|
119
125
|
);
|
|
120
126
|
this.name = "NestedWorkspaceInputError";
|
|
121
127
|
}
|
|
122
128
|
};
|
|
123
|
-
var MultipleWorkspaceInputError = class extends Error {
|
|
124
|
-
static {
|
|
125
|
-
__name(this, "MultipleWorkspaceInputError");
|
|
126
|
-
}
|
|
127
|
-
constructor() {
|
|
128
|
-
super(
|
|
129
|
-
"Multiple --workspace values are not supported yet. Multi-workspace serve is not enabled; pass one --workspace."
|
|
130
|
-
);
|
|
131
|
-
this.name = "MultipleWorkspaceInputError";
|
|
132
|
-
}
|
|
133
|
-
};
|
|
134
129
|
var MissingWorkspaceInputError = class extends Error {
|
|
135
130
|
static {
|
|
136
131
|
__name(this, "MissingWorkspaceInputError");
|
|
@@ -155,7 +150,7 @@ function isNestedWorkspace(parent, child) {
|
|
|
155
150
|
return parent !== child && isWithinRoot(child, parent);
|
|
156
151
|
}
|
|
157
152
|
__name(isNestedWorkspace, "isNestedWorkspace");
|
|
158
|
-
function
|
|
153
|
+
function rejectDuplicateOrNestedWorkspaceInputs(workspaces) {
|
|
159
154
|
if (workspaces.length <= 1) return;
|
|
160
155
|
let canonicalWorkspaces;
|
|
161
156
|
try {
|
|
@@ -163,7 +158,7 @@ function rejectUnsupportedMultiWorkspaceInputs(workspaces) {
|
|
|
163
158
|
(workspace) => canonicalizeWorkspace(workspace)
|
|
164
159
|
);
|
|
165
160
|
} catch {
|
|
166
|
-
|
|
161
|
+
return;
|
|
167
162
|
}
|
|
168
163
|
const seen = /* @__PURE__ */ new Set();
|
|
169
164
|
for (const workspace of canonicalWorkspaces) {
|
|
@@ -184,15 +179,14 @@ function rejectUnsupportedMultiWorkspaceInputs(workspaces) {
|
|
|
184
179
|
}
|
|
185
180
|
}
|
|
186
181
|
}
|
|
187
|
-
throw new MultipleWorkspaceInputError();
|
|
188
182
|
}
|
|
189
|
-
__name(
|
|
190
|
-
function
|
|
183
|
+
__name(rejectDuplicateOrNestedWorkspaceInputs, "rejectDuplicateOrNestedWorkspaceInputs");
|
|
184
|
+
function resolveWorkspaceInputs(workspace) {
|
|
191
185
|
const workspaces = normalizeWorkspaceInputs(workspace);
|
|
192
|
-
|
|
193
|
-
return workspaces
|
|
186
|
+
rejectDuplicateOrNestedWorkspaceInputs(workspaces);
|
|
187
|
+
return workspaces;
|
|
194
188
|
}
|
|
195
|
-
__name(
|
|
189
|
+
__name(resolveWorkspaceInputs, "resolveWorkspaceInputs");
|
|
196
190
|
|
|
197
191
|
// packages/cli/src/serve/permission-audit.ts
|
|
198
192
|
init_esbuild_shims();
|
|
@@ -938,11 +932,21 @@ function isNonNegativeIntegerOrInfinity(value) {
|
|
|
938
932
|
return value === Number.POSITIVE_INFINITY || Number.isFinite(value) && Number.isInteger(value) && value >= 0;
|
|
939
933
|
}
|
|
940
934
|
__name(isNonNegativeIntegerOrInfinity, "isNonNegativeIntegerOrInfinity");
|
|
935
|
+
function deriveDefaultMaxTotalSessions(maxSessionsPerWorkspace, workspaceCount) {
|
|
936
|
+
if (workspaceCount <= 1) return void 0;
|
|
937
|
+
const perWorkspace = maxSessionsPerWorkspace ?? DEFAULT_MAX_SESSIONS;
|
|
938
|
+
if (perWorkspace === 0 || perWorkspace === Number.POSITIVE_INFINITY) {
|
|
939
|
+
return void 0;
|
|
940
|
+
}
|
|
941
|
+
return perWorkspace * workspaceCount;
|
|
942
|
+
}
|
|
943
|
+
__name(deriveDefaultMaxTotalSessions, "deriveDefaultMaxTotalSessions");
|
|
941
944
|
function isNonNegativeIntegerMs(value) {
|
|
942
945
|
return Number.isFinite(value) && Number.isInteger(value) && value >= 0;
|
|
943
946
|
}
|
|
944
947
|
__name(isNonNegativeIntegerMs, "isNonNegativeIntegerMs");
|
|
945
948
|
var MAX_TIMEOUT_MS = 2147483647;
|
|
949
|
+
var MAX_PORT_ATTEMPTS = 10;
|
|
946
950
|
function assertTimerDelayInRange(name, value) {
|
|
947
951
|
if (value > MAX_TIMEOUT_MS) {
|
|
948
952
|
throw new TypeError(
|
|
@@ -1081,8 +1085,8 @@ __name(withSettingsLock, "withSettingsLock");
|
|
|
1081
1085
|
var channelWorkerRuntimePromise;
|
|
1082
1086
|
async function loadChannelWorkerRuntime() {
|
|
1083
1087
|
channelWorkerRuntimePromise ??= Promise.all([
|
|
1084
|
-
import("./channel-worker-supervisor-
|
|
1085
|
-
import("./pidfile-
|
|
1088
|
+
import("./channel-worker-supervisor-NZQUOEFJ.js"),
|
|
1089
|
+
import("./pidfile-7Y3QEDSZ.js")
|
|
1086
1090
|
]).then(([supervisor, pidfile]) => ({
|
|
1087
1091
|
createChannelWorkerSupervisor: supervisor.createChannelWorkerSupervisor,
|
|
1088
1092
|
channelServicePidfile: pidfile
|
|
@@ -1153,7 +1157,7 @@ function shouldPreheatBridge(deps) {
|
|
|
1153
1157
|
__name(shouldPreheatBridge, "shouldPreheatBridge");
|
|
1154
1158
|
var coreRuntimePromise;
|
|
1155
1159
|
function loadCoreRuntime() {
|
|
1156
|
-
coreRuntimePromise ??= import("./src-
|
|
1160
|
+
coreRuntimePromise ??= import("./src-BIWCD3VX.js");
|
|
1157
1161
|
return coreRuntimePromise;
|
|
1158
1162
|
}
|
|
1159
1163
|
__name(loadCoreRuntime, "loadCoreRuntime");
|
|
@@ -1183,11 +1187,13 @@ __name(resolveDaemonLogBaseDirForRun, "resolveDaemonLogBaseDirForRun");
|
|
|
1183
1187
|
var settingsRuntimePromise;
|
|
1184
1188
|
function loadSettingsRuntimeModules() {
|
|
1185
1189
|
settingsRuntimePromise ??= Promise.all([
|
|
1186
|
-
import("./settings-
|
|
1187
|
-
import("./
|
|
1188
|
-
import("./
|
|
1189
|
-
|
|
1190
|
+
import("./settings-LVFFGXGE.js"),
|
|
1191
|
+
import("./environment-WKW5TLSH.js"),
|
|
1192
|
+
import("./loadedSettingsAdapter-FDO752BA.js"),
|
|
1193
|
+
import("./trustedFolders-IJ2QHXSC.js")
|
|
1194
|
+
]).then(([settings, environment, loadedSettingsAdapter, trustedFolders]) => ({
|
|
1190
1195
|
settings,
|
|
1196
|
+
environment,
|
|
1191
1197
|
loadedSettingsAdapter,
|
|
1192
1198
|
trustedFolders
|
|
1193
1199
|
}));
|
|
@@ -1203,16 +1209,20 @@ async function loadServeRuntimeModules() {
|
|
|
1203
1209
|
workspaceTypesModule,
|
|
1204
1210
|
daemonStatusProviderModule,
|
|
1205
1211
|
workspaceProvidersStatusModule,
|
|
1206
|
-
workspaceSkillsStatusModule
|
|
1212
|
+
workspaceSkillsStatusModule,
|
|
1213
|
+
totalSessionAdmissionModule,
|
|
1214
|
+
workspaceRegistryModule
|
|
1207
1215
|
] = await Promise.all([
|
|
1208
|
-
import("./server-
|
|
1209
|
-
import("./bridge-
|
|
1210
|
-
import("./spawnChannel-
|
|
1211
|
-
import("./workspace-service-
|
|
1216
|
+
import("./server-FVGFFVZ4.js"),
|
|
1217
|
+
import("./bridge-LJLLDUMW.js"),
|
|
1218
|
+
import("./spawnChannel-KIMZHWNR.js"),
|
|
1219
|
+
import("./workspace-service-V6G2RCD4.js"),
|
|
1212
1220
|
import("./types-QX5C3CHJ.js"),
|
|
1213
|
-
import("./daemon-status-provider-
|
|
1214
|
-
import("./workspace-providers-status-
|
|
1215
|
-
import("./workspace-skills-status-
|
|
1221
|
+
import("./daemon-status-provider-WBOAMCHE.js"),
|
|
1222
|
+
import("./workspace-providers-status-YMPTRKW2.js"),
|
|
1223
|
+
import("./workspace-skills-status-ZCW44BCH.js"),
|
|
1224
|
+
import("./total-session-admission-JOD7SMPJ.js"),
|
|
1225
|
+
import("./workspace-registry-NBUL6LBH.js")
|
|
1216
1226
|
]);
|
|
1217
1227
|
return {
|
|
1218
1228
|
createServeApp: serverModule.createServeApp,
|
|
@@ -1225,7 +1235,9 @@ async function loadServeRuntimeModules() {
|
|
|
1225
1235
|
WorkspaceSettingsPartialPersistError: workspaceTypesModule.WorkspaceSettingsPartialPersistError,
|
|
1226
1236
|
createDaemonStatusProvider: daemonStatusProviderModule.createDaemonStatusProvider,
|
|
1227
1237
|
createWorkspaceProvidersStatusProvider: workspaceProvidersStatusModule.createWorkspaceProvidersStatusProvider,
|
|
1228
|
-
createWorkspaceSkillsStatusProvider: workspaceSkillsStatusModule.createWorkspaceSkillsStatusProvider
|
|
1238
|
+
createWorkspaceSkillsStatusProvider: workspaceSkillsStatusModule.createWorkspaceSkillsStatusProvider,
|
|
1239
|
+
createTotalSessionAdmissionController: totalSessionAdmissionModule.createTotalSessionAdmissionController,
|
|
1240
|
+
createWorkspaceRegistry: workspaceRegistryModule.createWorkspaceRegistry
|
|
1229
1241
|
};
|
|
1230
1242
|
}
|
|
1231
1243
|
__name(loadServeRuntimeModules, "loadServeRuntimeModules");
|
|
@@ -1421,6 +1433,7 @@ function createBootstrapServeApp(input) {
|
|
|
1421
1433
|
qwenCodeVersion,
|
|
1422
1434
|
sessionShellCommandEnabled,
|
|
1423
1435
|
permissionPolicy,
|
|
1436
|
+
multiWorkspaceCapabilitiesRequireRuntime,
|
|
1424
1437
|
getRuntimeError,
|
|
1425
1438
|
getChannelWorkerSnapshot,
|
|
1426
1439
|
onHealthServed
|
|
@@ -1457,6 +1470,17 @@ function createBootstrapServeApp(input) {
|
|
|
1457
1470
|
app.get(BOOTSTRAP_HEALTH_PATH, healthHandler);
|
|
1458
1471
|
}
|
|
1459
1472
|
app.get(BOOTSTRAP_CAPABILITIES_PATH, (_req, res) => {
|
|
1473
|
+
if (multiWorkspaceCapabilitiesRequireRuntime) {
|
|
1474
|
+
const runtimeError = getRuntimeError();
|
|
1475
|
+
if (runtimeError === void 0) {
|
|
1476
|
+
res.setHeader("Retry-After", "1");
|
|
1477
|
+
}
|
|
1478
|
+
res.status(503).json({
|
|
1479
|
+
error: runtimeError ? "Daemon runtime failed to start" : "Daemon runtime is still starting",
|
|
1480
|
+
code: runtimeError ? "daemon_runtime_failed" : "daemon_runtime_starting"
|
|
1481
|
+
});
|
|
1482
|
+
return;
|
|
1483
|
+
}
|
|
1460
1484
|
res.status(200).json(
|
|
1461
1485
|
createBootstrapCapabilities({
|
|
1462
1486
|
opts,
|
|
@@ -1517,11 +1541,13 @@ function createBootstrapServeApp(input) {
|
|
|
1517
1541
|
},
|
|
1518
1542
|
limits: {
|
|
1519
1543
|
maxSessions: advertisedMaxSessions(opts.maxSessions),
|
|
1544
|
+
maxTotalSessions: positiveFiniteOrNull(opts.maxTotalSessions),
|
|
1520
1545
|
maxPendingPromptsPerSession: advertisedMaxPendingPromptsPerSession(
|
|
1521
1546
|
opts.maxPendingPromptsPerSession
|
|
1522
1547
|
),
|
|
1523
1548
|
listenerMaxConnections: listenerMaxConnections(opts.maxConnections),
|
|
1524
1549
|
eventRingSize: opts.eventRingSize ?? DEFAULT_EVENT_RING_SIZE,
|
|
1550
|
+
compactedReplayMaxBytes: opts.compactedReplayMaxBytes ?? DEFAULT_COMPACTED_REPLAY_MAX_BYTES,
|
|
1525
1551
|
promptDeadlineMs: positiveFiniteOrNull(opts.promptDeadlineMs),
|
|
1526
1552
|
writerIdleTimeoutMs: positiveFiniteOrNull(opts.writerIdleTimeoutMs),
|
|
1527
1553
|
channelIdleTimeoutMs: channelIdleTimeoutMs(opts.channelIdleTimeoutMs),
|
|
@@ -1662,6 +1688,9 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1662
1688
|
}
|
|
1663
1689
|
};
|
|
1664
1690
|
preResolveServeFastPathHomeEnvOverrides();
|
|
1691
|
+
const daemonRuntimeBaseEnv = Object.freeze({
|
|
1692
|
+
...process.env
|
|
1693
|
+
});
|
|
1665
1694
|
const rawToken = optsIn.token ?? process.env[QWEN_SERVER_TOKEN_ENV];
|
|
1666
1695
|
const token = typeof rawToken === "string" && rawToken.trim().length > 0 ? rawToken.trim() : void 0;
|
|
1667
1696
|
const sessionShellCommandEnabled = optsIn.enableSessionShell === true && token !== void 0;
|
|
@@ -1683,7 +1712,8 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1683
1712
|
const chromeExtensionOriginAllowed = hasChromeExtensionOrigin(
|
|
1684
1713
|
optsIn.allowOrigins
|
|
1685
1714
|
);
|
|
1686
|
-
const
|
|
1715
|
+
const rawWorkspaces = resolveWorkspaceInputs(optsIn.workspace);
|
|
1716
|
+
const rawWorkspace = rawWorkspaces[0];
|
|
1687
1717
|
const opts = {
|
|
1688
1718
|
...optsIn,
|
|
1689
1719
|
token,
|
|
@@ -1829,35 +1859,76 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1829
1859
|
"qwen serve: --allow-private-auth-base-url enabled; /workspace/auth/provider may install localhost/private-network model endpoints. Use only for local development with trusted clients."
|
|
1830
1860
|
);
|
|
1831
1861
|
}
|
|
1832
|
-
|
|
1833
|
-
|
|
1834
|
-
`Invalid --workspace "${rawWorkspace}": must be an absolute path.`
|
|
1835
|
-
);
|
|
1836
|
-
}
|
|
1837
|
-
try {
|
|
1838
|
-
const stats = fs.statSync(rawWorkspace);
|
|
1839
|
-
if (!stats.isDirectory()) {
|
|
1862
|
+
const validateAndCanonicalizeWorkspace = /* @__PURE__ */ __name((workspace) => {
|
|
1863
|
+
if (!path.isAbsolute(workspace)) {
|
|
1840
1864
|
throw new Error(
|
|
1841
|
-
`Invalid --workspace "${
|
|
1865
|
+
`Invalid --workspace "${workspace}": must be an absolute path.`
|
|
1842
1866
|
);
|
|
1843
1867
|
}
|
|
1844
|
-
|
|
1845
|
-
|
|
1846
|
-
|
|
1847
|
-
if (code === "ENOENT") {
|
|
1868
|
+
try {
|
|
1869
|
+
const stats = fs.statSync(workspace);
|
|
1870
|
+
if (!stats.isDirectory()) {
|
|
1848
1871
|
throw new Error(
|
|
1849
|
-
`Invalid --workspace "${
|
|
1872
|
+
`Invalid --workspace "${workspace}": exists but is not a directory.`
|
|
1850
1873
|
);
|
|
1851
1874
|
}
|
|
1852
|
-
|
|
1875
|
+
} catch (err) {
|
|
1876
|
+
if (err && typeof err === "object" && "code" in err) {
|
|
1877
|
+
const code = err.code;
|
|
1878
|
+
if (code === "ENOENT") {
|
|
1879
|
+
throw new Error(
|
|
1880
|
+
`Invalid --workspace "${workspace}": directory does not exist.`
|
|
1881
|
+
);
|
|
1882
|
+
}
|
|
1883
|
+
if (code === "EACCES" || code === "EPERM") {
|
|
1884
|
+
throw new Error(
|
|
1885
|
+
`Invalid --workspace "${workspace}": permission denied (${String(code)}). The path exists but cannot be stat'd by the current user.`
|
|
1886
|
+
);
|
|
1887
|
+
}
|
|
1888
|
+
}
|
|
1889
|
+
throw err;
|
|
1890
|
+
}
|
|
1891
|
+
return canonicalizeWorkspace(workspace);
|
|
1892
|
+
}, "validateAndCanonicalizeWorkspace");
|
|
1893
|
+
const workspaceInputs = rawWorkspaces.map((workspace) => ({
|
|
1894
|
+
raw: workspace,
|
|
1895
|
+
cwd: validateAndCanonicalizeWorkspace(workspace)
|
|
1896
|
+
}));
|
|
1897
|
+
const boundWorkspace = workspaceInputs[0].cwd;
|
|
1898
|
+
const seenCanonicalWorkspaces = /* @__PURE__ */ new Set();
|
|
1899
|
+
for (const workspace of workspaceInputs) {
|
|
1900
|
+
if (seenCanonicalWorkspaces.has(workspace.cwd)) {
|
|
1901
|
+
throw new Error(
|
|
1902
|
+
`Duplicate --workspace value resolves to ${JSON.stringify(
|
|
1903
|
+
workspace.cwd
|
|
1904
|
+
)}.`
|
|
1905
|
+
);
|
|
1906
|
+
}
|
|
1907
|
+
seenCanonicalWorkspaces.add(workspace.cwd);
|
|
1908
|
+
}
|
|
1909
|
+
for (let i = 0; i < workspaceInputs.length; i++) {
|
|
1910
|
+
for (let j = i + 1; j < workspaceInputs.length; j++) {
|
|
1911
|
+
const first = workspaceInputs[i].cwd;
|
|
1912
|
+
const second = workspaceInputs[j].cwd;
|
|
1913
|
+
const firstRel = path.relative(first, second);
|
|
1914
|
+
const secondRel = path.relative(second, first);
|
|
1915
|
+
if (firstRel && !firstRel.startsWith("..") && !path.isAbsolute(firstRel)) {
|
|
1853
1916
|
throw new Error(
|
|
1854
|
-
`
|
|
1917
|
+
`Nested --workspace values are not supported: ${JSON.stringify(second)} is inside ${JSON.stringify(first)}.`
|
|
1918
|
+
);
|
|
1919
|
+
}
|
|
1920
|
+
if (secondRel && !secondRel.startsWith("..") && !path.isAbsolute(secondRel)) {
|
|
1921
|
+
throw new Error(
|
|
1922
|
+
`Nested --workspace values are not supported: ${JSON.stringify(first)} is inside ${JSON.stringify(second)}.`
|
|
1855
1923
|
);
|
|
1856
1924
|
}
|
|
1857
1925
|
}
|
|
1858
|
-
throw err;
|
|
1859
1926
|
}
|
|
1860
|
-
|
|
1927
|
+
if (workspaceInputs.length > 1 && deps.bridge) {
|
|
1928
|
+
throw new Error(
|
|
1929
|
+
"Injected bridge dependencies are only supported with a single workspace; multiple --workspace values require runQwenServe to construct one bridge per workspace."
|
|
1930
|
+
);
|
|
1931
|
+
}
|
|
1861
1932
|
let contextFilenameForInit;
|
|
1862
1933
|
let permissionPolicy;
|
|
1863
1934
|
let permissionConsensusQuorum;
|
|
@@ -1918,6 +1989,13 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1918
1989
|
);
|
|
1919
1990
|
}
|
|
1920
1991
|
}
|
|
1992
|
+
if (opts.maxTotalSessions !== void 0) {
|
|
1993
|
+
if (!isNonNegativeIntegerOrInfinity(opts.maxTotalSessions)) {
|
|
1994
|
+
throw new TypeError(
|
|
1995
|
+
`Invalid maxTotalSessions: ${opts.maxTotalSessions}. Must be a non-negative integer (0 / Infinity = unlimited).`
|
|
1996
|
+
);
|
|
1997
|
+
}
|
|
1998
|
+
}
|
|
1921
1999
|
if (opts.maxPendingPromptsPerSession !== void 0) {
|
|
1922
2000
|
if (!isNonNegativeIntegerOrInfinity(opts.maxPendingPromptsPerSession)) {
|
|
1923
2001
|
throw new TypeError(
|
|
@@ -1932,6 +2010,9 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1932
2010
|
);
|
|
1933
2011
|
}
|
|
1934
2012
|
}
|
|
2013
|
+
if (opts.compactedReplayMaxBytes !== void 0) {
|
|
2014
|
+
normalizeCompactedReplayMaxBytes(opts.compactedReplayMaxBytes);
|
|
2015
|
+
}
|
|
1935
2016
|
if (opts.writerIdleTimeoutMs !== void 0) {
|
|
1936
2017
|
if (!isPositiveIntegerMs(opts.writerIdleTimeoutMs)) {
|
|
1937
2018
|
throw new TypeError(
|
|
@@ -1967,6 +2048,10 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
1967
2048
|
);
|
|
1968
2049
|
}
|
|
1969
2050
|
}
|
|
2051
|
+
opts.maxTotalSessions ??= deriveDefaultMaxTotalSessions(
|
|
2052
|
+
opts.maxSessions,
|
|
2053
|
+
workspaceInputs.length
|
|
2054
|
+
);
|
|
1970
2055
|
const inheritedNoPool = process.env["QWEN_SERVE_NO_MCP_POOL"] === "1";
|
|
1971
2056
|
if (opts.mcpPoolActive === void 0 && inheritedNoPool) {
|
|
1972
2057
|
opts.mcpPoolActive = false;
|
|
@@ -2004,6 +2089,7 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2004
2089
|
let runtimeApp;
|
|
2005
2090
|
let runtimeAppForCleanup;
|
|
2006
2091
|
let bridgeRef = deps.bridge;
|
|
2092
|
+
const internalRuntimeBridgesForCleanup = [];
|
|
2007
2093
|
let daemonEventLoopMonitor;
|
|
2008
2094
|
let daemonMetricsSampler;
|
|
2009
2095
|
let runtimeStartupError;
|
|
@@ -2046,6 +2132,17 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2046
2132
|
() => bridgeRef,
|
|
2047
2133
|
() => runtimeStartupError
|
|
2048
2134
|
);
|
|
2135
|
+
const shutdownBridges = /* @__PURE__ */ new WeakSet();
|
|
2136
|
+
const getRuntimeBridgesForCleanup = /* @__PURE__ */ __name(() => {
|
|
2137
|
+
const appForCleanup = runtimeApp ?? runtimeAppForCleanup;
|
|
2138
|
+
const registry = appForCleanup?.locals?.["workspaceRegistry"];
|
|
2139
|
+
const bridges = [
|
|
2140
|
+
...registry ? registry.list().map((runtime) => runtime.bridge) : [],
|
|
2141
|
+
...bridgeRef ? [bridgeRef] : [],
|
|
2142
|
+
...internalRuntimeBridgesForCleanup
|
|
2143
|
+
];
|
|
2144
|
+
return [...new Set(bridges)];
|
|
2145
|
+
}, "getRuntimeBridgesForCleanup");
|
|
2049
2146
|
const buildRuntime = /* @__PURE__ */ __name(async () => {
|
|
2050
2147
|
const [runtime, core, settingsRuntime, resolvedCliVersion] = await Promise.all([
|
|
2051
2148
|
loadServeRuntimeModules(),
|
|
@@ -2072,6 +2169,43 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2072
2169
|
{ workspace: boundWorkspace }
|
|
2073
2170
|
);
|
|
2074
2171
|
}
|
|
2172
|
+
const runtimeEnvSnapshot = runtimeBootSettings ? settingsRuntime.environment.buildRuntimeEnvironment(
|
|
2173
|
+
runtimeBootSettings.merged,
|
|
2174
|
+
boundWorkspace,
|
|
2175
|
+
daemonRuntimeBaseEnv
|
|
2176
|
+
) : {
|
|
2177
|
+
effectiveEnv: { ...daemonRuntimeBaseEnv },
|
|
2178
|
+
overlayKeys: Object.freeze([]),
|
|
2179
|
+
envFilePaths: Object.freeze([]),
|
|
2180
|
+
envFileReadFailed: false,
|
|
2181
|
+
envFileReadFailures: Object.freeze([])
|
|
2182
|
+
};
|
|
2183
|
+
const logRuntimeEnvFileReadFailures = /* @__PURE__ */ __name((workspace, snapshot) => {
|
|
2184
|
+
if (!snapshot.envFileReadFailed) return;
|
|
2185
|
+
const failedFiles = snapshot.envFileReadFailures ?? [];
|
|
2186
|
+
daemonLog.warn("one or more runtime env files could not be read", {
|
|
2187
|
+
workspace,
|
|
2188
|
+
...failedFiles.length > 0 ? { failedFiles } : {}
|
|
2189
|
+
});
|
|
2190
|
+
}, "logRuntimeEnvFileReadFailures");
|
|
2191
|
+
logRuntimeEnvFileReadFailures(boundWorkspace, runtimeEnvSnapshot);
|
|
2192
|
+
const runtimeEffectiveEnv = {
|
|
2193
|
+
...runtimeEnvSnapshot.effectiveEnv
|
|
2194
|
+
};
|
|
2195
|
+
const replaceRuntimeEffectiveEnv = /* @__PURE__ */ __name((nextEnv) => {
|
|
2196
|
+
for (const key of Object.keys(runtimeEffectiveEnv)) {
|
|
2197
|
+
delete runtimeEffectiveEnv[key];
|
|
2198
|
+
}
|
|
2199
|
+
Object.assign(runtimeEffectiveEnv, nextEnv);
|
|
2200
|
+
}, "replaceRuntimeEffectiveEnv");
|
|
2201
|
+
const primaryRuntimeEnv = {
|
|
2202
|
+
mode: "runtime-overlay",
|
|
2203
|
+
overlayKeys: [...runtimeEnvSnapshot.overlayKeys],
|
|
2204
|
+
effectiveEnv: runtimeEffectiveEnv,
|
|
2205
|
+
envFilePaths: [...runtimeEnvSnapshot.envFilePaths],
|
|
2206
|
+
envFileReadFailed: runtimeEnvSnapshot.envFileReadFailed,
|
|
2207
|
+
envFileReadFailures: [...runtimeEnvSnapshot.envFileReadFailures]
|
|
2208
|
+
};
|
|
2075
2209
|
const daemonWorkspaceHash = core.hashDaemonWorkspace(boundWorkspace);
|
|
2076
2210
|
let daemonTelemetrySettings;
|
|
2077
2211
|
try {
|
|
@@ -2144,54 +2278,58 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2144
2278
|
promptQueueWaitStats.lastMs = durationMs;
|
|
2145
2279
|
core.recordDaemonPromptQueueWait(durationMs);
|
|
2146
2280
|
}, "recordPromptQueueWait");
|
|
2147
|
-
const
|
|
2148
|
-
|
|
2149
|
-
|
|
2150
|
-
|
|
2151
|
-
|
|
2152
|
-
|
|
2153
|
-
|
|
2154
|
-
|
|
2155
|
-
|
|
2156
|
-
|
|
2157
|
-
|
|
2158
|
-
|
|
2159
|
-
|
|
2160
|
-
|
|
2161
|
-
|
|
2162
|
-
|
|
2163
|
-
|
|
2164
|
-
|
|
2165
|
-
|
|
2166
|
-
|
|
2167
|
-
|
|
2168
|
-
|
|
2169
|
-
|
|
2170
|
-
|
|
2281
|
+
const createRuntimeBridgeTelemetry = /* @__PURE__ */ __name((workspaceHash) => {
|
|
2282
|
+
const telemetry = core.createDaemonBridgeTelemetry();
|
|
2283
|
+
telemetry.metrics = {
|
|
2284
|
+
sessionLifecycle(action) {
|
|
2285
|
+
core.recordDaemonSessionLifecycle(action);
|
|
2286
|
+
core.emitDaemonLog(
|
|
2287
|
+
`Session ${action}.`,
|
|
2288
|
+
{
|
|
2289
|
+
"qwen-code.workspace.hash": workspaceHash
|
|
2290
|
+
},
|
|
2291
|
+
{
|
|
2292
|
+
eventName: `qwen-code.daemon.session.${action}`
|
|
2293
|
+
}
|
|
2294
|
+
);
|
|
2295
|
+
},
|
|
2296
|
+
channelLifecycle(action, expected) {
|
|
2297
|
+
core.recordDaemonChannelLifecycle(action, expected);
|
|
2298
|
+
core.emitDaemonLog(
|
|
2299
|
+
action === "spawn" ? "ACP channel spawned." : `ACP channel exited (expected=${expected ?? true}).`,
|
|
2300
|
+
{
|
|
2301
|
+
...action === "exit" ? { "qwen-code.daemon.channel.expected": expected ?? true } : {}
|
|
2302
|
+
},
|
|
2303
|
+
{
|
|
2304
|
+
eventName: `qwen-code.daemon.channel.${action}`,
|
|
2305
|
+
...expected === false && action === "exit" ? { severityNumber: 13 } : {}
|
|
2306
|
+
}
|
|
2307
|
+
);
|
|
2308
|
+
},
|
|
2309
|
+
promptQueueWait(durationMs) {
|
|
2310
|
+
recordPromptQueueWait(durationMs);
|
|
2311
|
+
metricsRing.recordPromptQueueWait(durationMs);
|
|
2312
|
+
},
|
|
2313
|
+
promptDuration(durationMs) {
|
|
2314
|
+
core.recordDaemonPromptDuration(durationMs);
|
|
2315
|
+
metricsRing.recordPromptDuration(durationMs);
|
|
2316
|
+
},
|
|
2317
|
+
cancelled: core.recordDaemonCancel,
|
|
2318
|
+
// Per-round model token usage + LLM round-trip time sniffed off
|
|
2319
|
+
// `agent_message_chunk._meta` (`usage` + `durationMs`) at the bridge's
|
|
2320
|
+
// single session/update fan-in. Increments (not cumulative), so the ring
|
|
2321
|
+
// sums tokens per window (token-burn chart) and pools the round-trip times
|
|
2322
|
+
// for the LLM-latency percentiles.
|
|
2323
|
+
tokenUsage(inputTokens, outputTokens, durationMs) {
|
|
2324
|
+
metricsRing.recordTokens(inputTokens, outputTokens);
|
|
2325
|
+
if (typeof durationMs === "number") {
|
|
2326
|
+
metricsRing.recordLlmDuration(durationMs);
|
|
2171
2327
|
}
|
|
2172
|
-
);
|
|
2173
|
-
},
|
|
2174
|
-
promptQueueWait(durationMs) {
|
|
2175
|
-
recordPromptQueueWait(durationMs);
|
|
2176
|
-
metricsRing.recordPromptQueueWait(durationMs);
|
|
2177
|
-
},
|
|
2178
|
-
promptDuration(durationMs) {
|
|
2179
|
-
core.recordDaemonPromptDuration(durationMs);
|
|
2180
|
-
metricsRing.recordPromptDuration(durationMs);
|
|
2181
|
-
},
|
|
2182
|
-
cancelled: core.recordDaemonCancel,
|
|
2183
|
-
// Per-round model token usage + LLM round-trip time sniffed off
|
|
2184
|
-
// `agent_message_chunk._meta` (`usage` + `durationMs`) at the bridge's
|
|
2185
|
-
// single session/update fan-in. Increments (not cumulative), so the ring
|
|
2186
|
-
// sums tokens per window (token-burn chart) and pools the round-trip times
|
|
2187
|
-
// for the LLM-latency percentiles.
|
|
2188
|
-
tokenUsage(inputTokens, outputTokens, durationMs) {
|
|
2189
|
-
metricsRing.recordTokens(inputTokens, outputTokens);
|
|
2190
|
-
if (typeof durationMs === "number") {
|
|
2191
|
-
metricsRing.recordLlmDuration(durationMs);
|
|
2192
2328
|
}
|
|
2193
|
-
}
|
|
2194
|
-
|
|
2329
|
+
};
|
|
2330
|
+
return telemetry;
|
|
2331
|
+
}, "createRuntimeBridgeTelemetry");
|
|
2332
|
+
const daemonTelemetry = createRuntimeBridgeTelemetry(daemonWorkspaceHash);
|
|
2195
2333
|
const permissionAuditRing = new PermissionAuditRing();
|
|
2196
2334
|
const permissionAuditPublisher = createPermissionAuditPublisher({
|
|
2197
2335
|
ring: permissionAuditRing
|
|
@@ -2238,7 +2376,17 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2238
2376
|
pathLocks: sharedPathLocks,
|
|
2239
2377
|
...customIgnoreFiles !== void 0 ? { customIgnoreFiles } : {}
|
|
2240
2378
|
});
|
|
2379
|
+
const routeFsFactory = runtime.resolveBridgeFsFactory({
|
|
2380
|
+
// REST routes still return primary-relative paths, so keep their
|
|
2381
|
+
// filesystem boundary primary-only until responses carry root IDs.
|
|
2382
|
+
boundWorkspaces: [boundWorkspace],
|
|
2383
|
+
trusted: trustedWorkspace,
|
|
2384
|
+
emit: deps.fsAuditEmit,
|
|
2385
|
+
pathLocks: sharedPathLocks,
|
|
2386
|
+
...customIgnoreFiles !== void 0 ? { customIgnoreFiles } : {}
|
|
2387
|
+
});
|
|
2241
2388
|
const channelFactory = runtime.createSpawnChannelFactory({
|
|
2389
|
+
sourceEnv: runtimeEffectiveEnv,
|
|
2242
2390
|
onDiagnosticLine: diagnosticSink,
|
|
2243
2391
|
pipeHooks: {
|
|
2244
2392
|
onMessageSent: /* @__PURE__ */ __name((bytes) => recordPipeMessage("outbound", bytes), "onMessageSent"),
|
|
@@ -2251,10 +2399,21 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2251
2399
|
},
|
|
2252
2400
|
...opts.experimentalLsp === true ? { extraArgs: ["--experimental-lsp"] } : {}
|
|
2253
2401
|
});
|
|
2254
|
-
const statusProvider = runtime.createDaemonStatusProvider(
|
|
2255
|
-
|
|
2402
|
+
const statusProvider = runtime.createDaemonStatusProvider({
|
|
2403
|
+
env: runtimeEffectiveEnv
|
|
2404
|
+
});
|
|
2405
|
+
const workspaceProvidersStatusProvider = runtime.createWorkspaceProvidersStatusProvider({
|
|
2406
|
+
env: runtimeEffectiveEnv
|
|
2407
|
+
});
|
|
2256
2408
|
const workspaceSkillsStatusProvider = runtime.createWorkspaceSkillsStatusProvider();
|
|
2257
2409
|
const clientMcpSenderRegistry = new ClientMcpSenderRegistry();
|
|
2410
|
+
const runtimeBridges = [];
|
|
2411
|
+
const totalSessionAdmission = runtime.createTotalSessionAdmissionController(
|
|
2412
|
+
{
|
|
2413
|
+
maxTotalSessions: opts.maxTotalSessions,
|
|
2414
|
+
getBridges: /* @__PURE__ */ __name(() => runtimeBridges.length > 0 ? runtimeBridges : bridgeRef ? [bridgeRef] : [], "getBridges")
|
|
2415
|
+
}
|
|
2416
|
+
);
|
|
2258
2417
|
const persistDisabledToolsFn = /* @__PURE__ */ __name((workspace, toolName, enabled) => withSettingsLock(workspace, async () => {
|
|
2259
2418
|
const fresh = settingsRuntime.settings.loadSettings(workspace);
|
|
2260
2419
|
const wsScope = fresh.forScope(WORKSPACE_SETTING_SCOPE).settings;
|
|
@@ -2306,8 +2465,10 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2306
2465
|
// connection that hosts a named client MCP server (#5626).
|
|
2307
2466
|
clientMcpSender: clientMcpSenderRegistry.lookup,
|
|
2308
2467
|
maxSessions: opts.maxSessions,
|
|
2468
|
+
freshSessionAdmission: totalSessionAdmission.admit,
|
|
2309
2469
|
...opts.maxPendingPromptsPerSession !== void 0 ? { maxPendingPromptsPerSession: opts.maxPendingPromptsPerSession } : {},
|
|
2310
2470
|
...opts.eventRingSize !== void 0 ? { eventRingSize: opts.eventRingSize } : {},
|
|
2471
|
+
...opts.compactedReplayMaxBytes !== void 0 ? { compactedReplayMaxBytes: opts.compactedReplayMaxBytes } : {},
|
|
2311
2472
|
...opts.channelIdleTimeoutMs !== void 0 ? { channelIdleTimeoutMs: opts.channelIdleTimeoutMs } : {},
|
|
2312
2473
|
...opts.sessionReapIntervalMs !== void 0 ? { sessionReapIntervalMs: opts.sessionReapIntervalMs } : {},
|
|
2313
2474
|
...opts.sessionIdleTimeoutMs !== void 0 ? { sessionIdleTimeoutMs: opts.sessionIdleTimeoutMs } : {},
|
|
@@ -2330,7 +2491,9 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2330
2491
|
});
|
|
2331
2492
|
if (!deps.bridge) {
|
|
2332
2493
|
bridgeRef = bridge;
|
|
2494
|
+
internalRuntimeBridgesForCleanup.push(bridge);
|
|
2333
2495
|
}
|
|
2496
|
+
runtimeBridges.push(bridge);
|
|
2334
2497
|
const workspaceService = runtime.createDaemonWorkspaceService({
|
|
2335
2498
|
boundWorkspace,
|
|
2336
2499
|
contextFilename: contextFilenameForInit ?? "QWEN.md",
|
|
@@ -2345,18 +2508,273 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2345
2508
|
const fresh = settingsRuntime.settings.loadSettings(workspace, {
|
|
2346
2509
|
skipLoadEnvironment: true
|
|
2347
2510
|
});
|
|
2348
|
-
|
|
2511
|
+
const result = settingsRuntime.settings.reloadEnvironment(
|
|
2349
2512
|
fresh.merged,
|
|
2350
2513
|
workspace
|
|
2351
2514
|
);
|
|
2515
|
+
let refreshedRuntimeEnv;
|
|
2516
|
+
let fallbackReason;
|
|
2517
|
+
try {
|
|
2518
|
+
refreshedRuntimeEnv = settingsRuntime.environment.buildRuntimeEnvironment(
|
|
2519
|
+
fresh.merged,
|
|
2520
|
+
workspace,
|
|
2521
|
+
daemonRuntimeBaseEnv
|
|
2522
|
+
);
|
|
2523
|
+
} catch (err) {
|
|
2524
|
+
fallbackReason = err instanceof Error ? err.message : String(err);
|
|
2525
|
+
daemonLog.warn(
|
|
2526
|
+
"failed to rebuild runtime env snapshot after daemon env reload; preserving previous runtime env",
|
|
2527
|
+
{
|
|
2528
|
+
error: fallbackReason
|
|
2529
|
+
}
|
|
2530
|
+
);
|
|
2531
|
+
refreshedRuntimeEnv = {
|
|
2532
|
+
effectiveEnv: { ...runtimeEffectiveEnv },
|
|
2533
|
+
overlayKeys: [...primaryRuntimeEnv.overlayKeys],
|
|
2534
|
+
envFilePaths: [...primaryRuntimeEnv.envFilePaths],
|
|
2535
|
+
envFileReadFailed: primaryRuntimeEnv.envFileReadFailed ?? false,
|
|
2536
|
+
envFileReadFailures: [
|
|
2537
|
+
...primaryRuntimeEnv.envFileReadFailures ?? []
|
|
2538
|
+
]
|
|
2539
|
+
};
|
|
2540
|
+
}
|
|
2541
|
+
logRuntimeEnvFileReadFailures(workspace, refreshedRuntimeEnv);
|
|
2542
|
+
replaceRuntimeEffectiveEnv(refreshedRuntimeEnv.effectiveEnv);
|
|
2543
|
+
if (fallbackReason) {
|
|
2544
|
+
primaryRuntimeEnv.fallbackReason = fallbackReason;
|
|
2545
|
+
} else {
|
|
2546
|
+
delete primaryRuntimeEnv.fallbackReason;
|
|
2547
|
+
}
|
|
2548
|
+
primaryRuntimeEnv.envFileReadFailed = refreshedRuntimeEnv.envFileReadFailed;
|
|
2549
|
+
primaryRuntimeEnv.envFileReadFailures.splice(
|
|
2550
|
+
0,
|
|
2551
|
+
primaryRuntimeEnv.envFileReadFailures.length,
|
|
2552
|
+
...refreshedRuntimeEnv.envFileReadFailures
|
|
2553
|
+
);
|
|
2554
|
+
primaryRuntimeEnv.overlayKeys.splice(
|
|
2555
|
+
0,
|
|
2556
|
+
primaryRuntimeEnv.overlayKeys.length,
|
|
2557
|
+
...refreshedRuntimeEnv.overlayKeys
|
|
2558
|
+
);
|
|
2559
|
+
primaryRuntimeEnv.envFilePaths.splice(
|
|
2560
|
+
0,
|
|
2561
|
+
primaryRuntimeEnv.envFilePaths.length,
|
|
2562
|
+
...refreshedRuntimeEnv.envFilePaths
|
|
2563
|
+
);
|
|
2564
|
+
return result;
|
|
2352
2565
|
}), "reloadDaemonEnv"),
|
|
2353
2566
|
queryWorkspaceStatus: /* @__PURE__ */ __name((method, idle) => bridge.queryWorkspaceStatus(method, idle), "queryWorkspaceStatus"),
|
|
2354
2567
|
invokeWorkspaceCommand: /* @__PURE__ */ __name((method, params, invokeOpts) => bridge.invokeWorkspaceCommand(method, params, invokeOpts), "invokeWorkspaceCommand"),
|
|
2355
2568
|
refreshExtensionsForAllSessions: /* @__PURE__ */ __name(() => bridge.refreshExtensionsForAllSessions(), "refreshExtensionsForAllSessions"),
|
|
2356
2569
|
publishWorkspaceEvent: /* @__PURE__ */ __name((event) => bridge.publishWorkspaceEvent(event), "publishWorkspaceEvent")
|
|
2357
2570
|
});
|
|
2571
|
+
const workspaceRuntimes = [
|
|
2572
|
+
{
|
|
2573
|
+
workspaceId: daemonWorkspaceHash,
|
|
2574
|
+
workspaceCwd: boundWorkspace,
|
|
2575
|
+
primary: true,
|
|
2576
|
+
trusted: trustedWorkspace,
|
|
2577
|
+
env: primaryRuntimeEnv,
|
|
2578
|
+
bridge,
|
|
2579
|
+
workspaceService,
|
|
2580
|
+
routeFileSystemFactory: routeFsFactory,
|
|
2581
|
+
clientMcpSenderRegistry
|
|
2582
|
+
}
|
|
2583
|
+
];
|
|
2584
|
+
const createRuntimeEnvMetadata = /* @__PURE__ */ __name((workspace, settings) => {
|
|
2585
|
+
const snapshot = settings ? settingsRuntime.environment.buildRuntimeEnvironment(
|
|
2586
|
+
settings.merged,
|
|
2587
|
+
workspace,
|
|
2588
|
+
daemonRuntimeBaseEnv
|
|
2589
|
+
) : {
|
|
2590
|
+
effectiveEnv: { ...daemonRuntimeBaseEnv },
|
|
2591
|
+
overlayKeys: Object.freeze([]),
|
|
2592
|
+
envFilePaths: Object.freeze([]),
|
|
2593
|
+
envFileReadFailed: false,
|
|
2594
|
+
envFileReadFailures: Object.freeze([])
|
|
2595
|
+
};
|
|
2596
|
+
logRuntimeEnvFileReadFailures(workspace, snapshot);
|
|
2597
|
+
const effectiveEnv = { ...snapshot.effectiveEnv };
|
|
2598
|
+
const metadata = {
|
|
2599
|
+
mode: "runtime-overlay",
|
|
2600
|
+
overlayKeys: [...snapshot.overlayKeys],
|
|
2601
|
+
effectiveEnv,
|
|
2602
|
+
envFilePaths: [...snapshot.envFilePaths],
|
|
2603
|
+
envFileReadFailed: snapshot.envFileReadFailed,
|
|
2604
|
+
envFileReadFailures: [...snapshot.envFileReadFailures]
|
|
2605
|
+
};
|
|
2606
|
+
return {
|
|
2607
|
+
metadata,
|
|
2608
|
+
effectiveEnv,
|
|
2609
|
+
replace(nextEnv) {
|
|
2610
|
+
for (const key of Object.keys(effectiveEnv)) {
|
|
2611
|
+
delete effectiveEnv[key];
|
|
2612
|
+
}
|
|
2613
|
+
Object.assign(effectiveEnv, nextEnv);
|
|
2614
|
+
}
|
|
2615
|
+
};
|
|
2616
|
+
}, "createRuntimeEnvMetadata");
|
|
2617
|
+
for (const workspaceInput of workspaceInputs.slice(1)) {
|
|
2618
|
+
let secondarySettings;
|
|
2619
|
+
try {
|
|
2620
|
+
secondarySettings = settingsRuntime.settings.loadSettings(
|
|
2621
|
+
workspaceInput.cwd
|
|
2622
|
+
);
|
|
2623
|
+
} catch (err) {
|
|
2624
|
+
writeStderrLine(
|
|
2625
|
+
`qwen serve: could not read full settings for secondary workspace ${workspaceInput.cwd} (${err instanceof Error ? err.message : String(err)}); falling back to defaults.`
|
|
2626
|
+
);
|
|
2627
|
+
}
|
|
2628
|
+
const secondaryTrusted = secondarySettings ? settingsRuntime.trustedFolders.getWorkspaceTrustStatus(
|
|
2629
|
+
secondarySettings.merged,
|
|
2630
|
+
workspaceInput.cwd
|
|
2631
|
+
).effective.state === "trusted" : false;
|
|
2632
|
+
if (!secondaryTrusted) {
|
|
2633
|
+
daemonLog.warn("secondary workspace is not trusted", {
|
|
2634
|
+
workspace: workspaceInput.cwd,
|
|
2635
|
+
trustSettingsAvailable: secondarySettings !== void 0
|
|
2636
|
+
});
|
|
2637
|
+
}
|
|
2638
|
+
const secondaryEnv = createRuntimeEnvMetadata(
|
|
2639
|
+
workspaceInput.cwd,
|
|
2640
|
+
secondarySettings
|
|
2641
|
+
);
|
|
2642
|
+
const secondaryWorkspaceHash = core.hashDaemonWorkspace(
|
|
2643
|
+
workspaceInput.cwd
|
|
2644
|
+
);
|
|
2645
|
+
const secondaryStatusProvider = runtime.createDaemonStatusProvider({
|
|
2646
|
+
env: secondaryEnv.effectiveEnv
|
|
2647
|
+
});
|
|
2648
|
+
const secondaryBridgeFsFactory = runtime.resolveBridgeFsFactory({
|
|
2649
|
+
boundWorkspaces: [workspaceInput.cwd],
|
|
2650
|
+
trusted: secondaryTrusted,
|
|
2651
|
+
emit: deps.fsAuditEmit,
|
|
2652
|
+
pathLocks: sharedPathLocks,
|
|
2653
|
+
...customIgnoreFiles !== void 0 ? { customIgnoreFiles } : {}
|
|
2654
|
+
});
|
|
2655
|
+
const secondaryChannelFactory = runtime.createSpawnChannelFactory({
|
|
2656
|
+
sourceEnv: secondaryEnv.effectiveEnv,
|
|
2657
|
+
onDiagnosticLine: diagnosticSink,
|
|
2658
|
+
pipeHooks: {
|
|
2659
|
+
onMessageSent: /* @__PURE__ */ __name((bytes) => recordPipeMessage("outbound", bytes), "onMessageSent"),
|
|
2660
|
+
onMessageReceived: /* @__PURE__ */ __name((bytes) => recordPipeMessage("inbound", bytes), "onMessageReceived"),
|
|
2661
|
+
onMessageObserved: /* @__PURE__ */ __name(({ direction, bytes, message }) => observeLargePipeFrame({
|
|
2662
|
+
direction: daemonPipeDirection(direction),
|
|
2663
|
+
bytes,
|
|
2664
|
+
message
|
|
2665
|
+
}), "onMessageObserved")
|
|
2666
|
+
},
|
|
2667
|
+
...opts.experimentalLsp === true ? { extraArgs: ["--experimental-lsp"] } : {}
|
|
2668
|
+
});
|
|
2669
|
+
const secondaryClientMcpSenderRegistry = new ClientMcpSenderRegistry();
|
|
2670
|
+
const secondaryBridge = runtime.createAcpSessionBridge({
|
|
2671
|
+
clientMcpSender: secondaryClientMcpSenderRegistry.lookup,
|
|
2672
|
+
maxSessions: opts.maxSessions,
|
|
2673
|
+
freshSessionAdmission: totalSessionAdmission.admit,
|
|
2674
|
+
...opts.maxPendingPromptsPerSession !== void 0 ? { maxPendingPromptsPerSession: opts.maxPendingPromptsPerSession } : {},
|
|
2675
|
+
...opts.eventRingSize !== void 0 ? { eventRingSize: opts.eventRingSize } : {},
|
|
2676
|
+
...opts.compactedReplayMaxBytes !== void 0 ? { compactedReplayMaxBytes: opts.compactedReplayMaxBytes } : {},
|
|
2677
|
+
...opts.channelIdleTimeoutMs !== void 0 ? { channelIdleTimeoutMs: opts.channelIdleTimeoutMs } : {},
|
|
2678
|
+
...opts.sessionReapIntervalMs !== void 0 ? { sessionReapIntervalMs: opts.sessionReapIntervalMs } : {},
|
|
2679
|
+
...opts.sessionIdleTimeoutMs !== void 0 ? { sessionIdleTimeoutMs: opts.sessionIdleTimeoutMs } : {},
|
|
2680
|
+
...opts.permissionResponseTimeoutMs !== void 0 ? { permissionResponseTimeoutMs: opts.permissionResponseTimeoutMs } : {},
|
|
2681
|
+
boundWorkspace: workspaceInput.cwd,
|
|
2682
|
+
sessionShellCommandEnabled,
|
|
2683
|
+
childEnvOverrides,
|
|
2684
|
+
channelFactory: secondaryChannelFactory,
|
|
2685
|
+
onDiagnosticLine: diagnosticSink,
|
|
2686
|
+
telemetry: createRuntimeBridgeTelemetry(secondaryWorkspaceHash),
|
|
2687
|
+
...permissionPolicy !== void 0 ? { permissionPolicy } : {},
|
|
2688
|
+
...permissionConsensusQuorum !== void 0 ? {
|
|
2689
|
+
permissionConsensusQuorum
|
|
2690
|
+
} : {},
|
|
2691
|
+
permissionAudit: permissionAuditPublisher,
|
|
2692
|
+
statusProvider: secondaryStatusProvider,
|
|
2693
|
+
fileSystem: createBridgeFileSystemAdapter(secondaryBridgeFsFactory),
|
|
2694
|
+
persistApprovalMode: /* @__PURE__ */ __name((workspace, mode) => withSettingsLock(workspace, async () => {
|
|
2695
|
+
const fresh = settingsRuntime.settings.loadSettings(workspace);
|
|
2696
|
+
fresh.setValue(WORKSPACE_SETTING_SCOPE, "tools.approvalMode", mode);
|
|
2697
|
+
}), "persistApprovalMode")
|
|
2698
|
+
});
|
|
2699
|
+
runtimeBridges.push(secondaryBridge);
|
|
2700
|
+
internalRuntimeBridgesForCleanup.push(secondaryBridge);
|
|
2701
|
+
const secondaryWorkspaceService = runtime.createDaemonWorkspaceService({
|
|
2702
|
+
boundWorkspace: workspaceInput.cwd,
|
|
2703
|
+
contextFilename: contextFilenameForInit ?? "QWEN.md",
|
|
2704
|
+
statusProvider: secondaryStatusProvider,
|
|
2705
|
+
workspaceProvidersStatusProvider: runtime.createWorkspaceProvidersStatusProvider({
|
|
2706
|
+
env: secondaryEnv.effectiveEnv
|
|
2707
|
+
}),
|
|
2708
|
+
workspaceSkillsStatusProvider: runtime.createWorkspaceSkillsStatusProvider(),
|
|
2709
|
+
isChannelLive: /* @__PURE__ */ __name(() => secondaryBridge.isChannelLive(), "isChannelLive"),
|
|
2710
|
+
persistDisabledTools: persistDisabledToolsFn,
|
|
2711
|
+
persistSetting: persistSettingFn,
|
|
2712
|
+
persistSettings: persistSettingsFn,
|
|
2713
|
+
reloadDaemonEnv: /* @__PURE__ */ __name((workspace) => withSettingsLock(workspace, async () => {
|
|
2714
|
+
const fresh = settingsRuntime.settings.loadSettings(workspace, {
|
|
2715
|
+
skipLoadEnvironment: true
|
|
2716
|
+
});
|
|
2717
|
+
const result = settingsRuntime.settings.reloadEnvironment(
|
|
2718
|
+
fresh.merged,
|
|
2719
|
+
workspace
|
|
2720
|
+
);
|
|
2721
|
+
try {
|
|
2722
|
+
const refreshedRuntimeEnv = settingsRuntime.environment.buildRuntimeEnvironment(
|
|
2723
|
+
fresh.merged,
|
|
2724
|
+
workspace,
|
|
2725
|
+
daemonRuntimeBaseEnv
|
|
2726
|
+
);
|
|
2727
|
+
logRuntimeEnvFileReadFailures(workspace, refreshedRuntimeEnv);
|
|
2728
|
+
secondaryEnv.replace(refreshedRuntimeEnv.effectiveEnv);
|
|
2729
|
+
secondaryEnv.metadata.envFileReadFailed = refreshedRuntimeEnv.envFileReadFailed;
|
|
2730
|
+
secondaryEnv.metadata.envFileReadFailures.splice(
|
|
2731
|
+
0,
|
|
2732
|
+
secondaryEnv.metadata.envFileReadFailures.length,
|
|
2733
|
+
...refreshedRuntimeEnv.envFileReadFailures
|
|
2734
|
+
);
|
|
2735
|
+
secondaryEnv.metadata.overlayKeys.splice(
|
|
2736
|
+
0,
|
|
2737
|
+
secondaryEnv.metadata.overlayKeys.length,
|
|
2738
|
+
...refreshedRuntimeEnv.overlayKeys
|
|
2739
|
+
);
|
|
2740
|
+
secondaryEnv.metadata.envFilePaths.splice(
|
|
2741
|
+
0,
|
|
2742
|
+
secondaryEnv.metadata.envFilePaths.length,
|
|
2743
|
+
...refreshedRuntimeEnv.envFilePaths
|
|
2744
|
+
);
|
|
2745
|
+
delete secondaryEnv.metadata.fallbackReason;
|
|
2746
|
+
} catch (err) {
|
|
2747
|
+
secondaryEnv.metadata.fallbackReason = err instanceof Error ? err.message : String(err);
|
|
2748
|
+
daemonLog.warn(
|
|
2749
|
+
"failed to rebuild secondary runtime env snapshot after daemon env reload; preserving previous runtime env",
|
|
2750
|
+
{
|
|
2751
|
+
workspace,
|
|
2752
|
+
error: secondaryEnv.metadata.fallbackReason
|
|
2753
|
+
}
|
|
2754
|
+
);
|
|
2755
|
+
}
|
|
2756
|
+
return result;
|
|
2757
|
+
}), "reloadDaemonEnv"),
|
|
2758
|
+
queryWorkspaceStatus: /* @__PURE__ */ __name((method, idle) => secondaryBridge.queryWorkspaceStatus(method, idle), "queryWorkspaceStatus"),
|
|
2759
|
+
invokeWorkspaceCommand: /* @__PURE__ */ __name((method, params, invokeOpts) => secondaryBridge.invokeWorkspaceCommand(method, params, invokeOpts), "invokeWorkspaceCommand"),
|
|
2760
|
+
refreshExtensionsForAllSessions: /* @__PURE__ */ __name(() => secondaryBridge.refreshExtensionsForAllSessions(), "refreshExtensionsForAllSessions"),
|
|
2761
|
+
publishWorkspaceEvent: /* @__PURE__ */ __name((event) => secondaryBridge.publishWorkspaceEvent(event), "publishWorkspaceEvent")
|
|
2762
|
+
});
|
|
2763
|
+
workspaceRuntimes.push({
|
|
2764
|
+
workspaceId: secondaryWorkspaceHash,
|
|
2765
|
+
workspaceCwd: workspaceInput.cwd,
|
|
2766
|
+
primary: false,
|
|
2767
|
+
trusted: secondaryTrusted,
|
|
2768
|
+
env: secondaryEnv.metadata,
|
|
2769
|
+
bridge: secondaryBridge,
|
|
2770
|
+
workspaceService: secondaryWorkspaceService,
|
|
2771
|
+
routeFileSystemFactory: secondaryBridgeFsFactory,
|
|
2772
|
+
clientMcpSenderRegistry: secondaryClientMcpSenderRegistry
|
|
2773
|
+
});
|
|
2774
|
+
}
|
|
2775
|
+
const workspaceRegistry = runtime.createWorkspaceRegistry(workspaceRuntimes);
|
|
2358
2776
|
core.registerDaemonGaugeCallbacks({
|
|
2359
|
-
sessionCount: /* @__PURE__ */ __name(() => bridge.sessionCount, "sessionCount"),
|
|
2777
|
+
sessionCount: /* @__PURE__ */ __name(() => workspaceRegistry.list().reduce((sum, item) => sum + item.bridge.sessionCount, 0), "sessionCount"),
|
|
2360
2778
|
sseCount: /* @__PURE__ */ __name(() => runtime.getActiveSseCount(), "sseCount"),
|
|
2361
2779
|
heapUsed: /* @__PURE__ */ __name(() => process.memoryUsage().heapUsed, "heapUsed")
|
|
2362
2780
|
});
|
|
@@ -2396,9 +2814,15 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2396
2814
|
cpuPercent,
|
|
2397
2815
|
rssBytes: mem.rss,
|
|
2398
2816
|
heapUsedBytes: mem.heapUsed,
|
|
2399
|
-
activeSessions: bridge.sessionCount,
|
|
2400
|
-
activePrompts:
|
|
2401
|
-
|
|
2817
|
+
activeSessions: workspaceRegistry.list().reduce((sum, item) => sum + item.bridge.sessionCount, 0),
|
|
2818
|
+
activePrompts: workspaceRegistry.list().reduce(
|
|
2819
|
+
(sum, item) => sum + (item.bridge.activePromptCount ?? 0),
|
|
2820
|
+
0
|
|
2821
|
+
),
|
|
2822
|
+
queuedPrompts: workspaceRegistry.list().reduce(
|
|
2823
|
+
(sum, item) => sum + (item.bridge.pendingPromptTotal ?? 0),
|
|
2824
|
+
0
|
|
2825
|
+
),
|
|
2402
2826
|
eventLoopLagP99Ms,
|
|
2403
2827
|
sseConnections: runtime.getActiveSseCount(),
|
|
2404
2828
|
wsConnections: acp?.wsStreams ?? 0,
|
|
@@ -2441,21 +2865,19 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2441
2865
|
}
|
|
2442
2866
|
};
|
|
2443
2867
|
const app2 = runtime.createServeApp(opts, () => actualPort, {
|
|
2868
|
+
workspaceRegistry,
|
|
2444
2869
|
bridge,
|
|
2445
2870
|
webShellDir,
|
|
2446
2871
|
boundWorkspace,
|
|
2447
2872
|
qwenCodeVersion: resolvedCliVersion,
|
|
2448
2873
|
startup,
|
|
2449
|
-
|
|
2450
|
-
|
|
2451
|
-
|
|
2452
|
-
|
|
2453
|
-
|
|
2454
|
-
emit: deps.fsAuditEmit,
|
|
2455
|
-
pathLocks: sharedPathLocks,
|
|
2456
|
-
...customIgnoreFiles !== void 0 ? { customIgnoreFiles } : {}
|
|
2457
|
-
}),
|
|
2874
|
+
// The real long-running daemon keeps scheduled-task sessions resident
|
|
2875
|
+
// (keepalive) and reloads them on boot (rehydration). Off by default so
|
|
2876
|
+
// direct createServeApp embeds/tests don't spawn sessions.
|
|
2877
|
+
manageScheduledTaskSessions: true,
|
|
2878
|
+
fsFactory: routeFsFactory,
|
|
2458
2879
|
primaryWorkspaceTrusted: trustedWorkspace,
|
|
2880
|
+
primaryRuntimeEnv,
|
|
2459
2881
|
daemonLog,
|
|
2460
2882
|
getChannelWorkerSnapshot,
|
|
2461
2883
|
getPerfSnapshot: /* @__PURE__ */ __name(() => ({
|
|
@@ -2472,6 +2894,7 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2472
2894
|
}
|
|
2473
2895
|
}), "getPerfSnapshot"),
|
|
2474
2896
|
getMetricsSeries: /* @__PURE__ */ __name(() => metricsRing.snapshot(), "getMetricsSeries"),
|
|
2897
|
+
getTotalSessionAdmissionSnapshot: totalSessionAdmission.snapshot,
|
|
2475
2898
|
recordDaemonRequest: /* @__PURE__ */ __name((durationMs, statusCode) => metricsRing.recordRequest(durationMs, statusCode), "recordDaemonRequest"),
|
|
2476
2899
|
workspace: workspaceService,
|
|
2477
2900
|
// Reverse tool channel (#5626): the SAME registry wired into `bridge` above,
|
|
@@ -2540,6 +2963,7 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2540
2963
|
qwenCodeVersion: cliVersion,
|
|
2541
2964
|
sessionShellCommandEnabled,
|
|
2542
2965
|
permissionPolicy,
|
|
2966
|
+
multiWorkspaceCapabilitiesRequireRuntime: workspaceInputs.length > 1,
|
|
2543
2967
|
getRuntimeError: /* @__PURE__ */ __name(() => runtimeStartupError, "getRuntimeError"),
|
|
2544
2968
|
getChannelWorkerSnapshot,
|
|
2545
2969
|
onHealthServed: deferRuntimeUntilFirstHealth ? () => startRuntimeAfterHealth?.() : void 0
|
|
@@ -2689,6 +3113,8 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2689
3113
|
}, "cancelDeferredRuntimeStartup");
|
|
2690
3114
|
const shutdownBridgeAfterFailedStartup = /* @__PURE__ */ __name(async (bridge) => {
|
|
2691
3115
|
if (!bridge || deps.bridge) return;
|
|
3116
|
+
if (shutdownBridges.has(bridge)) return;
|
|
3117
|
+
shutdownBridges.add(bridge);
|
|
2692
3118
|
try {
|
|
2693
3119
|
await bridge.shutdown();
|
|
2694
3120
|
} catch (shutdownErr) {
|
|
@@ -2729,7 +3155,10 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2729
3155
|
await stopChannelWorkerAfterFailedStartup();
|
|
2730
3156
|
disposeDaemonEventLoopMonitor();
|
|
2731
3157
|
removeCurrentServePidfile();
|
|
2732
|
-
|
|
3158
|
+
const bridgesForCleanup = bridgeForCleanup ? [bridgeForCleanup, ...getRuntimeBridgesForCleanup()] : getRuntimeBridgesForCleanup();
|
|
3159
|
+
for (const bridge of [...new Set(bridgesForCleanup)]) {
|
|
3160
|
+
await shutdownBridgeAfterFailedStartup(bridge);
|
|
3161
|
+
}
|
|
2733
3162
|
markRuntimeFailed(error);
|
|
2734
3163
|
}, "failRuntimeStartup");
|
|
2735
3164
|
const armRuntimeStartupTimer = /* @__PURE__ */ __name(() => {
|
|
@@ -2838,7 +3267,9 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2838
3267
|
daemonLog.warn(`received ${signal} during drain \u2014 forcing exit`);
|
|
2839
3268
|
try {
|
|
2840
3269
|
channelWorker.killAllSync();
|
|
2841
|
-
|
|
3270
|
+
for (const runtimeBridge of getRuntimeBridgesForCleanup()) {
|
|
3271
|
+
runtimeBridge.killAllSync();
|
|
3272
|
+
}
|
|
2842
3273
|
removeCurrentServePidfile();
|
|
2843
3274
|
} catch (err) {
|
|
2844
3275
|
daemonLog.error(
|
|
@@ -2879,6 +3310,7 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2879
3310
|
if (closePromise) return closePromise;
|
|
2880
3311
|
closePromise = new Promise((res, rej) => {
|
|
2881
3312
|
shuttingDown = true;
|
|
3313
|
+
app.locals.stopScheduledTaskKeepalive?.();
|
|
2882
3314
|
clearRuntimeStartAfterHealthTimer();
|
|
2883
3315
|
clearRuntimeStartFallbackTimer();
|
|
2884
3316
|
cancelDeferredRuntimeStartup();
|
|
@@ -2948,8 +3380,9 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
2948
3380
|
);
|
|
2949
3381
|
});
|
|
2950
3382
|
removeCurrentServePidfile();
|
|
2951
|
-
const bridgeForShutdown
|
|
2952
|
-
|
|
3383
|
+
for (const bridgeForShutdown of getRuntimeBridgesForCleanup()) {
|
|
3384
|
+
if (shutdownBridges.has(bridgeForShutdown)) continue;
|
|
3385
|
+
shutdownBridges.add(bridgeForShutdown);
|
|
2953
3386
|
await bridgeForShutdown.shutdown().catch((err) => {
|
|
2954
3387
|
daemonLog.error(
|
|
2955
3388
|
"bridge shutdown error",
|
|
@@ -3028,8 +3461,8 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
3028
3461
|
}
|
|
3029
3462
|
}, "onListening");
|
|
3030
3463
|
let server;
|
|
3464
|
+
let httpsServer;
|
|
3031
3465
|
if (tlsOptions) {
|
|
3032
|
-
let httpsServer;
|
|
3033
3466
|
try {
|
|
3034
3467
|
httpsServer = https.createServer(tlsOptions, app);
|
|
3035
3468
|
} catch (err) {
|
|
@@ -3040,14 +3473,40 @@ async function runQwenServe(optsIn, deps = {}) {
|
|
|
3040
3473
|
);
|
|
3041
3474
|
return;
|
|
3042
3475
|
}
|
|
3043
|
-
server = httpsServer.listen(opts.port, listenHostname, onListening);
|
|
3044
|
-
} else {
|
|
3045
|
-
server = app.listen(opts.port, listenHostname, onListening);
|
|
3046
3476
|
}
|
|
3047
|
-
|
|
3048
|
-
|
|
3049
|
-
|
|
3050
|
-
|
|
3477
|
+
const tryListen = /* @__PURE__ */ __name((attemptPort, attempt) => {
|
|
3478
|
+
try {
|
|
3479
|
+
if (httpsServer) {
|
|
3480
|
+
httpsServer.removeAllListeners("listening");
|
|
3481
|
+
server = httpsServer.listen(attemptPort, listenHostname, onListening);
|
|
3482
|
+
} else {
|
|
3483
|
+
server = app.listen(attemptPort, listenHostname, onListening);
|
|
3484
|
+
}
|
|
3485
|
+
} catch (err) {
|
|
3486
|
+
removeCurrentServePidfile();
|
|
3487
|
+
reject(err instanceof Error ? err : new Error(String(err)));
|
|
3488
|
+
return;
|
|
3489
|
+
}
|
|
3490
|
+
server.once("error", (err) => {
|
|
3491
|
+
server.close();
|
|
3492
|
+
const nextPort = attemptPort + 1;
|
|
3493
|
+
if (err.code === "EADDRINUSE" && opts.port !== 0 && nextPort <= 65535 && attempt < MAX_PORT_ATTEMPTS - 1) {
|
|
3494
|
+
writeStderrLine(
|
|
3495
|
+
`qwen serve: port ${attemptPort} is in use, trying ${nextPort}...`
|
|
3496
|
+
);
|
|
3497
|
+
tryListen(nextPort, attempt + 1);
|
|
3498
|
+
} else {
|
|
3499
|
+
if (err.code === "EADDRINUSE" && attempt > 0) {
|
|
3500
|
+
writeStderrLine(
|
|
3501
|
+
`qwen serve: all ports ${opts.port}\u2013${attemptPort} are in use`
|
|
3502
|
+
);
|
|
3503
|
+
}
|
|
3504
|
+
removeCurrentServePidfile();
|
|
3505
|
+
reject(err);
|
|
3506
|
+
}
|
|
3507
|
+
});
|
|
3508
|
+
}, "tryListen");
|
|
3509
|
+
tryListen(opts.port, 0);
|
|
3051
3510
|
});
|
|
3052
3511
|
}
|
|
3053
3512
|
__name(runQwenServe, "runQwenServe");
|