@rubytech/create-maxy-code 0.1.316 → 0.1.318
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/package.json +2 -2
- package/payload/platform/lib/mcp-eager/dist/index.d.ts +0 -20
- package/payload/platform/lib/mcp-eager/dist/index.d.ts.map +1 -1
- package/payload/platform/lib/mcp-eager/dist/index.js +2 -1
- package/payload/platform/lib/mcp-eager/dist/index.js.map +1 -1
- package/payload/platform/lib/mcp-eager/src/index.ts +3 -1
- package/payload/platform/lib/mcp-lifeline/dist/index.d.ts +8 -0
- package/payload/platform/lib/mcp-lifeline/dist/index.d.ts.map +1 -0
- package/payload/platform/lib/mcp-lifeline/dist/index.js +71 -0
- package/payload/platform/lib/mcp-lifeline/dist/index.js.map +1 -0
- package/payload/platform/lib/mcp-lifeline/package.json +7 -0
- package/payload/platform/lib/mcp-lifeline/src/__tests__/lifeline.test.ts +146 -0
- package/payload/platform/lib/mcp-lifeline/src/index.ts +78 -0
- package/payload/platform/lib/mcp-lifeline/tsconfig.json +9 -0
- package/payload/platform/lib/mcp-lifeline/vitest.config.ts +9 -0
- package/payload/platform/lib/models/dist/index.d.ts +8 -0
- package/payload/platform/lib/models/dist/index.d.ts.map +1 -1
- package/payload/platform/lib/models/dist/index.js +20 -1
- package/payload/platform/lib/models/dist/index.js.map +1 -1
- package/payload/platform/lib/models/src/index.ts +22 -0
- package/payload/platform/package.json +5 -2
- package/payload/platform/plugins/admin/mcp/dist/index.js +11 -10
- package/payload/platform/plugins/admin/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/admin/skills/platform-architecture/SKILL.md +19 -10
- package/payload/platform/plugins/docs/references/admin-ui.md +4 -2
- package/payload/platform/plugins/docs/references/internals.md +14 -7
- package/payload/platform/plugins/memory/mcp/dist/index.js +32 -31
- package/payload/platform/plugins/memory/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/outlook/mcp/dist/index.js +8 -7
- package/payload/platform/plugins/outlook/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/quickbooks/mcp/dist/index.js +12 -11
- package/payload/platform/plugins/quickbooks/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/replicate/mcp/dist/index.js +4 -3
- package/payload/platform/plugins/replicate/mcp/dist/index.js.map +1 -1
- package/payload/platform/plugins/whatsapp/mcp/dist/index.js +11 -10
- package/payload/platform/plugins/whatsapp/mcp/dist/index.js.map +1 -1
- package/payload/platform/scripts/__tests__/check-no-raw-mcp-registrations.test.sh +57 -0
- package/payload/platform/scripts/check-no-raw-mcp-registrations.mjs +70 -0
- package/payload/platform/services/claude-session-manager/dist/http-server.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/http-server.js +57 -9
- package/payload/platform/services/claude-session-manager/dist/http-server.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.d.ts +5 -0
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.js +7 -0
- package/payload/platform/services/claude-session-manager/dist/pty-spawner.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js +3 -12
- package/payload/platform/services/claude-session-manager/dist/rc-daemon.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/session-sidecar.d.ts +8 -0
- package/payload/platform/services/claude-session-manager/dist/session-sidecar.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/session-sidecar.js +9 -0
- package/payload/platform/services/claude-session-manager/dist/session-sidecar.js.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/system-prompt.d.ts +5 -0
- package/payload/platform/services/claude-session-manager/dist/system-prompt.d.ts.map +1 -1
- package/payload/platform/services/claude-session-manager/dist/system-prompt.js +15 -0
- package/payload/platform/services/claude-session-manager/dist/system-prompt.js.map +1 -1
- package/payload/premium-plugins/writer-craft/lib/mcp-lifeline/dist/index.d.ts +8 -0
- package/payload/premium-plugins/writer-craft/lib/mcp-lifeline/dist/index.d.ts.map +1 -0
- package/payload/premium-plugins/writer-craft/lib/mcp-lifeline/dist/index.js +71 -0
- package/payload/premium-plugins/writer-craft/lib/mcp-lifeline/dist/index.js.map +1 -0
- package/payload/premium-plugins/writer-craft/lib/mcp-lifeline/package.json +7 -0
- package/payload/premium-plugins/writer-craft/mcp/dist/index.d.ts.map +1 -1
- package/payload/premium-plugins/writer-craft/mcp/dist/index.js +6 -5
- package/payload/premium-plugins/writer-craft/mcp/dist/index.js.map +1 -1
- package/payload/premium-plugins/writer-craft/mcp/src/index.ts +6 -5
- package/payload/server/{chunk-Q7EWROVN.js → chunk-NCRJQEZ3.js} +0 -101
- package/payload/server/maxy-edge.js +1 -1
- package/payload/server/public/assets/AdminLoginScreens-CrdmA3KA.js +1 -0
- package/payload/server/public/assets/AdminShell-0meAFBva.js +1 -0
- package/payload/server/public/assets/Checkbox-DXisJRUK.js +1 -0
- package/payload/server/public/assets/OperatorConversations-DBy2G8q3.js +9 -0
- package/payload/server/public/assets/OperatorConversations-DvRXfq3q.css +1 -0
- package/payload/server/public/assets/admin-DX5lZxWt.js +1 -0
- package/payload/server/public/assets/{arc-J2g2u5Xv.js → arc-CxLB9WCE.js} +1 -1
- package/payload/server/public/assets/architecture-YZFGNWBL-DN-MYxff.js +1 -0
- package/payload/server/public/assets/{architectureDiagram-Q4EWVU46-CN0BXxpE.js → architectureDiagram-Q4EWVU46-D-EdJPSY.js} +1 -1
- package/payload/server/public/assets/{blockDiagram-DXYQGD6D-HX-8wF2p.js → blockDiagram-DXYQGD6D-CXx9RgCm.js} +1 -1
- package/payload/server/public/assets/browser-Bxx8w8BA.js +1 -0
- package/payload/server/public/assets/{c4Diagram-AHTNJAMY-wIuarKF5.js → c4Diagram-AHTNJAMY-RFBXEe0B.js} +1 -1
- package/payload/server/public/assets/channel-y27xl53N.js +1 -0
- package/payload/server/public/assets/chat-CT9YrNtI.js +1 -0
- package/payload/server/public/assets/{chunk-2KRD3SAO-Buz7egJZ.js → chunk-2KRD3SAO-DBqAFwK9.js} +1 -1
- package/payload/server/public/assets/{chunk-336JU56O-_JcFXJqc.js → chunk-336JU56O-DdnFEz6R.js} +2 -2
- package/payload/server/public/assets/chunk-426QAEUC-D8Iwaegm.js +1 -0
- package/payload/server/public/assets/{chunk-4BX2VUAB-DUR5Dg3M.js → chunk-4BX2VUAB-cnw-3Gbs.js} +1 -1
- package/payload/server/public/assets/{chunk-4TB4RGXK-BRIqQ9st.js → chunk-4TB4RGXK-BnqJ0bDc.js} +1 -1
- package/payload/server/public/assets/{chunk-55IACEB6-CezTHWXL.js → chunk-55IACEB6-BwyHvvzo.js} +1 -1
- package/payload/server/public/assets/{chunk-5FUZZQ4R-DHYUPzF1.js → chunk-5FUZZQ4R-DXA9U02I.js} +1 -1
- package/payload/server/public/assets/{chunk-5PVQY5BW-BVn4_fI5.js → chunk-5PVQY5BW-D78bZ_8D.js} +1 -1
- package/payload/server/public/assets/{chunk-67CJDMHE-BBLA8Mbi.js → chunk-67CJDMHE-CtE_Mgv7.js} +1 -1
- package/payload/server/public/assets/{chunk-7N4EOEYR-CdWfEI5c.js → chunk-7N4EOEYR-CUZDaySl.js} +1 -1
- package/payload/server/public/assets/{chunk-AA7GKIK3-tS11knCR.js → chunk-AA7GKIK3-CYQ3jO4X.js} +1 -1
- package/payload/server/public/assets/{chunk-BSJP7CBP-GEu1OOZ6.js → chunk-BSJP7CBP-BbA_HyTR.js} +1 -1
- package/payload/server/public/assets/{chunk-CIAEETIT-DKrNbbp_.js → chunk-CIAEETIT-D7_YqRhG.js} +1 -1
- package/payload/server/public/assets/{chunk-EDXVE4YY-B0InXNyr.js → chunk-EDXVE4YY-B23LrtSw.js} +1 -1
- package/payload/server/public/assets/{chunk-ENJZ2VHE-CO7lkHdm.js → chunk-ENJZ2VHE-D3fTHYKN.js} +1 -1
- package/payload/server/public/assets/{chunk-FMBD7UC4-CMj74lWo.js → chunk-FMBD7UC4-DFAA2tyh.js} +1 -1
- package/payload/server/public/assets/{chunk-FOC6F5B3-CLnKQoXw.js → chunk-FOC6F5B3-BF4IHvlI.js} +1 -1
- package/payload/server/public/assets/{chunk-ICPOFSXX-CdiEKIaz.js → chunk-ICPOFSXX-DBUGemHy.js} +2 -2
- package/payload/server/public/assets/{chunk-K5T4RW27-B6LA3fiv.js → chunk-K5T4RW27-rMMs08Eh.js} +1 -1
- package/payload/server/public/assets/{chunk-KGLVRYIC-DrhRrb8Q.js → chunk-KGLVRYIC-BD2r8R2G.js} +1 -1
- package/payload/server/public/assets/{chunk-LIHQZDEY-DVQukevB.js → chunk-LIHQZDEY-D4sYTTwM.js} +1 -1
- package/payload/server/public/assets/{chunk-ORNJ4GCN-ZMLkoDhP.js → chunk-ORNJ4GCN-CAs_uFzb.js} +1 -1
- package/payload/server/public/assets/{chunk-OYMX7WX6-C0dJkynG.js → chunk-OYMX7WX6-Fkp-2ORc.js} +1 -1
- package/payload/server/public/assets/chunk-QZHKN3VN-qHqDpwz3.js +1 -0
- package/payload/server/public/assets/{chunk-U2HBQHQK-BQ9BPIFZ.js → chunk-U2HBQHQK-D_pxZh25.js} +1 -1
- package/payload/server/public/assets/{chunk-X2U36JSP-CAonGMOd.js → chunk-X2U36JSP-CeVmvvRf.js} +1 -1
- package/payload/server/public/assets/{chunk-XPW4576I-D5C_WNlk.js → chunk-XPW4576I-iWP54fKp.js} +1 -1
- package/payload/server/public/assets/{chunk-YZCP3GAM-Ecdvzekb.js → chunk-YZCP3GAM-CNtbWJNN.js} +1 -1
- package/payload/server/public/assets/{chunk-ZZ45TVLE-BsFZd1cN.js → chunk-ZZ45TVLE-BmlFjU_9.js} +1 -1
- package/payload/server/public/assets/classDiagram-6PBFFD2Q-DgVoYWhO.js +1 -0
- package/payload/server/public/assets/classDiagram-v2-HSJHXN6E-C0WNP3uN.js +1 -0
- package/payload/server/public/assets/clone-D50F_pvg.js +1 -0
- package/payload/server/public/assets/{cose-bilkent-S5V4N54A-DBWHaIwm.js → cose-bilkent-S5V4N54A-C7YmF1Pg.js} +1 -1
- package/payload/server/public/assets/{dagre-Dr7ZJYeS.js → dagre-BAmiDDtR.js} +1 -1
- package/payload/server/public/assets/{dagre-KV5264BT-oIJddk7m.js → dagre-KV5264BT-Ca3ESJhc.js} +1 -1
- package/payload/server/public/assets/data-B9NtsXgF.js +1 -0
- package/payload/server/public/assets/{diagram-5BDNPKRD-CEVxqOZ4.js → diagram-5BDNPKRD-BgT1ORf2.js} +1 -1
- package/payload/server/public/assets/{diagram-G4DWMVQ6-BovF7Rjx.js → diagram-G4DWMVQ6-BTaUIiem.js} +1 -1
- package/payload/server/public/assets/{diagram-MMDJMWI5-BhrF8zoF.js → diagram-MMDJMWI5-Bdb2g6Uo.js} +1 -1
- package/payload/server/public/assets/{diagram-TYMM5635-DCUYwxtR.js → diagram-TYMM5635-CkLGC0zZ.js} +1 -1
- package/payload/server/public/assets/{dist-DSsFp0Qd.js → dist-Bkbhs3jw.js} +1 -1
- package/payload/server/public/assets/{erDiagram-SMLLAGMA-BS2-HdCg.js → erDiagram-SMLLAGMA-D_sj4DMg.js} +1 -1
- package/payload/server/public/assets/{flatten-BZMXCpLh.js → flatten-E2Sr0FeD.js} +1 -1
- package/payload/server/public/assets/{flowDiagram-DWJPFMVM-BzSFLoea.js → flowDiagram-DWJPFMVM-iLERoZTe.js} +1 -1
- package/payload/server/public/assets/{ganttDiagram-T4ZO3ILL-1-3QU7mT.js → ganttDiagram-T4ZO3ILL-D60hjMBy.js} +1 -1
- package/payload/server/public/assets/gitGraph-7Q5UKJZL-D-L2yzYf.js +1 -0
- package/payload/server/public/assets/{gitGraphDiagram-UUTBAWPF-fTrJ35Wk.js → gitGraphDiagram-UUTBAWPF-Di0XM6fi.js} +1 -1
- package/payload/server/public/assets/{graph-BZNc3EXa.js → graph-B59N222f.js} +3 -3
- package/payload/server/public/assets/graph-labels-70w-1ov0.js +1 -0
- package/payload/server/public/assets/{graphlib-rlEzI2qD.js → graphlib-C8fUP7uV.js} +1 -1
- package/payload/server/public/assets/info-OMHHGYJF-BQn6jndO.js +1 -0
- package/payload/server/public/assets/infoDiagram-42DDH7IO-BwMdbiXg.js +2 -0
- package/payload/server/public/assets/{isEmpty-DaYIrHay.js → isEmpty-CLz-UprQ.js} +1 -1
- package/payload/server/public/assets/{ishikawaDiagram-UXIWVN3A-0eU_UtlT.js → ishikawaDiagram-UXIWVN3A-CwgI4B5Z.js} +1 -1
- package/payload/server/public/assets/{journeyDiagram-VCZTEJTY-BKLeZohp.js → journeyDiagram-VCZTEJTY-CxBu-tze.js} +1 -1
- package/payload/server/public/assets/{kanban-definition-6JOO6SKY-Dq72xyaN.js → kanban-definition-6JOO6SKY-D2qlheA5.js} +1 -1
- package/payload/server/public/assets/{line-LQhmDT8k.js → line-Bdod7uzQ.js} +1 -1
- package/payload/server/public/assets/{linear-BGotDbGs.js → linear-BiVe6QzC.js} +1 -1
- package/payload/server/public/assets/{mermaid-parser.core-DoLdho1V.js → mermaid-parser.core-xZN7hC6M.js} +2 -2
- package/payload/server/public/assets/{mermaid.core-C1RRyHGm.js → mermaid.core-D0IylAac.js} +3 -3
- package/payload/server/public/assets/{mindmap-definition-QFDTVHPH-vUVVVyV1.js → mindmap-definition-QFDTVHPH-J_Szhwf1.js} +1 -1
- package/payload/server/public/assets/operator-DpRAhwQN.js +1 -0
- package/payload/server/public/assets/{ordinal-BqEhkPyh.js → ordinal-5RtyPJVt.js} +1 -1
- package/payload/server/public/assets/packet-4T2RLAQJ-DmkQBx4h.js +1 -0
- package/payload/server/public/assets/page-Ehjc9b9V.js +30 -0
- package/payload/server/public/assets/pie-ZZUOXDRM-DDnxYUBm.js +1 -0
- package/payload/server/public/assets/{pieDiagram-DEJITSTG-B9Pl6Qhc.js → pieDiagram-DEJITSTG-CV5DxUVx.js} +1 -1
- package/payload/server/public/assets/public-BcqXGSaE.js +1 -0
- package/payload/server/public/assets/{quadrantDiagram-34T5L4WZ-Drn9T81A.js → quadrantDiagram-34T5L4WZ-BsFMVizF.js} +1 -1
- package/payload/server/public/assets/radar-PYXPWWZC-7H4k0ChM.js +1 -0
- package/payload/server/public/assets/{reduce-T2IuntYP.js → reduce-B3Mw_0s1.js} +1 -1
- package/payload/server/public/assets/{requirementDiagram-MS252O5E-C0PAItJm.js → requirementDiagram-MS252O5E-C5eRRvGc.js} +1 -1
- package/payload/server/public/assets/{sankeyDiagram-XADWPNL6-BR42Mtwd.js → sankeyDiagram-XADWPNL6-CJYv5gpw.js} +1 -1
- package/payload/server/public/assets/{sequenceDiagram-FGHM5R23-c2lR9UOS.js → sequenceDiagram-FGHM5R23-B25563_2.js} +1 -1
- package/payload/server/public/assets/{src-DXUM2BJo.js → src-BKOAoFQc.js} +1 -1
- package/payload/server/public/assets/{stateDiagram-FHFEXIEX-BcHhtqsZ.js → stateDiagram-FHFEXIEX-BLyNJYOA.js} +1 -1
- package/payload/server/public/assets/stateDiagram-v2-QKLJ7IA2-BSVuxZxz.js +1 -0
- package/payload/server/public/assets/{timeline-definition-GMOUNBTQ-Ax32c10H.js → timeline-definition-GMOUNBTQ-D-HgOM6Q.js} +1 -1
- package/payload/server/public/assets/treeView-SZITEDCU-BLXWTQtW.js +1 -0
- package/payload/server/public/assets/treemap-W4RFUUIX-DiePDF5d.js +1 -0
- package/payload/server/public/assets/{vennDiagram-DHZGUBPP-BxePewPq.js → vennDiagram-DHZGUBPP-Cw1JElYp.js} +1 -1
- package/payload/server/public/assets/wardley-RL74JXVD-OSUWK5LN.js +1 -0
- package/payload/server/public/assets/{wardleyDiagram-NUSXRM2D-DmJwZ2f5.js → wardleyDiagram-NUSXRM2D-BqMWzEko.js} +1 -1
- package/payload/server/public/assets/{xychartDiagram-5P7HB3ND-YjHomudv.js → xychartDiagram-5P7HB3ND-DBp71TLT.js} +1 -1
- package/payload/server/public/browser.html +5 -8
- package/payload/server/public/chat.html +8 -12
- package/payload/server/public/data.html +5 -7
- package/payload/server/public/graph.html +7 -10
- package/payload/server/public/index.html +8 -11
- package/payload/server/public/operator.html +10 -14
- package/payload/server/public/public.html +8 -10
- package/payload/server/server.js +276 -219
- package/payload/server/public/assets/AccessGate-bu988Xo-.js +0 -1
- package/payload/server/public/assets/AdminLoginScreens-BCYaOOuk.js +0 -1
- package/payload/server/public/assets/AdminShell-DSjJ4Biu.js +0 -1
- package/payload/server/public/assets/Checkbox-B4Dbvjls.js +0 -1
- package/payload/server/public/assets/OperatorConversations-XsXP7-P-.js +0 -1
- package/payload/server/public/assets/OperatorConversations-qc_xy7Az.css +0 -1
- package/payload/server/public/assets/admin-m0797WGA.js +0 -1
- package/payload/server/public/assets/architecture-YZFGNWBL-C6nkAxzW.js +0 -1
- package/payload/server/public/assets/audio-attachment-mime-Jm4KJ4YC.js +0 -30
- package/payload/server/public/assets/brand-D8LClgr_.js +0 -9
- package/payload/server/public/assets/brand-DvttVeGB.css +0 -1
- package/payload/server/public/assets/browser-CBjNMPsz.js +0 -1
- package/payload/server/public/assets/channel-Q39xIXyT.js +0 -1
- package/payload/server/public/assets/chat-Sg-RGuV6.js +0 -1
- package/payload/server/public/assets/chunk-426QAEUC-CCYjp9C2.js +0 -1
- package/payload/server/public/assets/chunk-QZHKN3VN-BNBxnHZh.js +0 -1
- package/payload/server/public/assets/classDiagram-6PBFFD2Q-BShusfby.js +0 -1
- package/payload/server/public/assets/classDiagram-v2-HSJHXN6E-D4ivPLFF.js +0 -1
- package/payload/server/public/assets/clone-CjEM8LwB.js +0 -1
- package/payload/server/public/assets/data-CEqE4BDw.js +0 -1
- package/payload/server/public/assets/gitGraph-7Q5UKJZL-Btp3PwZh.js +0 -1
- package/payload/server/public/assets/graph-labels-Bj5yM9bI.js +0 -1
- package/payload/server/public/assets/info-OMHHGYJF-CPt2y6_L.js +0 -1
- package/payload/server/public/assets/infoDiagram-42DDH7IO-CpXNTMgd.js +0 -2
- package/payload/server/public/assets/inter-cyrillic-400-normal-HOLc17fK.woff +0 -0
- package/payload/server/public/assets/inter-cyrillic-400-normal-obahsSVq.woff2 +0 -0
- package/payload/server/public/assets/inter-cyrillic-500-normal-BasfLYem.woff2 +0 -0
- package/payload/server/public/assets/inter-cyrillic-500-normal-CxZf_p3X.woff +0 -0
- package/payload/server/public/assets/inter-cyrillic-ext-400-normal-BQZuk6qB.woff2 +0 -0
- package/payload/server/public/assets/inter-cyrillic-ext-400-normal-DQukG94-.woff +0 -0
- package/payload/server/public/assets/inter-cyrillic-ext-500-normal-B0yAr1jD.woff2 +0 -0
- package/payload/server/public/assets/inter-cyrillic-ext-500-normal-BmqWE9Dz.woff +0 -0
- package/payload/server/public/assets/inter-greek-400-normal-B4URO6DV.woff2 +0 -0
- package/payload/server/public/assets/inter-greek-400-normal-q2sYcFCs.woff +0 -0
- package/payload/server/public/assets/inter-greek-500-normal-BIZE56-Y.woff2 +0 -0
- package/payload/server/public/assets/inter-greek-500-normal-Xzm54t5V.woff +0 -0
- package/payload/server/public/assets/inter-greek-ext-400-normal-DGGRlc-M.woff2 +0 -0
- package/payload/server/public/assets/inter-greek-ext-400-normal-KugGGMne.woff +0 -0
- package/payload/server/public/assets/inter-greek-ext-500-normal-2j5mBUwD.woff +0 -0
- package/payload/server/public/assets/inter-greek-ext-500-normal-C4iEst2y.woff2 +0 -0
- package/payload/server/public/assets/inter-latin-400-normal-C38fXH4l.woff2 +0 -0
- package/payload/server/public/assets/inter-latin-400-normal-CyCys3Eg.woff +0 -0
- package/payload/server/public/assets/inter-latin-500-normal-BL9OpVg8.woff +0 -0
- package/payload/server/public/assets/inter-latin-500-normal-Cerq10X2.woff2 +0 -0
- package/payload/server/public/assets/inter-latin-ext-400-normal-77YHD8bZ.woff +0 -0
- package/payload/server/public/assets/inter-latin-ext-400-normal-C1nco2VV.woff2 +0 -0
- package/payload/server/public/assets/inter-latin-ext-500-normal-BxGbmqWO.woff +0 -0
- package/payload/server/public/assets/inter-latin-ext-500-normal-CV4jyFjo.woff2 +0 -0
- package/payload/server/public/assets/inter-vietnamese-400-normal-Bbgyi5SW.woff +0 -0
- package/payload/server/public/assets/inter-vietnamese-400-normal-DMkecbls.woff2 +0 -0
- package/payload/server/public/assets/inter-vietnamese-500-normal-DOriooB6.woff2 +0 -0
- package/payload/server/public/assets/inter-vietnamese-500-normal-mJboJaSs.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-300-normal-AOSWdb_s.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-300-normal-FGBQ0wlI.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-400-normal-BFBkh4jY.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-400-normal-gRTjlS2D.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-500-normal-B66TYsaK.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-500-normal-DFwuUcdu.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-300-normal-CFtw49Zd.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-300-normal-DRMzurxT.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-400-normal-DYA1XoQK.woff +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-400-normal-svq1FPys.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-500-normal-BNHmvKvI.woff2 +0 -0
- package/payload/server/public/assets/newsreader-latin-ext-500-normal-CZruMFou.woff +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-300-normal-CsrIkm-V.woff +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-300-normal-D3VHEe81.woff2 +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-400-normal-BekUZro8.woff +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-400-normal-DdKr49mV.woff2 +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-500-normal-BEAbKU8A.woff +0 -0
- package/payload/server/public/assets/newsreader-vietnamese-500-normal-CL6a8tp2.woff2 +0 -0
- package/payload/server/public/assets/operator-Bph7mx87.js +0 -1
- package/payload/server/public/assets/packet-4T2RLAQJ-Cwc-j_AI.js +0 -1
- package/payload/server/public/assets/page-CtWCeXdg.js +0 -1
- package/payload/server/public/assets/pie-ZZUOXDRM-BZ9fjD1_.js +0 -1
- package/payload/server/public/assets/public-gxHCJCs3.js +0 -6
- package/payload/server/public/assets/public-next-C3clISGQ.js +0 -1
- package/payload/server/public/assets/public-vnj7OhQj.css +0 -1
- package/payload/server/public/assets/radar-PYXPWWZC-BNz5Rt9V.js +0 -1
- package/payload/server/public/assets/stateDiagram-v2-QKLJ7IA2-BUQ_F4eP.js +0 -1
- package/payload/server/public/assets/treeView-SZITEDCU-DcVCQgp1.js +0 -1
- package/payload/server/public/assets/treemap-W4RFUUIX-Bm12mwGd.js +0 -1
- package/payload/server/public/assets/useSelectionMode-BMn70cch.js +0 -5
- package/payload/server/public/assets/wardley-RL74JXVD-47Z3ymtK.js +0 -1
- package/payload/server/public/public-next.html +0 -25
- /package/payload/server/public/assets/{_baseFor-Y5mTRiRv.js → _baseFor-DVaNaTfF.js} +0 -0
- /package/payload/server/public/assets/{admin-types-D2qTXuCg.js → admin-types-CJrGd46U.js} +0 -0
- /package/payload/server/public/assets/{array-BwJyW1Dp.js → array-8_H1156C.js} +0 -0
- /package/payload/server/public/assets/{chunk-CAM3fms7.js → chunk-Pqm5yXtL.js} +0 -0
- /package/payload/server/public/assets/{cytoscape.esm-D95TtHqz.js → cytoscape.esm-h10p_6j-.js} +0 -0
- /package/payload/server/public/assets/{defaultLocale-kiwRz9Au.js → defaultLocale-pD7tFa1r.js} +0 -0
- /package/payload/server/public/assets/{init-CKZirZ49.js → init-CwJ4b81e.js} +0 -0
- /package/payload/server/public/assets/{katex-8mXVa4k3.js → katex-DJPjIBAI.js} +0 -0
- /package/payload/server/public/assets/{path-B0d9ncVi.js → path-CK8wrAxY.js} +0 -0
- /package/payload/server/public/assets/{preload-helper-C5gCWwwF.js → preload-helper-Bf_JiD2A.js} +0 -0
- /package/payload/server/public/assets/{rough.esm-BWqoIFNR.js → rough.esm-Dwml_la6.js} +0 -0
package/payload/server/server.js
CHANGED
|
@@ -27,9 +27,7 @@ import {
|
|
|
27
27
|
WEBSOCKIFY_PORT,
|
|
28
28
|
accessPasswordCollides,
|
|
29
29
|
autoDeliverPremiumPlugins,
|
|
30
|
-
bindVisitorToGroup,
|
|
31
30
|
canAccessAdmin,
|
|
32
|
-
checkGroupMembership,
|
|
33
31
|
checkRateLimit,
|
|
34
32
|
classifyHost,
|
|
35
33
|
cleanupLeakedPremiumSubs,
|
|
@@ -42,7 +40,6 @@ import {
|
|
|
42
40
|
emitMissingOnResolve,
|
|
43
41
|
ensureConversation,
|
|
44
42
|
fetchBranding,
|
|
45
|
-
findGroupBySlug,
|
|
46
43
|
findMissingPlugins,
|
|
47
44
|
findRecentConversation,
|
|
48
45
|
fingerprintSessionKey,
|
|
@@ -50,7 +47,6 @@ import {
|
|
|
50
47
|
getAgentSessionIdForConversation,
|
|
51
48
|
getConversationClaudeSessionIds,
|
|
52
49
|
getDefaultAccountId,
|
|
53
|
-
getGroupParticipants,
|
|
54
50
|
getOperatorDomains,
|
|
55
51
|
getRecentMessages,
|
|
56
52
|
getRoleForSession,
|
|
@@ -110,7 +106,7 @@ import {
|
|
|
110
106
|
vncLog,
|
|
111
107
|
walkPremiumBundles,
|
|
112
108
|
writeAdminUserAndPerson
|
|
113
|
-
} from "./chunk-
|
|
109
|
+
} from "./chunk-NCRJQEZ3.js";
|
|
114
110
|
import {
|
|
115
111
|
__commonJS,
|
|
116
112
|
__toESM
|
|
@@ -532,63 +528,63 @@ var require_dist2 = __commonJS({
|
|
|
532
528
|
}
|
|
533
529
|
function pickShortLabel(node) {
|
|
534
530
|
const props = node.properties;
|
|
535
|
-
const
|
|
536
|
-
if (
|
|
531
|
+
const primaryLabel2 = node.labels[0];
|
|
532
|
+
if (primaryLabel2 === "ToolCall") {
|
|
537
533
|
const v = props.toolName;
|
|
538
534
|
if (typeof v === "string" && v.length > 0) {
|
|
539
535
|
return v.length > 24 ? v.slice(0, 24) + "\u2026" : v;
|
|
540
536
|
}
|
|
541
|
-
} else if (
|
|
537
|
+
} else if (primaryLabel2 === "WorkflowRun") {
|
|
542
538
|
const v = props.startedAt;
|
|
543
539
|
if (typeof v === "string" && v.length > 0) {
|
|
544
540
|
const ts = formatRunTimestamp(v);
|
|
545
541
|
if (ts)
|
|
546
542
|
return ts;
|
|
547
543
|
}
|
|
548
|
-
} else if (
|
|
544
|
+
} else if (primaryLabel2 === "WorkflowStep") {
|
|
549
545
|
const v = props.label;
|
|
550
546
|
if (typeof v === "string" && v.length > 0) {
|
|
551
547
|
return v.length > 24 ? v.slice(0, 24) + "\u2026" : v;
|
|
552
548
|
}
|
|
553
|
-
} else if (
|
|
549
|
+
} else if (primaryLabel2 === "Person") {
|
|
554
550
|
const given = typeof props.givenName === "string" ? props.givenName : "";
|
|
555
551
|
const family = typeof props.familyName === "string" ? props.familyName : "";
|
|
556
552
|
const full = [given, family].filter((s) => s.length > 0).join(" ");
|
|
557
553
|
if (full.length > 0) {
|
|
558
554
|
return full.length > 24 ? full.slice(0, 24) + "\u2026" : full;
|
|
559
555
|
}
|
|
560
|
-
} else if (
|
|
556
|
+
} else if (primaryLabel2 === "Agent") {
|
|
561
557
|
const dn = typeof props.displayName === "string" ? props.displayName : "";
|
|
562
558
|
const slug = typeof props.slug === "string" ? props.slug : "";
|
|
563
559
|
const v = dn.length > 0 ? dn : slug;
|
|
564
560
|
if (v.length > 0) {
|
|
565
561
|
return v.length > 24 ? v.slice(0, 24) + "\u2026" : v;
|
|
566
562
|
}
|
|
567
|
-
} else if (
|
|
563
|
+
} else if (primaryLabel2 === "Job") {
|
|
568
564
|
const client = typeof props.client === "string" ? props.client : "";
|
|
569
565
|
const jobId = typeof props.jobId === "string" ? props.jobId : "";
|
|
570
566
|
const composed = [client, jobId.length > 0 ? `#${jobId}` : ""].filter((s) => s.length > 0).join(" ");
|
|
571
567
|
if (composed.length > 0) {
|
|
572
568
|
return composed.length > 24 ? composed.slice(0, 24) + "\u2026" : composed;
|
|
573
569
|
}
|
|
574
|
-
} else if (
|
|
570
|
+
} else if (primaryLabel2 === "QuoteDocument") {
|
|
575
571
|
const ref = typeof props.ref === "string" ? props.ref : "";
|
|
576
572
|
if (ref.length > 0) {
|
|
577
573
|
return ref.length > 24 ? ref.slice(0, 24) + "\u2026" : ref;
|
|
578
574
|
}
|
|
579
|
-
} else if (
|
|
575
|
+
} else if (primaryLabel2 === "InboundInvoice") {
|
|
580
576
|
const supplier = typeof props.supplier === "string" ? props.supplier : "";
|
|
581
577
|
const conf = typeof props.confirmationNumber === "string" ? props.confirmationNumber : "";
|
|
582
578
|
const composed = [supplier, conf.length > 0 ? `#${conf}` : ""].filter((s) => s.length > 0).join(" ");
|
|
583
579
|
if (composed.length > 0) {
|
|
584
580
|
return composed.length > 24 ? composed.slice(0, 24) + "\u2026" : composed;
|
|
585
581
|
}
|
|
586
|
-
} else if (
|
|
582
|
+
} else if (primaryLabel2 === "WhatsAppGroup") {
|
|
587
583
|
const clientName = typeof props.clientName === "string" ? props.clientName : "";
|
|
588
584
|
if (clientName.length > 0) {
|
|
589
585
|
return clientName.length > 24 ? clientName.slice(0, 24) + "\u2026" : clientName;
|
|
590
586
|
}
|
|
591
|
-
} else if (
|
|
587
|
+
} else if (primaryLabel2 === "Message") {
|
|
592
588
|
const role = typeof props.role === "string" ? props.role : "";
|
|
593
589
|
const roleShort = role === "user" ? "user" : role === "assistant" ? "asst" : role === "system" ? "sys" : role === "tool" ? "tool" : null;
|
|
594
590
|
const createdAt = typeof props.createdAt === "string" ? props.createdAt : "";
|
|
@@ -604,60 +600,60 @@ var require_dist2 = __commonJS({
|
|
|
604
600
|
return v.length > 24 ? v.slice(0, 24) + "\u2026" : v;
|
|
605
601
|
}
|
|
606
602
|
}
|
|
607
|
-
if (
|
|
603
|
+
if (primaryLabel2 === "Conversation") {
|
|
608
604
|
const id = typeof props.sessionId === "string" ? props.sessionId : null;
|
|
609
605
|
if (id)
|
|
610
606
|
return `Conv ${id.slice(0, 8)}`;
|
|
611
607
|
}
|
|
612
|
-
return
|
|
608
|
+
return primaryLabel2 ?? "\u2026";
|
|
613
609
|
}
|
|
614
610
|
function pickDisplayName(node) {
|
|
615
611
|
const props = node.properties;
|
|
616
|
-
const
|
|
617
|
-
if (
|
|
612
|
+
const primaryLabel2 = node.labels[0];
|
|
613
|
+
if (primaryLabel2 === "ToolCall") {
|
|
618
614
|
const v = props.toolName;
|
|
619
615
|
if (typeof v === "string" && v.length > 0)
|
|
620
616
|
return v;
|
|
621
|
-
} else if (
|
|
617
|
+
} else if (primaryLabel2 === "WorkflowRun") {
|
|
622
618
|
const v = props.startedAt;
|
|
623
619
|
if (typeof v === "string" && v.length > 0) {
|
|
624
620
|
const ts = formatRunTimestamp(v);
|
|
625
621
|
if (ts)
|
|
626
622
|
return ts;
|
|
627
623
|
}
|
|
628
|
-
} else if (
|
|
624
|
+
} else if (primaryLabel2 === "WorkflowStep") {
|
|
629
625
|
const v = props.label;
|
|
630
626
|
if (typeof v === "string" && v.length > 0)
|
|
631
627
|
return v;
|
|
632
|
-
} else if (
|
|
628
|
+
} else if (primaryLabel2 === "Person") {
|
|
633
629
|
const given = typeof props.givenName === "string" ? props.givenName : "";
|
|
634
630
|
const family = typeof props.familyName === "string" ? props.familyName : "";
|
|
635
631
|
const full = [given, family].filter((s) => s.length > 0).join(" ");
|
|
636
632
|
if (full.length > 0)
|
|
637
633
|
return full;
|
|
638
|
-
} else if (
|
|
634
|
+
} else if (primaryLabel2 === "Agent") {
|
|
639
635
|
const dn = typeof props.displayName === "string" ? props.displayName : "";
|
|
640
636
|
const slug = typeof props.slug === "string" ? props.slug : "";
|
|
641
637
|
const v = dn.length > 0 ? dn : slug;
|
|
642
638
|
if (v.length > 0)
|
|
643
639
|
return v;
|
|
644
|
-
} else if (
|
|
640
|
+
} else if (primaryLabel2 === "Job") {
|
|
645
641
|
const client = typeof props.client === "string" ? props.client : "";
|
|
646
642
|
const jobId = typeof props.jobId === "string" ? props.jobId : "";
|
|
647
643
|
const composed = [client, jobId.length > 0 ? `#${jobId}` : ""].filter((s) => s.length > 0).join(" ");
|
|
648
644
|
if (composed.length > 0)
|
|
649
645
|
return composed;
|
|
650
|
-
} else if (
|
|
646
|
+
} else if (primaryLabel2 === "QuoteDocument") {
|
|
651
647
|
const ref = typeof props.ref === "string" ? props.ref : "";
|
|
652
648
|
if (ref.length > 0)
|
|
653
649
|
return ref;
|
|
654
|
-
} else if (
|
|
650
|
+
} else if (primaryLabel2 === "InboundInvoice") {
|
|
655
651
|
const supplier = typeof props.supplier === "string" ? props.supplier : "";
|
|
656
652
|
const conf = typeof props.confirmationNumber === "string" ? props.confirmationNumber : "";
|
|
657
653
|
const composed = [supplier, conf.length > 0 ? `#${conf}` : ""].filter((s) => s.length > 0).join(" ");
|
|
658
654
|
if (composed.length > 0)
|
|
659
655
|
return composed;
|
|
660
|
-
} else if (
|
|
656
|
+
} else if (primaryLabel2 === "WhatsAppGroup") {
|
|
661
657
|
const clientName = typeof props.clientName === "string" ? props.clientName : "";
|
|
662
658
|
if (clientName.length > 0)
|
|
663
659
|
return clientName;
|
|
@@ -667,12 +663,12 @@ var require_dist2 = __commonJS({
|
|
|
667
663
|
if (typeof v === "string" && v.length > 0)
|
|
668
664
|
return v;
|
|
669
665
|
}
|
|
670
|
-
if (
|
|
666
|
+
if (primaryLabel2 === "Conversation") {
|
|
671
667
|
const id = typeof props.sessionId === "string" ? props.sessionId : null;
|
|
672
668
|
if (id)
|
|
673
669
|
return `Conv ${id.slice(0, 8)}`;
|
|
674
670
|
}
|
|
675
|
-
return
|
|
671
|
+
return primaryLabel2 ?? "\u2026";
|
|
676
672
|
}
|
|
677
673
|
}
|
|
678
674
|
});
|
|
@@ -7953,18 +7949,37 @@ var UUID = /^[0-9a-fA-F]{8}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-fA-F]{4}-[0-9a-f
|
|
|
7953
7949
|
function canonicalOverridePath(accountDir) {
|
|
7954
7950
|
return join13(accountDir, FILE);
|
|
7955
7951
|
}
|
|
7956
|
-
function
|
|
7952
|
+
function readRaw(accountDir) {
|
|
7957
7953
|
try {
|
|
7958
|
-
|
|
7959
|
-
return typeof raw.sessionId === "string" && UUID.test(raw.sessionId) ? raw.sessionId : null;
|
|
7954
|
+
return JSON.parse(readFileSync14(canonicalOverridePath(accountDir), "utf8"));
|
|
7960
7955
|
} catch {
|
|
7961
7956
|
return null;
|
|
7962
7957
|
}
|
|
7963
7958
|
}
|
|
7964
|
-
function
|
|
7959
|
+
function readCanonicalOverrideId(accountDir, userId, primaryUserId) {
|
|
7960
|
+
const raw = readRaw(accountDir);
|
|
7961
|
+
if (!raw) return null;
|
|
7962
|
+
if (raw.byAdmin && typeof raw.byAdmin === "object") {
|
|
7963
|
+
const v = raw.byAdmin[userId];
|
|
7964
|
+
return typeof v === "string" && UUID.test(v) ? v : null;
|
|
7965
|
+
}
|
|
7966
|
+
if (typeof raw.sessionId === "string" && UUID.test(raw.sessionId) && primaryUserId !== null && userId === primaryUserId) {
|
|
7967
|
+
return raw.sessionId;
|
|
7968
|
+
}
|
|
7969
|
+
return null;
|
|
7970
|
+
}
|
|
7971
|
+
function writeCanonicalOverrideId(accountDir, userId, sessionId) {
|
|
7972
|
+
const raw = readRaw(accountDir);
|
|
7973
|
+
const byAdmin = {};
|
|
7974
|
+
if (raw?.byAdmin && typeof raw.byAdmin === "object") {
|
|
7975
|
+
for (const [k, v] of Object.entries(raw.byAdmin)) {
|
|
7976
|
+
if (typeof v === "string") byAdmin[k] = v;
|
|
7977
|
+
}
|
|
7978
|
+
}
|
|
7979
|
+
byAdmin[userId] = sessionId;
|
|
7965
7980
|
const path2 = canonicalOverridePath(accountDir);
|
|
7966
7981
|
const tmp = `${path2}.${process.pid}.tmp`;
|
|
7967
|
-
writeFileSync5(tmp, JSON.stringify({
|
|
7982
|
+
writeFileSync5(tmp, JSON.stringify({ byAdmin }, null, 2), "utf8");
|
|
7968
7983
|
renameSync(tmp, path2);
|
|
7969
7984
|
}
|
|
7970
7985
|
|
|
@@ -7980,6 +7995,33 @@ function adminSessionIdFor(accountId, senderId, personId) {
|
|
|
7980
7995
|
return `${h.slice(0, 8)}-${h.slice(8, 12)}-${h.slice(12, 16)}-${h.slice(16, 20)}-${h.slice(20, 32)}`;
|
|
7981
7996
|
}
|
|
7982
7997
|
|
|
7998
|
+
// ../lib/models/src/index.ts
|
|
7999
|
+
var OPUS_MODEL = "claude-opus-4-8[1m]";
|
|
8000
|
+
var SONNET_MODEL = "claude-sonnet-4-6";
|
|
8001
|
+
var HAIKU_MODEL = "claude-haiku-4-5";
|
|
8002
|
+
var MODEL_CONTEXT_WINDOW = {
|
|
8003
|
+
[OPUS_MODEL]: 1e6,
|
|
8004
|
+
[SONNET_MODEL]: 2e5,
|
|
8005
|
+
[HAIKU_MODEL]: 2e5
|
|
8006
|
+
};
|
|
8007
|
+
var MODEL_DISPLAY_NAMES = {
|
|
8008
|
+
[OPUS_MODEL]: "Opus 4.8 (1M context)",
|
|
8009
|
+
[SONNET_MODEL]: "Sonnet 4.6",
|
|
8010
|
+
[HAIKU_MODEL]: "Haiku 4.5"
|
|
8011
|
+
};
|
|
8012
|
+
var SELECTABLE_MODELS = [OPUS_MODEL, SONNET_MODEL, HAIKU_MODEL];
|
|
8013
|
+
function isSelectableModel(id) {
|
|
8014
|
+
return SELECTABLE_MODELS.includes(id);
|
|
8015
|
+
}
|
|
8016
|
+
var PERMISSION_MODES = ["default", "acceptEdits", "plan", "auto", "bypassPermissions"];
|
|
8017
|
+
function isPermissionMode(value) {
|
|
8018
|
+
return PERMISSION_MODES.includes(value);
|
|
8019
|
+
}
|
|
8020
|
+
var EFFORT_LEVELS = ["low", "medium", "high", "xhigh"];
|
|
8021
|
+
function isEffortLevel(value) {
|
|
8022
|
+
return EFFORT_LEVELS.includes(value);
|
|
8023
|
+
}
|
|
8024
|
+
|
|
7983
8025
|
// ../services/claude-session-manager/src/sidecar-store.ts
|
|
7984
8026
|
import { existsSync as existsSync8, mkdirSync as mkdirSync2, readdirSync as readdirSync9, readFileSync as readFileSync15, renameSync as renameSync2, unlinkSync, writeFileSync as writeFileSync6 } from "fs";
|
|
7985
8027
|
import { join as join14 } from "path";
|
|
@@ -8133,11 +8175,25 @@ function locateSidecar(sessionId) {
|
|
|
8133
8175
|
for (const slug of slugs) {
|
|
8134
8176
|
const metaPath = join15(projectsRoot, slug, `${sessionId}.meta.json`);
|
|
8135
8177
|
if (existsSync9(metaPath)) {
|
|
8136
|
-
|
|
8178
|
+
const meta = readSidecarMeta(metaPath);
|
|
8179
|
+
return { channel: meta.channel, adminUserId: meta.adminUserId };
|
|
8137
8180
|
}
|
|
8138
8181
|
}
|
|
8139
8182
|
return null;
|
|
8140
8183
|
}
|
|
8184
|
+
function readTargetOwner(sessionId) {
|
|
8185
|
+
const sidecar = locateSidecar(sessionId);
|
|
8186
|
+
if (sidecar !== null) return { found: true, owner: sidecar.adminUserId };
|
|
8187
|
+
const { projectDir } = locateSession(sessionId);
|
|
8188
|
+
if (projectDir !== null) {
|
|
8189
|
+
return { found: true, owner: readSidecarMeta(join15(projectDir, `${sessionId}.meta.json`)).adminUserId };
|
|
8190
|
+
}
|
|
8191
|
+
return { found: false, owner: null };
|
|
8192
|
+
}
|
|
8193
|
+
function ownedByRequester(owner, requesterUserId, primaryUserId) {
|
|
8194
|
+
if (requesterUserId === null) return false;
|
|
8195
|
+
return owner === requesterUserId || owner === null && requesterUserId === primaryUserId;
|
|
8196
|
+
}
|
|
8141
8197
|
function sessionSidecarExists(sessionId) {
|
|
8142
8198
|
return locateSidecar(sessionId) !== null;
|
|
8143
8199
|
}
|
|
@@ -8188,8 +8244,6 @@ async function fetchComposerIndicators(sessionId) {
|
|
|
8188
8244
|
}
|
|
8189
8245
|
}
|
|
8190
8246
|
var MODEL_ID_PATTERN = /^claude-[a-z0-9][a-z0-9.-]*(\[1m\])?$/;
|
|
8191
|
-
var EFFORT_LEVELS = /* @__PURE__ */ new Set(["low", "medium", "high", "xhigh"]);
|
|
8192
|
-
var PERMISSION_MODE_VALUES = /* @__PURE__ */ new Set(["default", "acceptEdits", "plan", "auto", "bypassPermissions"]);
|
|
8193
8247
|
function readLevers(preResolved) {
|
|
8194
8248
|
let account = preResolved;
|
|
8195
8249
|
if (account === void 0) {
|
|
@@ -8205,11 +8259,20 @@ function readLevers(preResolved) {
|
|
|
8205
8259
|
const mode = account.config.adminPermissionMode;
|
|
8206
8260
|
return {
|
|
8207
8261
|
leverModel: typeof model === "string" && MODEL_ID_PATTERN.test(model) ? model : null,
|
|
8208
|
-
leverEffort: typeof effort === "string" &&
|
|
8209
|
-
leverMode: typeof mode === "string" &&
|
|
8262
|
+
leverEffort: typeof effort === "string" && isEffortLevel(effort) ? effort : null,
|
|
8263
|
+
leverMode: typeof mode === "string" && isPermissionMode(mode) ? mode : null
|
|
8210
8264
|
};
|
|
8211
8265
|
}
|
|
8212
|
-
function
|
|
8266
|
+
function resolvePrimaryAdminUserId() {
|
|
8267
|
+
try {
|
|
8268
|
+
const users = readUsersFile(USERS_FILE);
|
|
8269
|
+
return users && users.length > 0 ? users[0].userId : null;
|
|
8270
|
+
} catch {
|
|
8271
|
+
return null;
|
|
8272
|
+
}
|
|
8273
|
+
}
|
|
8274
|
+
function latestAdminWebchatSessionId(requesterUserId, primaryUserId) {
|
|
8275
|
+
if (requesterUserId === null) return null;
|
|
8213
8276
|
const cfg = claudeConfigDir();
|
|
8214
8277
|
if (!cfg) return null;
|
|
8215
8278
|
let best = null;
|
|
@@ -8224,6 +8287,13 @@ function latestAdminWebchatSessionId() {
|
|
|
8224
8287
|
} catch {
|
|
8225
8288
|
continue;
|
|
8226
8289
|
}
|
|
8290
|
+
const owned = meta.adminUserId === requesterUserId || meta.adminUserId === null && requesterUserId === primaryUserId;
|
|
8291
|
+
if (!owned) {
|
|
8292
|
+
if (best === null || mtimeMs > best.mtimeMs) {
|
|
8293
|
+
console.error(`[webchat:inbound] op=owner-skip candidate=${id.slice(0, 8)} owner=${meta.adminUserId ? meta.adminUserId.slice(0, 8) : "none"} requester=${requesterUserId.slice(0, 8)}`);
|
|
8294
|
+
}
|
|
8295
|
+
continue;
|
|
8296
|
+
}
|
|
8227
8297
|
if (best === null || mtimeMs > best.mtimeMs) best = { id, mtimeMs };
|
|
8228
8298
|
}
|
|
8229
8299
|
return best === null ? null : best.id;
|
|
@@ -8233,14 +8303,17 @@ function overrideKnownNonArchived(id) {
|
|
|
8233
8303
|
if (projectDir === null) return sessionSidecarExists(id);
|
|
8234
8304
|
return basename4(projectDir) !== "archive";
|
|
8235
8305
|
}
|
|
8236
|
-
function resolveCanonical(accountId, accountDir) {
|
|
8237
|
-
|
|
8306
|
+
function resolveCanonical(accountId, accountDir, requesterUserId, primaryUserId) {
|
|
8307
|
+
if (requesterUserId === null) {
|
|
8308
|
+
return { sessionId: adminSessionIdFor(accountId, WEBCHAT_ADMIN_KEY), source: "canonical-empty" };
|
|
8309
|
+
}
|
|
8310
|
+
const latest = latestAdminWebchatSessionId(requesterUserId, primaryUserId);
|
|
8238
8311
|
if (latest !== null) return { sessionId: latest, source: "latest" };
|
|
8239
8312
|
if (accountDir) {
|
|
8240
|
-
const override = readCanonicalOverrideId(accountDir);
|
|
8313
|
+
const override = readCanonicalOverrideId(accountDir, requesterUserId, primaryUserId);
|
|
8241
8314
|
if (override && overrideKnownNonArchived(override)) return { sessionId: override, source: "override" };
|
|
8242
8315
|
}
|
|
8243
|
-
return { sessionId: adminSessionIdFor(accountId, WEBCHAT_ADMIN_KEY), source: "canonical-empty" };
|
|
8316
|
+
return { sessionId: adminSessionIdFor(accountId, WEBCHAT_ADMIN_KEY, requesterUserId), source: "canonical-empty" };
|
|
8244
8317
|
}
|
|
8245
8318
|
var REAPPLY_TIMEOUT_MS = 1500;
|
|
8246
8319
|
async function reapplyLeversViaManager() {
|
|
@@ -8273,6 +8346,9 @@ function createWebchatRoutes(deps) {
|
|
|
8273
8346
|
console.error(`[webchat:inbound] op=send-refused reason=account-unresolved detail=${detail}`);
|
|
8274
8347
|
return c.json({ error: "account unresolved" }, 503);
|
|
8275
8348
|
}
|
|
8349
|
+
const cacheKey = c.get("cacheKey");
|
|
8350
|
+
const requesterUserId = (cacheKey ? getUserIdForSession(cacheKey) : void 0) ?? null;
|
|
8351
|
+
const primaryUserId = resolvePrimaryAdminUserId();
|
|
8276
8352
|
let text;
|
|
8277
8353
|
let target;
|
|
8278
8354
|
let files = [];
|
|
@@ -8313,10 +8389,18 @@ function createWebchatRoutes(deps) {
|
|
|
8313
8389
|
}
|
|
8314
8390
|
let deliveryKey = WEBCHAT_ADMIN_KEY;
|
|
8315
8391
|
let deliverySessionId;
|
|
8392
|
+
const explicitTarget = target !== void 0;
|
|
8316
8393
|
if (target === void 0) {
|
|
8317
|
-
const latest = latestAdminWebchatSessionId();
|
|
8394
|
+
const latest = latestAdminWebchatSessionId(requesterUserId, primaryUserId);
|
|
8318
8395
|
if (latest !== null) target = latest;
|
|
8319
8396
|
}
|
|
8397
|
+
if (explicitTarget && target !== void 0) {
|
|
8398
|
+
const t = readTargetOwner(target);
|
|
8399
|
+
if (t.found && !ownedByRequester(t.owner, requesterUserId, primaryUserId)) {
|
|
8400
|
+
console.error(`[webchat:inbound] op=send-refused key=session:${target.slice(0, 8)} reason=foreign-target requester=${requesterUserId ? requesterUserId.slice(0, 8) : "none"}`);
|
|
8401
|
+
return c.json({ error: "session not found" }, 404);
|
|
8402
|
+
}
|
|
8403
|
+
}
|
|
8320
8404
|
if (target !== void 0) {
|
|
8321
8405
|
let { projectDir, channel } = locateSession(target);
|
|
8322
8406
|
if (projectDir === null) {
|
|
@@ -8392,10 +8476,11 @@ ${note}` : note;
|
|
|
8392
8476
|
}
|
|
8393
8477
|
console.log(`[webchat:inbound] op=send-accepted kind=${kind} files=${stored.length} bytes=${Buffer.byteLength(text, "utf8")}`);
|
|
8394
8478
|
}
|
|
8479
|
+
const adminUserId = requesterUserId ?? void 0;
|
|
8395
8480
|
if (deliverySessionId !== void 0) {
|
|
8396
|
-
await deps.handleInbound({ role: "admin", accountId, key: deliveryKey, text, sessionId: deliverySessionId });
|
|
8481
|
+
await deps.handleInbound({ role: "admin", accountId, key: deliveryKey, text, sessionId: deliverySessionId, adminUserId });
|
|
8397
8482
|
} else {
|
|
8398
|
-
await deps.handleInbound({ role: "admin", accountId, key: deliveryKey, text });
|
|
8483
|
+
await deps.handleInbound({ role: "admin", accountId, key: deliveryKey, text, adminUserId });
|
|
8399
8484
|
}
|
|
8400
8485
|
const sendId = ++sendSeq;
|
|
8401
8486
|
let turnSessionId = deliverySessionId;
|
|
@@ -8406,7 +8491,7 @@ ${note}` : note;
|
|
|
8406
8491
|
} catch {
|
|
8407
8492
|
canonAccount = null;
|
|
8408
8493
|
}
|
|
8409
|
-
turnSessionId = resolveCanonical(accountId, canonAccount?.accountDir ?? null).sessionId;
|
|
8494
|
+
turnSessionId = resolveCanonical(accountId, canonAccount?.accountDir ?? null, requesterUserId, primaryUserId).sessionId;
|
|
8410
8495
|
}
|
|
8411
8496
|
const keyDisplay2 = deliveryKey.startsWith("session:") ? deliveryKey.slice(0, "session:".length + 8) : WEBCHAT_ADMIN_KEY;
|
|
8412
8497
|
const baseline = jsonlSizeBytes(locateSession(turnSessionId).projectDir, turnSessionId);
|
|
@@ -8431,7 +8516,7 @@ ${note}` : note;
|
|
|
8431
8516
|
console.error(`[webchat:settings] op=${String(op)} outcome=refused reason=unknown-op`);
|
|
8432
8517
|
return c.json({ error: "op must be model, effort, or mode" }, 400);
|
|
8433
8518
|
}
|
|
8434
|
-
if (typeof value !== "string" || op === "model" && !MODEL_ID_PATTERN.test(value) || op === "effort" && !
|
|
8519
|
+
if (typeof value !== "string" || op === "model" && !MODEL_ID_PATTERN.test(value) || op === "effort" && !isEffortLevel(value) || op === "mode" && !isPermissionMode(value)) {
|
|
8435
8520
|
console.error(`[webchat:settings] op=${op} outcome=refused value=${JSON.stringify(value)} reason=invalid-value`);
|
|
8436
8521
|
return c.json({ error: `invalid ${op} value` }, 400);
|
|
8437
8522
|
}
|
|
@@ -8472,11 +8557,19 @@ ${note}` : note;
|
|
|
8472
8557
|
console.error(`[webchat:inbound] op=session-refused reason=account-unresolved detail=${detail}`);
|
|
8473
8558
|
return c.json({ error: "account unresolved" }, 503);
|
|
8474
8559
|
}
|
|
8560
|
+
const cacheKey = c.get("cacheKey");
|
|
8561
|
+
const requesterUserId = (cacheKey ? getUserIdForSession(cacheKey) : void 0) ?? null;
|
|
8562
|
+
const primaryUserId = resolvePrimaryAdminUserId();
|
|
8475
8563
|
const target = c.req.query("session");
|
|
8476
8564
|
if (target !== void 0) {
|
|
8477
8565
|
if (!UUID_PATTERN.test(target)) {
|
|
8478
8566
|
return c.json({ error: "invalid session id" }, 400);
|
|
8479
8567
|
}
|
|
8568
|
+
const owned = readTargetOwner(target);
|
|
8569
|
+
if (owned.found && !ownedByRequester(owned.owner, requesterUserId, primaryUserId)) {
|
|
8570
|
+
console.error(`[webchat:inbound] op=session-target-foreign key=session:${target.slice(0, 8)} requester=${requesterUserId ? requesterUserId.slice(0, 8) : "none"}`);
|
|
8571
|
+
return c.json({ error: "session not found" }, 404);
|
|
8572
|
+
}
|
|
8480
8573
|
const { projectDir: projectDir2, channel } = locateSession(target);
|
|
8481
8574
|
let resolvedProjectDir = projectDir2;
|
|
8482
8575
|
let transcriptSessionId = target;
|
|
@@ -8505,11 +8598,14 @@ ${note}` : note;
|
|
|
8505
8598
|
} catch {
|
|
8506
8599
|
account = null;
|
|
8507
8600
|
}
|
|
8508
|
-
const { sessionId, source } = resolveCanonical(accountId, account?.accountDir ?? null);
|
|
8509
|
-
if (
|
|
8510
|
-
|
|
8601
|
+
const { sessionId, source } = resolveCanonical(accountId, account?.accountDir ?? null, requesterUserId, primaryUserId);
|
|
8602
|
+
if (requesterUserId === null) {
|
|
8603
|
+
console.error(`[webchat:inbound] op=session-resolve-no-identity key=${sessionId.slice(0, 8)}`);
|
|
8511
8604
|
}
|
|
8512
|
-
|
|
8605
|
+
if (source === "latest" && account?.accountDir && requesterUserId !== null) {
|
|
8606
|
+
writeCanonicalOverrideId(account.accountDir, requesterUserId, sessionId);
|
|
8607
|
+
}
|
|
8608
|
+
console.log(`[webchat:inbound] op=session-resolve key=${sessionId.slice(0, 8)} source=${source} admin=${requesterUserId ? requesterUserId.slice(0, 8) : "none"}`);
|
|
8513
8609
|
const cfg = claudeConfigDir();
|
|
8514
8610
|
let projectDir = null;
|
|
8515
8611
|
if (cfg) {
|
|
@@ -8520,6 +8616,12 @@ ${note}` : note;
|
|
|
8520
8616
|
}
|
|
8521
8617
|
}
|
|
8522
8618
|
}
|
|
8619
|
+
if (source === "latest" && requesterUserId !== null) {
|
|
8620
|
+
const owner = readSidecarMeta(join15(projectDir ?? "", `${sessionId}.meta.json`)).adminUserId;
|
|
8621
|
+
if (owner !== null && owner !== requesterUserId && requesterUserId !== primaryUserId) {
|
|
8622
|
+
console.error(`[webchat:inbound] op=session-resolve-foreign key=${sessionId.slice(0, 8)} owner=${owner.slice(0, 8)} requester=${requesterUserId.slice(0, 8)}`);
|
|
8623
|
+
}
|
|
8624
|
+
}
|
|
8523
8625
|
const indicators = await fetchComposerIndicators(sessionId);
|
|
8524
8626
|
return c.json({ sessionId, projectDir, sizeBytes: jsonlSizeBytes(projectDir, sessionId), pendingPermissionPrompt: deps.pendingPromptFor?.(`session:${sessionId}`) ?? null, ...indicators, ...readLevers(account) });
|
|
8525
8627
|
});
|
|
@@ -8721,7 +8823,8 @@ async function managerSpawn(opts) {
|
|
|
8721
8823
|
personId: opts.personId,
|
|
8722
8824
|
visitorId: opts.visitorId,
|
|
8723
8825
|
name: opts.name,
|
|
8724
|
-
webchatChannel: opts.webchatChannel
|
|
8826
|
+
webchatChannel: opts.webchatChannel,
|
|
8827
|
+
previousContext: opts.previousContext
|
|
8725
8828
|
})
|
|
8726
8829
|
}).catch((err) => ({ __throw: err instanceof Error ? err.message : String(err) }));
|
|
8727
8830
|
if ("__throw" in res) {
|
|
@@ -8748,6 +8851,7 @@ async function managerRcSpawn(opts) {
|
|
|
8748
8851
|
sliceToken: opts.sliceToken,
|
|
8749
8852
|
personId: opts.personId,
|
|
8750
8853
|
userId: opts.userId,
|
|
8854
|
+
adminUserId: opts.adminUserId,
|
|
8751
8855
|
waChannel: opts.waChannel,
|
|
8752
8856
|
webchatChannel: opts.webchatChannel,
|
|
8753
8857
|
role: opts.role,
|
|
@@ -16102,29 +16206,6 @@ var session_rc_spawn_default = app32;
|
|
|
16102
16206
|
|
|
16103
16207
|
// server/routes/admin/session-reseat.ts
|
|
16104
16208
|
import { randomUUID as randomUUID12 } from "crypto";
|
|
16105
|
-
|
|
16106
|
-
// ../lib/models/src/index.ts
|
|
16107
|
-
var OPUS_MODEL = "claude-opus-4-8[1m]";
|
|
16108
|
-
var SONNET_MODEL = "claude-sonnet-4-6";
|
|
16109
|
-
var HAIKU_MODEL = "claude-haiku-4-5";
|
|
16110
|
-
var MODEL_CONTEXT_WINDOW = {
|
|
16111
|
-
[OPUS_MODEL]: 1e6,
|
|
16112
|
-
[SONNET_MODEL]: 2e5,
|
|
16113
|
-
[HAIKU_MODEL]: 2e5
|
|
16114
|
-
};
|
|
16115
|
-
var MODEL_DISPLAY_NAMES = {
|
|
16116
|
-
[OPUS_MODEL]: "Opus 4.8 (1M context)",
|
|
16117
|
-
[SONNET_MODEL]: "Sonnet 4.6",
|
|
16118
|
-
[HAIKU_MODEL]: "Haiku 4.5"
|
|
16119
|
-
};
|
|
16120
|
-
var SELECTABLE_MODELS = [OPUS_MODEL, SONNET_MODEL, HAIKU_MODEL];
|
|
16121
|
-
function isSelectableModel(id) {
|
|
16122
|
-
return SELECTABLE_MODELS.includes(id);
|
|
16123
|
-
}
|
|
16124
|
-
|
|
16125
|
-
// server/routes/admin/session-reseat.ts
|
|
16126
|
-
var RESEAT_PERMISSION_MODES = /* @__PURE__ */ new Set(["default", "acceptEdits", "plan", "auto", "bypassPermissions"]);
|
|
16127
|
-
var RESEAT_EFFORT_LEVELS = /* @__PURE__ */ new Set(["low", "medium", "high", "xhigh"]);
|
|
16128
16209
|
function resolveReseatPlan(body, mintId = randomUUID12, adminUserId, authenticatedName) {
|
|
16129
16210
|
const sessionId = mintId();
|
|
16130
16211
|
const key = `session:${sessionId}`;
|
|
@@ -16157,8 +16238,8 @@ app33.post("/", requireAdminSession, async (c) => {
|
|
|
16157
16238
|
const model = typeof body.model === "string" && isSelectableModel(body.model) ? body.model : null;
|
|
16158
16239
|
if (fromSessionId === null) return c.json({ error: "fromSessionId must be a valid session id" }, 400);
|
|
16159
16240
|
if (model === null) return c.json({ error: "model must be a selectable model" }, 400);
|
|
16160
|
-
const permissionMode = typeof body.permissionMode === "string" ?
|
|
16161
|
-
const effort = typeof body.effort === "string" ?
|
|
16241
|
+
const permissionMode = typeof body.permissionMode === "string" ? isPermissionMode(body.permissionMode) ? body.permissionMode : null : void 0;
|
|
16242
|
+
const effort = typeof body.effort === "string" ? isEffortLevel(body.effort) ? body.effort : null : void 0;
|
|
16162
16243
|
if (permissionMode === null) return c.json({ error: "permissionMode must be a composer-writable mode" }, 400);
|
|
16163
16244
|
if (effort === null) return c.json({ error: "effort must be an accepted level" }, 400);
|
|
16164
16245
|
if (reseatsInFlight.has(fromSessionId)) {
|
|
@@ -16168,6 +16249,13 @@ app33.post("/", requireAdminSession, async (c) => {
|
|
|
16168
16249
|
try {
|
|
16169
16250
|
const cacheKey = c.get("cacheKey");
|
|
16170
16251
|
const adminUserId = cacheKey ? getUserIdForSession(cacheKey) : void 0;
|
|
16252
|
+
{
|
|
16253
|
+
const ownerInfo = readTargetOwner(fromSessionId);
|
|
16254
|
+
if (!(ownerInfo.found && ownedByRequester(ownerInfo.owner, adminUserId ?? null, resolvePrimaryAdminUserId()))) {
|
|
16255
|
+
console.error(`[chat-reseat] op=reseat-refused from=${fromSessionId.slice(0, 8)} reason=foreign-source requester=${adminUserId ? adminUserId.slice(0, 8) : "none"}`);
|
|
16256
|
+
return c.json({ error: "session not found" }, 404);
|
|
16257
|
+
}
|
|
16258
|
+
}
|
|
16171
16259
|
const accountId = cacheKey ? getAccountIdForSession(cacheKey) : void 0;
|
|
16172
16260
|
const authenticatedName = accountId ? await resolveAuthenticatedName(accountId, adminUserId) : void 0;
|
|
16173
16261
|
const plan = resolveReseatPlan(
|
|
@@ -16204,12 +16292,13 @@ app33.post("/", requireAdminSession, async (c) => {
|
|
|
16204
16292
|
}
|
|
16205
16293
|
try {
|
|
16206
16294
|
const account = resolveAccount();
|
|
16207
|
-
if (account) {
|
|
16295
|
+
if (account && adminUserId) {
|
|
16208
16296
|
const accountId2 = resolvePlatformAccountId();
|
|
16209
|
-
const
|
|
16210
|
-
const
|
|
16297
|
+
const primaryUserId = resolvePrimaryAdminUserId();
|
|
16298
|
+
const canonicalId = adminSessionIdFor(accountId2, WEBCHAT_ADMIN_KEY, adminUserId);
|
|
16299
|
+
const currentOverride = readCanonicalOverrideId(account.accountDir, adminUserId, primaryUserId);
|
|
16211
16300
|
if (fromSessionId === canonicalId || fromSessionId === currentOverride) {
|
|
16212
|
-
writeCanonicalOverrideId(account.accountDir, plan.sessionId);
|
|
16301
|
+
writeCanonicalOverrideId(account.accountDir, adminUserId, plan.sessionId);
|
|
16213
16302
|
console.log(`[chat-reseat] op=canonical-forward reseatReqId=${reseatReqId} from=${fromSessionId} to=${plan.sessionId}`);
|
|
16214
16303
|
}
|
|
16215
16304
|
}
|
|
@@ -16668,9 +16757,8 @@ app37.get("/", async (c) => {
|
|
|
16668
16757
|
});
|
|
16669
16758
|
var post_turn_context_default = app37;
|
|
16670
16759
|
|
|
16671
|
-
//
|
|
16760
|
+
// app/lib/slice-writes.ts
|
|
16672
16761
|
import neo4j4 from "neo4j-driver";
|
|
16673
|
-
var TAG32 = "[public-session-context]";
|
|
16674
16762
|
var STRIPPED_PROPERTIES3 = /* @__PURE__ */ new Set([
|
|
16675
16763
|
"embedding",
|
|
16676
16764
|
"passwordHash",
|
|
@@ -16678,9 +16766,6 @@ var STRIPPED_PROPERTIES3 = /* @__PURE__ */ new Set([
|
|
|
16678
16766
|
"otpCode",
|
|
16679
16767
|
"cacheKey"
|
|
16680
16768
|
]);
|
|
16681
|
-
function isLoopbackAddr3(addr) {
|
|
16682
|
-
return addr === "127.0.0.1" || addr === "::1" || addr === "::ffff:127.0.0.1";
|
|
16683
|
-
}
|
|
16684
16769
|
function convertValue2(value) {
|
|
16685
16770
|
if (neo4j4.isDateTime(value) || neo4j4.isDate(value) || neo4j4.isLocalDateTime(value) || neo4j4.isLocalTime(value) || neo4j4.isTime(value) || neo4j4.isDuration(value)) {
|
|
16686
16771
|
return value.toString();
|
|
@@ -16708,6 +16793,78 @@ function pruneProperties2(raw) {
|
|
|
16708
16793
|
}
|
|
16709
16794
|
return out;
|
|
16710
16795
|
}
|
|
16796
|
+
async function fetchSliceWrites(session, sliceToken, accountId) {
|
|
16797
|
+
const cypher = `
|
|
16798
|
+
MATCH (n)
|
|
16799
|
+
WHERE n.sliceToken = $sliceToken AND n.accountId = $accountId
|
|
16800
|
+
RETURN elementId(n) AS elementId,
|
|
16801
|
+
labels(n) AS labels,
|
|
16802
|
+
properties(n) AS properties,
|
|
16803
|
+
coalesce(n.createdAt, n.observedAt, '') AS sortKey
|
|
16804
|
+
`;
|
|
16805
|
+
const res = await session.executeRead((tx) => tx.run(cypher, { sliceToken, accountId }));
|
|
16806
|
+
const writes = res.records.map((r) => ({
|
|
16807
|
+
elementId: r.get("elementId"),
|
|
16808
|
+
labels: r.get("labels"),
|
|
16809
|
+
properties: pruneProperties2(r.get("properties")),
|
|
16810
|
+
sortKey: String(r.get("sortKey") ?? "")
|
|
16811
|
+
}));
|
|
16812
|
+
writes.sort((a, b) => a.sortKey.localeCompare(b.sortKey));
|
|
16813
|
+
return writes.map(({ elementId, labels, properties }) => ({ elementId, labels, properties }));
|
|
16814
|
+
}
|
|
16815
|
+
var STRUCTURAL_KEYS = /* @__PURE__ */ new Set([
|
|
16816
|
+
"accountId",
|
|
16817
|
+
"scope",
|
|
16818
|
+
"sliceToken",
|
|
16819
|
+
"preferenceId",
|
|
16820
|
+
"ideaId",
|
|
16821
|
+
"createdAt",
|
|
16822
|
+
"updatedAt",
|
|
16823
|
+
"observedAt",
|
|
16824
|
+
"sessionId",
|
|
16825
|
+
"createdByAgent",
|
|
16826
|
+
"createdBySession",
|
|
16827
|
+
"confidence",
|
|
16828
|
+
"notApplicable"
|
|
16829
|
+
]);
|
|
16830
|
+
function primaryLabel(labels) {
|
|
16831
|
+
return labels.find((l) => l.length > 0) ?? "Node";
|
|
16832
|
+
}
|
|
16833
|
+
function renderWrite(write) {
|
|
16834
|
+
const label = primaryLabel(write.labels);
|
|
16835
|
+
const props = write.properties;
|
|
16836
|
+
const parts = [];
|
|
16837
|
+
if (label === "Person") {
|
|
16838
|
+
const name = [props.givenName, props.familyName].filter((v) => typeof v === "string" && v.length > 0).join(" ");
|
|
16839
|
+
if (name) parts.push(name);
|
|
16840
|
+
}
|
|
16841
|
+
const kv = [];
|
|
16842
|
+
for (const [k, v] of Object.entries(props)) {
|
|
16843
|
+
if (STRUCTURAL_KEYS.has(k)) continue;
|
|
16844
|
+
if (label === "Person" && (k === "givenName" || k === "familyName")) continue;
|
|
16845
|
+
if (v === null || v === void 0 || v === "") continue;
|
|
16846
|
+
const val = String(v).slice(0, 200);
|
|
16847
|
+
kv.push(`${k}=${val}`);
|
|
16848
|
+
}
|
|
16849
|
+
const tail = [parts.join(" "), kv.join("; ")].filter((s) => s.length > 0).join(" \u2014 ");
|
|
16850
|
+
if (tail.length === 0) return null;
|
|
16851
|
+
return `- ${label}: ${tail}`;
|
|
16852
|
+
}
|
|
16853
|
+
function formatPreviousContext(writes) {
|
|
16854
|
+
if (writes.length === 0) return null;
|
|
16855
|
+
const lines = writes.filter((w) => w.properties.scope === "user").map(renderWrite).filter((l) => l !== null);
|
|
16856
|
+
if (lines.length === 0) return null;
|
|
16857
|
+
return [
|
|
16858
|
+
"What you already know about this visitor from earlier conversations:",
|
|
16859
|
+
...lines
|
|
16860
|
+
].join("\n");
|
|
16861
|
+
}
|
|
16862
|
+
|
|
16863
|
+
// server/routes/admin/public-session-context.ts
|
|
16864
|
+
var TAG32 = "[public-session-context]";
|
|
16865
|
+
function isLoopbackAddr3(addr) {
|
|
16866
|
+
return addr === "127.0.0.1" || addr === "::1" || addr === "::ffff:127.0.0.1";
|
|
16867
|
+
}
|
|
16711
16868
|
var app38 = new Hono();
|
|
16712
16869
|
app38.get("/", async (c) => {
|
|
16713
16870
|
const remoteAddr = c.env?.incoming?.socket?.remoteAddress ?? "";
|
|
@@ -16732,31 +16889,12 @@ app38.get("/", async (c) => {
|
|
|
16732
16889
|
const session = getSession();
|
|
16733
16890
|
const started = Date.now();
|
|
16734
16891
|
try {
|
|
16735
|
-
const
|
|
16736
|
-
MATCH (n)
|
|
16737
|
-
WHERE n.sliceToken = $sliceToken AND n.accountId = $accountId
|
|
16738
|
-
RETURN elementId(n) AS elementId,
|
|
16739
|
-
labels(n) AS labels,
|
|
16740
|
-
properties(n) AS properties,
|
|
16741
|
-
coalesce(n.createdAt, n.observedAt, '') AS sortKey
|
|
16742
|
-
`;
|
|
16743
|
-
const res = await session.executeRead(
|
|
16744
|
-
(tx) => tx.run(cypher, { sliceToken, accountId })
|
|
16745
|
-
);
|
|
16746
|
-
const writes = res.records.map((r) => ({
|
|
16747
|
-
elementId: r.get("elementId"),
|
|
16748
|
-
labels: r.get("labels"),
|
|
16749
|
-
properties: pruneProperties2(r.get("properties")),
|
|
16750
|
-
sortKey: String(r.get("sortKey") ?? "")
|
|
16751
|
-
}));
|
|
16752
|
-
writes.sort((a, b) => a.sortKey.localeCompare(b.sortKey));
|
|
16892
|
+
const writes = await fetchSliceWrites(session, sliceToken, accountId);
|
|
16753
16893
|
const total = Date.now() - started;
|
|
16754
16894
|
console.log(
|
|
16755
16895
|
`${TAG32} sliceToken=${sliceToken.slice(0, 8)} writes=${writes.length} ms=${total}`
|
|
16756
16896
|
);
|
|
16757
|
-
return c.json({
|
|
16758
|
-
writes: writes.map(({ elementId, labels, properties }) => ({ elementId, labels, properties }))
|
|
16759
|
-
});
|
|
16897
|
+
return c.json({ writes });
|
|
16760
16898
|
} catch (err) {
|
|
16761
16899
|
const elapsed = Date.now() - started;
|
|
16762
16900
|
const message = err instanceof Error ? err.message : String(err);
|
|
@@ -17995,19 +18133,8 @@ app51.post("/", async (c) => {
|
|
|
17995
18133
|
const account = resolveAccount();
|
|
17996
18134
|
const cookieHeader = c.req.header("cookie");
|
|
17997
18135
|
const visitorId = parseVisitorCookie2(cookieHeader);
|
|
17998
|
-
const groupSlug = body.group_slug && typeof body.group_slug === "string" ? body.group_slug : null;
|
|
17999
|
-
let groupInfo = null;
|
|
18000
|
-
if (groupSlug) {
|
|
18001
|
-
groupInfo = await findGroupBySlug(groupSlug, accountId).catch(() => null);
|
|
18002
|
-
if (!groupInfo) {
|
|
18003
|
-
console.error(`[session] group not found: slug=${groupSlug} account=${accountId.slice(0, 8)}\u2026`);
|
|
18004
|
-
return c.json({ error: "Group not found" }, 404);
|
|
18005
|
-
}
|
|
18006
|
-
}
|
|
18007
18136
|
let agentSlug = null;
|
|
18008
|
-
if (
|
|
18009
|
-
agentSlug = groupInfo.agentSlug;
|
|
18010
|
-
} else if (body.agent) {
|
|
18137
|
+
if (body.agent) {
|
|
18011
18138
|
if (!validateAgentSlug(body.agent)) {
|
|
18012
18139
|
return c.json({ error: "Invalid agent name" }, 400);
|
|
18013
18140
|
}
|
|
@@ -18040,11 +18167,6 @@ app51.post("/", async (c) => {
|
|
|
18040
18167
|
...agentConfig.imageShape ? { agentImageShape: agentConfig.imageShape } : {},
|
|
18041
18168
|
...agentConfig.showAgentName ? { showAgentName: agentConfig.showAgentName } : {}
|
|
18042
18169
|
} : {};
|
|
18043
|
-
const groupFields = groupInfo ? {
|
|
18044
|
-
group: true,
|
|
18045
|
-
groupName: groupInfo.groupName,
|
|
18046
|
-
groupSlug
|
|
18047
|
-
} : {};
|
|
18048
18170
|
const branding = await fetchBranding(accountId).catch(() => null);
|
|
18049
18171
|
if (branding) writeBrandingCache(accountId, agentSlug, branding);
|
|
18050
18172
|
let accessSession = null;
|
|
@@ -18057,7 +18179,6 @@ app51.post("/", async (c) => {
|
|
|
18057
18179
|
Response.json({
|
|
18058
18180
|
auth_required: true,
|
|
18059
18181
|
agent_id: agentSlug,
|
|
18060
|
-
...groupFields,
|
|
18061
18182
|
...branding ? { branding } : {},
|
|
18062
18183
|
...agentIdentity
|
|
18063
18184
|
}),
|
|
@@ -18082,7 +18203,6 @@ app51.post("/", async (c) => {
|
|
|
18082
18203
|
agent_id: agentSlug,
|
|
18083
18204
|
resumed,
|
|
18084
18205
|
...resumed ? { messages: uiMessages } : {},
|
|
18085
|
-
...groupFields,
|
|
18086
18206
|
...branding ? { branding } : {},
|
|
18087
18207
|
...agentIdentity
|
|
18088
18208
|
});
|
|
@@ -18093,56 +18213,10 @@ app51.post("/", async (c) => {
|
|
|
18093
18213
|
session_key: body.session_key,
|
|
18094
18214
|
agent_id: agentSlug,
|
|
18095
18215
|
resumed: false,
|
|
18096
|
-
...groupFields,
|
|
18097
18216
|
...branding ? { branding } : {},
|
|
18098
18217
|
...agentIdentity
|
|
18099
18218
|
});
|
|
18100
18219
|
}
|
|
18101
|
-
if (groupInfo && visitorId) {
|
|
18102
|
-
let memberName = await checkGroupMembership(groupInfo.sessionId, visitorId).catch(() => null);
|
|
18103
|
-
if (!memberName && accessSession) {
|
|
18104
|
-
const contactValue = accessSession.contactValue;
|
|
18105
|
-
const isEmail = contactValue?.includes("@");
|
|
18106
|
-
const bindResult = await bindVisitorToGroup(
|
|
18107
|
-
groupInfo.sessionId,
|
|
18108
|
-
visitorId,
|
|
18109
|
-
isEmail ? contactValue : void 0,
|
|
18110
|
-
!isEmail ? contactValue : void 0
|
|
18111
|
-
).catch(() => null);
|
|
18112
|
-
memberName = bindResult?.displayName ?? null;
|
|
18113
|
-
}
|
|
18114
|
-
if (memberName) {
|
|
18115
|
-
const neo4jMessages = await getRecentMessages(groupInfo.sessionId).catch(() => []);
|
|
18116
|
-
const uiMessages = neo4jMessages.filter((m) => m.content !== GREETING_DIRECTIVE).map((m) => ({
|
|
18117
|
-
role: m.role === "user" ? "visitor" : "maxy",
|
|
18118
|
-
content: m.content,
|
|
18119
|
-
timestamp: new Date(m.createdAt).getTime() || Date.now()
|
|
18120
|
-
}));
|
|
18121
|
-
const participants = await getGroupParticipants(groupInfo.sessionId).catch(() => []);
|
|
18122
|
-
const cacheKey2 = crypto.randomUUID();
|
|
18123
|
-
const resumed = uiMessages.length > 0;
|
|
18124
|
-
console.log(`[session] cold-resume group=${groupSlug} visitor=${visitorId.slice(0, 8)}\u2026 messages=${uiMessages.length}`);
|
|
18125
|
-
return withVisitorCookie(
|
|
18126
|
-
Response.json({
|
|
18127
|
-
session_key: cacheKey2,
|
|
18128
|
-
agent_id: agentSlug,
|
|
18129
|
-
resumed,
|
|
18130
|
-
...resumed ? { messages: uiMessages } : {},
|
|
18131
|
-
...groupFields,
|
|
18132
|
-
participants: participants.map((p) => ({ displayName: p.displayName, joinedAt: p.joinedAt })),
|
|
18133
|
-
...branding ? { branding } : {},
|
|
18134
|
-
...agentIdentity
|
|
18135
|
-
}),
|
|
18136
|
-
visitorId
|
|
18137
|
-
);
|
|
18138
|
-
}
|
|
18139
|
-
console.log(`[session] group cold-resume denied: visitor=${visitorId.slice(0, 8)}\u2026 not a member of group=${groupSlug}`);
|
|
18140
|
-
return c.json({ error: "Not a member of this group" }, 403);
|
|
18141
|
-
}
|
|
18142
|
-
if (groupInfo) {
|
|
18143
|
-
console.error(`[session] group=${groupSlug} requires visitor cookie`);
|
|
18144
|
-
return c.json({ error: "Groups require member authentication" }, 400);
|
|
18145
|
-
}
|
|
18146
18220
|
if (visitorId) {
|
|
18147
18221
|
const recent = await findRecentConversation(visitorId, accountId, agentSlug).catch(() => null);
|
|
18148
18222
|
if (recent) {
|
|
@@ -18544,7 +18618,7 @@ var defaultResolveName = async (accountId, userId) => {
|
|
|
18544
18618
|
const res = await loadAdminUserName(accountId, userId);
|
|
18545
18619
|
return res.source === "neo4j" && res.joined.length > 0 ? res.joined : null;
|
|
18546
18620
|
};
|
|
18547
|
-
async function
|
|
18621
|
+
async function readRaw2(path2) {
|
|
18548
18622
|
let raw;
|
|
18549
18623
|
try {
|
|
18550
18624
|
raw = await readFile7(path2, "utf8");
|
|
@@ -18652,7 +18726,7 @@ async function migrateAdminWebchatSidecars(opts = {}) {
|
|
|
18652
18726
|
};
|
|
18653
18727
|
const sidecars = await collectLiveSidecars(projectsRoot);
|
|
18654
18728
|
for (const path2 of sidecars) {
|
|
18655
|
-
const raw = await
|
|
18729
|
+
const raw = await readRaw2(path2);
|
|
18656
18730
|
if (!raw) continue;
|
|
18657
18731
|
if (raw.role !== ADMIN_ROLE2 || raw.channel !== WEBCHAT_CHANNEL2) continue;
|
|
18658
18732
|
result.scanned++;
|
|
@@ -18670,7 +18744,7 @@ async function migrateAdminWebchatSidecars(opts = {}) {
|
|
|
18670
18744
|
await writeRaw(path2, raw);
|
|
18671
18745
|
result.backfilled++;
|
|
18672
18746
|
await resolveAdminName();
|
|
18673
|
-
const back = await
|
|
18747
|
+
const back = await readRaw2(path2);
|
|
18674
18748
|
const wrote = back && back.adminUserId === soleAdminUserId;
|
|
18675
18749
|
if (wrote && resolvedNameForAdmin) {
|
|
18676
18750
|
result.resolvedName++;
|
|
@@ -19614,6 +19688,9 @@ var WebchatGateway = class _WebchatGateway {
|
|
|
19614
19688
|
// Task 800 — only present on a session-targeted launch, so the
|
|
19615
19689
|
// default-path call shape stays byte-identical.
|
|
19616
19690
|
...input.sessionId !== void 0 ? { sessionId: input.sessionId } : {},
|
|
19691
|
+
// The authenticated admin's userId on an admin bootstrap inbound; the
|
|
19692
|
+
// default-path call shape stays byte-identical when absent.
|
|
19693
|
+
...input.adminUserId !== void 0 ? { adminUserId: input.adminUserId } : {},
|
|
19617
19694
|
// Task 756 — public spawn params on a role:'public' inbound.
|
|
19618
19695
|
...input.public !== void 0 ? { public: input.public } : {}
|
|
19619
19696
|
});
|
|
@@ -19648,6 +19725,7 @@ function buildPublicWebchatSpawnRequest(input) {
|
|
|
19648
19725
|
...sliceToken ? { sliceToken } : {},
|
|
19649
19726
|
...personId ? { personId } : {},
|
|
19650
19727
|
...visitorId ? { visitorId } : {},
|
|
19728
|
+
...input.previousContext ? { previousContext: input.previousContext } : {},
|
|
19651
19729
|
name,
|
|
19652
19730
|
webchatChannel: { key: input.key, gatewayUrl: input.gatewayUrl, serverPath: input.serverPath }
|
|
19653
19731
|
};
|
|
@@ -20120,14 +20198,27 @@ waGateway.startSweeper();
|
|
|
20120
20198
|
var webchatGateway = new WebchatGateway({
|
|
20121
20199
|
gatewayUrl: webchatGatewayUrl(),
|
|
20122
20200
|
serverPath: webchatServerPath(),
|
|
20123
|
-
ensureChannelSession: async ({ accountId, key, role, gatewayUrl, serverPath, sessionId, public: pub }) => {
|
|
20201
|
+
ensureChannelSession: async ({ accountId, key, role, adminUserId, gatewayUrl, serverPath, sessionId, public: pub }) => {
|
|
20124
20202
|
if (role === "public") {
|
|
20125
20203
|
if (!pub) {
|
|
20126
20204
|
console.error(`[webchat:inbound] op=spawn-refused key=${key} role=public reason=missing-public-params`);
|
|
20127
20205
|
return;
|
|
20128
20206
|
}
|
|
20207
|
+
let previousContext;
|
|
20208
|
+
if (pub.sliceToken) {
|
|
20209
|
+
const session = getSession();
|
|
20210
|
+
try {
|
|
20211
|
+
const writes = await fetchSliceWrites(session, pub.sliceToken, accountId);
|
|
20212
|
+
previousContext = formatPreviousContext(writes) ?? void 0;
|
|
20213
|
+
console.log(`[webchat:inbound] op=slice-readback key=${key} writes=${writes.length} injected=${previousContext ? "yes" : "no"}`);
|
|
20214
|
+
} catch (err) {
|
|
20215
|
+
console.error(`[webchat:inbound] op=slice-readback-failed key=${key} err=${err instanceof Error ? err.message : String(err)}`);
|
|
20216
|
+
} finally {
|
|
20217
|
+
await session.close();
|
|
20218
|
+
}
|
|
20219
|
+
}
|
|
20129
20220
|
const result2 = await managerSpawn(
|
|
20130
|
-
buildPublicWebchatSpawnRequest({ accountId, key, gatewayUrl, serverPath, public: pub })
|
|
20221
|
+
buildPublicWebchatSpawnRequest({ accountId, key, gatewayUrl, serverPath, previousContext, public: pub })
|
|
20131
20222
|
);
|
|
20132
20223
|
if ("error" in result2) {
|
|
20133
20224
|
console.error(`[webchat:inbound] op=spawn-failed key=${key} role=public error=${result2.error} status=${result2.status}`);
|
|
@@ -20136,10 +20227,11 @@ var webchatGateway = new WebchatGateway({
|
|
|
20136
20227
|
return { sessionId: result2.sessionId };
|
|
20137
20228
|
}
|
|
20138
20229
|
const result = await managerRcSpawn({
|
|
20139
|
-
sessionId: sessionId ?? adminSessionIdFor(accountId, key),
|
|
20230
|
+
sessionId: sessionId ?? adminSessionIdFor(accountId, key, adminUserId),
|
|
20140
20231
|
role: "admin",
|
|
20141
20232
|
channel: "webchat",
|
|
20142
20233
|
senderId: key,
|
|
20234
|
+
adminUserId,
|
|
20143
20235
|
webchatChannel: { key, gatewayUrl, serverPath },
|
|
20144
20236
|
logContext: `channel=webchat key=${key} role=${role}`
|
|
20145
20237
|
});
|
|
@@ -20658,7 +20750,6 @@ ${clientErrorReporterScript}
|
|
|
20658
20750
|
}
|
|
20659
20751
|
return html;
|
|
20660
20752
|
}
|
|
20661
|
-
var brandedHtmlCache = /* @__PURE__ */ new Map();
|
|
20662
20753
|
function loadBrandingCache(agentSlug) {
|
|
20663
20754
|
const configDir2 = join28(homedir3(), BRAND.configDir);
|
|
20664
20755
|
try {
|
|
@@ -20676,36 +20767,6 @@ function resolveDefaultSlug() {
|
|
|
20676
20767
|
if (!account) return null;
|
|
20677
20768
|
return resolveDefaultAgentSlug(account.accountDir);
|
|
20678
20769
|
}
|
|
20679
|
-
function wantsNextSurface(c) {
|
|
20680
|
-
return c.req.query("surface") === "next";
|
|
20681
|
-
}
|
|
20682
|
-
function brandedPublicHtml(agentSlug) {
|
|
20683
|
-
const baseHtml = cachedHtml("public.html");
|
|
20684
|
-
if (!agentSlug) return baseHtml;
|
|
20685
|
-
const cached3 = brandedHtmlCache.get(agentSlug);
|
|
20686
|
-
const branding = loadBrandingCache(agentSlug);
|
|
20687
|
-
if (!branding) return baseHtml;
|
|
20688
|
-
const brandHash = JSON.stringify(branding).length;
|
|
20689
|
-
if (cached3 && cached3.mtime === brandHash) return cached3.html;
|
|
20690
|
-
const title = escapeHtml(branding.name);
|
|
20691
|
-
const description = branding.tagline ? escapeHtml(branding.tagline) : "";
|
|
20692
|
-
const themeColor = branding.primaryColor || "";
|
|
20693
|
-
const ogImage = branding.logoUrl || "";
|
|
20694
|
-
const favicon = branding.faviconUrl || "";
|
|
20695
|
-
const metaTags = [
|
|
20696
|
-
` <title>${title}</title>`,
|
|
20697
|
-
favicon ? ` <link rel="icon" href="${escapeHtml(favicon)}">` : ` <link rel="icon" href="${escapeHtml(brandFaviconPath)}">`,
|
|
20698
|
-
themeColor ? ` <meta name="theme-color" content="${escapeHtml(themeColor)}">` : "",
|
|
20699
|
-
` <meta property="og:title" content="${title}">`,
|
|
20700
|
-
description ? ` <meta property="og:description" content="${description}">` : "",
|
|
20701
|
-
ogImage ? ` <meta property="og:image" content="${escapeHtml(ogImage)}">` : "",
|
|
20702
|
-
' <meta property="og:type" content="website">'
|
|
20703
|
-
].filter(Boolean).join("\n");
|
|
20704
|
-
const html = baseHtml.replace(` <title>${escapeHtml(BRAND.productName)}</title>
|
|
20705
|
-
<link rel="icon" href="${escapeHtml(brandFaviconPath)}">`, metaTags);
|
|
20706
|
-
brandedHtmlCache.set(agentSlug, { html, mtime: brandHash });
|
|
20707
|
-
return html;
|
|
20708
|
-
}
|
|
20709
20770
|
function escapeHtml(s) {
|
|
20710
20771
|
return s.replace(/&/g, "&").replace(/"/g, """).replace(/</g, "<").replace(/>/g, ">");
|
|
20711
20772
|
}
|
|
@@ -20729,8 +20790,7 @@ app52.get("/", (c) => {
|
|
|
20729
20790
|
);
|
|
20730
20791
|
}
|
|
20731
20792
|
console.error(`[public-root] op=serve-default slug=${defaultSlug}`);
|
|
20732
|
-
|
|
20733
|
-
return c.html(brandedPublicHtml(defaultSlug));
|
|
20793
|
+
return c.html(cachedHtml("public.html"));
|
|
20734
20794
|
}
|
|
20735
20795
|
console.log(`[host-class] host=${host} class=admin served=index.html`);
|
|
20736
20796
|
return c.html(cachedHtml("index.html"));
|
|
@@ -20738,13 +20798,11 @@ app52.get("/", (c) => {
|
|
|
20738
20798
|
app52.get("/public", (c) => {
|
|
20739
20799
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
20740
20800
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
20741
|
-
if (wantsNextSurface(c)) return c.html(cachedHtml("public-next.html"));
|
|
20742
20801
|
return c.html(cachedHtml("public.html"));
|
|
20743
20802
|
});
|
|
20744
20803
|
app52.get("/public-chat", (c) => {
|
|
20745
20804
|
const host = (c.req.header("host") ?? "").split(":")[0];
|
|
20746
20805
|
if (isPublicHost(host)) return c.text("Not found", 404);
|
|
20747
|
-
if (wantsNextSurface(c)) return c.html(cachedHtml("public-next.html"));
|
|
20748
20806
|
return c.html(cachedHtml("public.html"));
|
|
20749
20807
|
});
|
|
20750
20808
|
async function logViewerFetch(c, next) {
|
|
@@ -20798,7 +20856,7 @@ app52.post("/api/vnc/client-event", async (c) => {
|
|
|
20798
20856
|
return c.json({ ok: true });
|
|
20799
20857
|
});
|
|
20800
20858
|
app52.get("/g/:slug", (c) => {
|
|
20801
|
-
return c.html(
|
|
20859
|
+
return c.html(cachedHtml("public.html"));
|
|
20802
20860
|
});
|
|
20803
20861
|
for (const pwa of PWA_SURFACES) {
|
|
20804
20862
|
app52.get(pwa.manifestPath, (c) => {
|
|
@@ -20854,8 +20912,7 @@ app52.get("/:slug", async (c, next) => {
|
|
|
20854
20912
|
}
|
|
20855
20913
|
const branding = loadBrandingCache(slug);
|
|
20856
20914
|
console.error(`[public-catchall] served path=/${slug} slug=${slug} branding=${branding ? "hit" : "miss"}`);
|
|
20857
|
-
|
|
20858
|
-
return c.html(brandedPublicHtml(slug));
|
|
20915
|
+
return c.html(cachedHtml("public.html"));
|
|
20859
20916
|
}
|
|
20860
20917
|
await next();
|
|
20861
20918
|
});
|