agim-cli 1.2.143 → 1.2.147
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/CHANGELOG.md +186 -0
- package/dist/cli-ui/setup-llm.d.ts.map +1 -1
- package/dist/cli-ui/setup-llm.js +3 -1
- package/dist/cli-ui/setup-llm.js.map +1 -1
- package/dist/cli-ui/tui/app.d.ts +1 -0
- package/dist/cli-ui/tui/app.d.ts.map +1 -1
- package/dist/cli-ui/tui/app.js +24 -9
- package/dist/cli-ui/tui/app.js.map +1 -1
- package/dist/cli-ui/tui/markdown.d.ts.map +1 -1
- package/dist/cli-ui/tui/markdown.js +12 -3
- package/dist/cli-ui/tui/markdown.js.map +1 -1
- package/dist/cli.js +23 -3
- package/dist/cli.js.map +1 -1
- package/dist/core/access-token.d.ts.map +1 -1
- package/dist/core/access-token.js +4 -2
- package/dist/core/access-token.js.map +1 -1
- package/dist/core/circuit-breaker.d.ts +28 -0
- package/dist/core/circuit-breaker.d.ts.map +1 -1
- package/dist/core/circuit-breaker.js +45 -0
- package/dist/core/circuit-breaker.js.map +1 -1
- package/dist/core/intent.d.ts.map +1 -1
- package/dist/core/intent.js +3 -1
- package/dist/core/intent.js.map +1 -1
- package/dist/core/llm/agent-loop.d.ts +9 -1
- package/dist/core/llm/agent-loop.d.ts.map +1 -1
- package/dist/core/llm/agent-loop.js +80 -1
- package/dist/core/llm/agent-loop.js.map +1 -1
- package/dist/core/llm/anthropic-provider.d.ts.map +1 -1
- package/dist/core/llm/anthropic-provider.js +18 -4
- package/dist/core/llm/anthropic-provider.js.map +1 -1
- package/dist/core/llm/hallucination-detector.d.ts +33 -0
- package/dist/core/llm/hallucination-detector.d.ts.map +1 -0
- package/dist/core/llm/hallucination-detector.js +103 -0
- package/dist/core/llm/hallucination-detector.js.map +1 -0
- package/dist/core/llm/imhub-dispatcher.d.ts.map +1 -1
- package/dist/core/llm/imhub-dispatcher.js +7 -0
- package/dist/core/llm/imhub-dispatcher.js.map +1 -1
- package/dist/core/llm/provider-base.d.ts +9 -0
- package/dist/core/llm/provider-base.d.ts.map +1 -1
- package/dist/core/llm/provider-base.js.map +1 -1
- package/dist/core/memory-distill.d.ts.map +1 -1
- package/dist/core/memory-distill.js +18 -3
- package/dist/core/memory-distill.js.map +1 -1
- package/dist/core/memory.d.ts +14 -0
- package/dist/core/memory.d.ts.map +1 -1
- package/dist/core/memory.js +39 -0
- package/dist/core/memory.js.map +1 -1
- package/dist/core/message-sink.d.ts +6 -0
- package/dist/core/message-sink.d.ts.map +1 -1
- package/dist/core/message-sink.js +18 -3
- package/dist/core/message-sink.js.map +1 -1
- package/dist/core/outbox.d.ts +30 -2
- package/dist/core/outbox.d.ts.map +1 -1
- package/dist/core/outbox.js +102 -10
- package/dist/core/outbox.js.map +1 -1
- package/dist/core/reminders.d.ts.map +1 -1
- package/dist/core/reminders.js +11 -1
- package/dist/core/reminders.js.map +1 -1
- package/dist/core/router.d.ts.map +1 -1
- package/dist/core/router.js +16 -4
- package/dist/core/router.js.map +1 -1
- package/dist/core/schedule.d.ts +18 -0
- package/dist/core/schedule.d.ts.map +1 -1
- package/dist/core/schedule.js +80 -17
- package/dist/core/schedule.js.map +1 -1
- package/dist/core/sensitive-paths.d.ts.map +1 -1
- package/dist/core/sensitive-paths.js +53 -9
- package/dist/core/sensitive-paths.js.map +1 -1
- package/dist/core/types.d.ts +6 -0
- package/dist/core/types.d.ts.map +1 -1
- package/dist/plugins/agents/native/index.d.ts +47 -8
- package/dist/plugins/agents/native/index.d.ts.map +1 -1
- package/dist/plugins/agents/native/index.js +253 -102
- package/dist/plugins/agents/native/index.js.map +1 -1
- package/dist/plugins/agents/native/tool-registry.d.ts +33 -0
- package/dist/plugins/agents/native/tool-registry.d.ts.map +1 -0
- package/dist/plugins/agents/native/tool-registry.js +82 -0
- package/dist/plugins/agents/native/tool-registry.js.map +1 -0
- package/dist/plugins/messengers/dingtalk/dingtalk-client.d.ts.map +1 -1
- package/dist/plugins/messengers/dingtalk/dingtalk-client.js +11 -11
- package/dist/plugins/messengers/dingtalk/dingtalk-client.js.map +1 -1
- package/dist/plugins/messengers/feishu/feishu-adapter.d.ts.map +1 -1
- package/dist/plugins/messengers/feishu/feishu-adapter.js +9 -5
- package/dist/plugins/messengers/feishu/feishu-adapter.js.map +1 -1
- package/dist/plugins/messengers/wechat/ilink-adapter.d.ts.map +1 -1
- package/dist/plugins/messengers/wechat/ilink-adapter.js +11 -1
- package/dist/plugins/messengers/wechat/ilink-adapter.js.map +1 -1
- package/dist/web/public/assets/{a2a-DczMMkbl.js → a2a-Cll3P4QN.js} +2 -2
- package/dist/web/public/assets/{a2a-DczMMkbl.js.map → a2a-Cll3P4QN.js.map} +1 -1
- package/dist/web/public/assets/{activity-cbLHkzca.js → activity-B7T7YFlD.js} +2 -2
- package/dist/web/public/assets/{activity-cbLHkzca.js.map → activity-B7T7YFlD.js.map} +1 -1
- package/dist/web/public/assets/{admins-C-YsGMj7.js → admins-CN7P018S.js} +2 -2
- package/dist/web/public/assets/{admins-C-YsGMj7.js.map → admins-CN7P018S.js.map} +1 -1
- package/dist/web/public/assets/{agents-BWfov_1-.js → agents-Bqgq7GBF.js} +2 -2
- package/dist/web/public/assets/{agents-BWfov_1-.js.map → agents-Bqgq7GBF.js.map} +1 -1
- package/dist/web/public/assets/{approvals-HSssmXKS.js → approvals-C8IUJQ_A.js} +2 -2
- package/dist/web/public/assets/{approvals-HSssmXKS.js.map → approvals-C8IUJQ_A.js.map} +1 -1
- package/dist/web/public/assets/{arrow-down-BXvC8Al2.js → arrow-down-SLWKqtDc.js} +2 -2
- package/dist/web/public/assets/{arrow-down-BXvC8Al2.js.map → arrow-down-SLWKqtDc.js.map} +1 -1
- package/dist/web/public/assets/{arrow-up-63xELY5Q.js → arrow-up-BOADc9ce.js} +2 -2
- package/dist/web/public/assets/{arrow-up-63xELY5Q.js.map → arrow-up-BOADc9ce.js.map} +1 -1
- package/dist/web/public/assets/{asks-COLEFOvK.js → asks-C-j-DypC.js} +2 -2
- package/dist/web/public/assets/{asks-COLEFOvK.js.map → asks-C-j-DypC.js.map} +1 -1
- package/dist/web/public/assets/{audit-D4ZEiZub.js → audit-DQb-RuXh.js} +2 -2
- package/dist/web/public/assets/{audit-D4ZEiZub.js.map → audit-DQb-RuXh.js.map} +1 -1
- package/dist/web/public/assets/{bell-Cg2Bvv06.js → bell-CV88-ul6.js} +2 -2
- package/dist/web/public/assets/{bell-Cg2Bvv06.js.map → bell-CV88-ul6.js.map} +1 -1
- package/dist/web/public/assets/{bgjobs-CEjCzwtd.js → bgjobs-CDrK0d-W.js} +2 -2
- package/dist/web/public/assets/{bgjobs-CEjCzwtd.js.map → bgjobs-CDrK0d-W.js.map} +1 -1
- package/dist/web/public/assets/{brain-euvl6F6C.js → brain-B7HtSOQU.js} +2 -2
- package/dist/web/public/assets/{brain-euvl6F6C.js.map → brain-B7HtSOQU.js.map} +1 -1
- package/dist/web/public/assets/{briefcase-DPWLbCnA.js → briefcase-mdzuIa__.js} +2 -2
- package/dist/web/public/assets/{briefcase-DPWLbCnA.js.map → briefcase-mdzuIa__.js.map} +1 -1
- package/dist/web/public/assets/{browser-ponyfill-BUutOaRz.js → browser-ponyfill-DBWdeCTC.js} +2 -2
- package/dist/web/public/assets/{browser-ponyfill-BUutOaRz.js.map → browser-ponyfill-DBWdeCTC.js.map} +1 -1
- package/dist/web/public/assets/{chat-Dz9kfaxH.js → chat-CSjtY2rN.js} +3 -3
- package/dist/web/public/assets/{chat-Dz9kfaxH.js.map → chat-CSjtY2rN.js.map} +1 -1
- package/dist/web/public/assets/{chevron-left-BeIh5thq.js → chevron-left-uSfPn636.js} +2 -2
- package/dist/web/public/assets/{chevron-left-BeIh5thq.js.map → chevron-left-uSfPn636.js.map} +1 -1
- package/dist/web/public/assets/{chevron-right-uP_l9MMb.js → chevron-right-CtelqacW.js} +2 -2
- package/dist/web/public/assets/{chevron-right-uP_l9MMb.js.map → chevron-right-CtelqacW.js.map} +1 -1
- package/dist/web/public/assets/{circle-check-CewnjFgv.js → circle-check-8dbL-u7O.js} +2 -2
- package/dist/web/public/assets/{circle-check-CewnjFgv.js.map → circle-check-8dbL-u7O.js.map} +1 -1
- package/dist/web/public/assets/{circle-check-big-C2RTc48c.js → circle-check-big-D8-svk9a.js} +2 -2
- package/dist/web/public/assets/{circle-check-big-C2RTc48c.js.map → circle-check-big-D8-svk9a.js.map} +1 -1
- package/dist/web/public/assets/{circle-x-Ccg1HyV-.js → circle-x-rUxzIz5P.js} +2 -2
- package/dist/web/public/assets/{circle-x-Ccg1HyV-.js.map → circle-x-rUxzIz5P.js.map} +1 -1
- package/dist/web/public/assets/{clock-qxbYSynv.js → clock-CG5dlBGB.js} +2 -2
- package/dist/web/public/assets/{clock-qxbYSynv.js.map → clock-CG5dlBGB.js.map} +1 -1
- package/dist/web/public/assets/{confirm-dialog-DmJq4Td9.js → confirm-dialog-DlUsSur3.js} +2 -2
- package/dist/web/public/assets/{confirm-dialog-DmJq4Td9.js.map → confirm-dialog-DlUsSur3.js.map} +1 -1
- package/dist/web/public/assets/{copy-DxSHRdbc.js → copy-DnC76wFT.js} +2 -2
- package/dist/web/public/assets/{copy-DxSHRdbc.js.map → copy-DnC76wFT.js.map} +1 -1
- package/dist/web/public/assets/{data-table-S7rIjwdO.js → data-table-DswkWUfG.js} +2 -2
- package/dist/web/public/assets/{data-table-S7rIjwdO.js.map → data-table-DswkWUfG.js.map} +1 -1
- package/dist/web/public/assets/dialog-Ceo4YuXy.js +6 -0
- package/dist/web/public/assets/dialog-Ceo4YuXy.js.map +1 -0
- package/dist/web/public/assets/{download-OhsGtnO-.js → download-DF-46tS4.js} +2 -2
- package/dist/web/public/assets/{download-OhsGtnO-.js.map → download-DF-46tS4.js.map} +1 -1
- package/dist/web/public/assets/{email-C1-HxWLF.js → email-CZee26-_.js} +3 -3
- package/dist/web/public/assets/{email-C1-HxWLF.js.map → email-CZee26-_.js.map} +1 -1
- package/dist/web/public/assets/{empty-state-C-qjOHyu.js → empty-state-D9Hi0Atm.js} +2 -2
- package/dist/web/public/assets/{empty-state-C-qjOHyu.js.map → empty-state-D9Hi0Atm.js.map} +1 -1
- package/dist/web/public/assets/{external-link-DRVp9-lb.js → external-link-D64iZa9P.js} +2 -2
- package/dist/web/public/assets/{external-link-DRVp9-lb.js.map → external-link-D64iZa9P.js.map} +1 -1
- package/dist/web/public/assets/{eye-CFhg5BTa.js → eye-sY6WZb7D.js} +2 -2
- package/dist/web/public/assets/{eye-CFhg5BTa.js.map → eye-sY6WZb7D.js.map} +1 -1
- package/dist/web/public/assets/{facts-CGaLWhzi.js → facts-B7bGGwvi.js} +2 -2
- package/dist/web/public/assets/{facts-CGaLWhzi.js.map → facts-B7bGGwvi.js.map} +1 -1
- package/dist/web/public/assets/{goals-C-dJANmn.js → goals-BfQbsvZv.js} +2 -2
- package/dist/web/public/assets/{goals-C-dJANmn.js.map → goals-BfQbsvZv.js.map} +1 -1
- package/dist/web/public/assets/{health-CWcti5h3.js → health-Ba_mY0Ts.js} +2 -2
- package/dist/web/public/assets/{health-CWcti5h3.js.map → health-Ba_mY0Ts.js.map} +1 -1
- package/dist/web/public/assets/{heart-pulse-DmGhKR2W.js → heart-pulse-BjikOVwU.js} +2 -2
- package/dist/web/public/assets/{heart-pulse-DmGhKR2W.js.map → heart-pulse-BjikOVwU.js.map} +1 -1
- package/dist/web/public/assets/{heartbeat-kLoGBNCo.js → heartbeat-BM8LlPes.js} +2 -2
- package/dist/web/public/assets/{heartbeat-kLoGBNCo.js.map → heartbeat-BM8LlPes.js.map} +1 -1
- package/dist/web/public/assets/{hot-BITDoax1.js → hot-BtuLL6n8.js} +2 -2
- package/dist/web/public/assets/{hot-BITDoax1.js.map → hot-BtuLL6n8.js.map} +1 -1
- package/dist/web/public/assets/index-DEWFfW_Z.js +199 -0
- package/dist/web/public/assets/index-DEWFfW_Z.js.map +1 -0
- package/dist/web/public/assets/{installed-Co9WrtQ7.js → installed-Xr8p31ij.js} +2 -2
- package/dist/web/public/assets/{installed-Co9WrtQ7.js.map → installed-Xr8p31ij.js.map} +1 -1
- package/dist/web/public/assets/{jobs-hdHhBEvi.js → jobs-Ddy81Udm.js} +2 -2
- package/dist/web/public/assets/{jobs-hdHhBEvi.js.map → jobs-Ddy81Udm.js.map} +1 -1
- package/dist/web/public/assets/{layout-CQtbOBag.js → layout-BL74fT-L.js} +2 -2
- package/dist/web/public/assets/{layout-CQtbOBag.js.map → layout-BL74fT-L.js.map} +1 -1
- package/dist/web/public/assets/{layout-bDMXIKIR.js → layout-Bn2qUxcK.js} +2 -2
- package/dist/web/public/assets/{layout-bDMXIKIR.js.map → layout-Bn2qUxcK.js.map} +1 -1
- package/dist/web/public/assets/{layout-BMXC1Uh1.js → layout-Bp4SAA8_.js} +2 -2
- package/dist/web/public/assets/{layout-BMXC1Uh1.js.map → layout-Bp4SAA8_.js.map} +1 -1
- package/dist/web/public/assets/{layout-CysVsySh.js → layout-CZ9pGnW8.js} +2 -2
- package/dist/web/public/assets/{layout-CysVsySh.js.map → layout-CZ9pGnW8.js.map} +1 -1
- package/dist/web/public/assets/{layout-CyBGneZ9.js → layout-pasFRkKV.js} +2 -2
- package/dist/web/public/assets/{layout-CyBGneZ9.js.map → layout-pasFRkKV.js.map} +1 -1
- package/dist/web/public/assets/llm-yp7b5xxL.js +7 -0
- package/dist/web/public/assets/llm-yp7b5xxL.js.map +1 -0
- package/dist/web/public/assets/{loader-circle-9VUMGitw.js → loader-circle-Bbw4pEyE.js} +2 -2
- package/dist/web/public/assets/{loader-circle-9VUMGitw.js.map → loader-circle-Bbw4pEyE.js.map} +1 -1
- package/dist/web/public/assets/{map-pin-BXYvvHry.js → map-pin-DIXHUQgM.js} +2 -2
- package/dist/web/public/assets/{map-pin-BXYvvHry.js.map → map-pin-DIXHUQgM.js.map} +1 -1
- package/dist/web/public/assets/{mcp-BgLdlwSn.js → mcp-DyaljIM_.js} +2 -2
- package/dist/web/public/assets/{mcp-BgLdlwSn.js.map → mcp-DyaljIM_.js.map} +1 -1
- package/dist/web/public/assets/memos-Dkoc157i.js +12 -0
- package/dist/web/public/assets/memos-Dkoc157i.js.map +1 -0
- package/dist/web/public/assets/{messengers-7Phqea62.js → messengers-CcyGDeUI.js} +2 -2
- package/dist/web/public/assets/{messengers-7Phqea62.js.map → messengers-CcyGDeUI.js.map} +1 -1
- package/dist/web/public/assets/{mobile-CV5b6D2W.js → mobile-DqzIv4Xb.js} +2 -2
- package/dist/web/public/assets/{mobile-CV5b6D2W.js.map → mobile-DqzIv4Xb.js.map} +1 -1
- package/dist/web/public/assets/{native-agent-QvIa6LjE.js → native-agent-BQ7WaRGK.js} +2 -2
- package/dist/web/public/assets/{native-agent-QvIa6LjE.js.map → native-agent-BQ7WaRGK.js.map} +1 -1
- package/dist/web/public/assets/{network-BXhEjGhE.js → network-B_yUFAqC.js} +2 -2
- package/dist/web/public/assets/{network-BXhEjGhE.js.map → network-B_yUFAqC.js.map} +1 -1
- package/dist/web/public/assets/{outbox-DHQL7TQb.js → outbox-l8aVOZqO.js} +2 -2
- package/dist/web/public/assets/{outbox-DHQL7TQb.js.map → outbox-l8aVOZqO.js.map} +1 -1
- package/dist/web/public/assets/{pagination-VKuPb1Ot.js → pagination-BAKRGKa9.js} +2 -2
- package/dist/web/public/assets/{pagination-VKuPb1Ot.js.map → pagination-BAKRGKa9.js.map} +1 -1
- package/dist/web/public/assets/{persona-CWug2GLR.js → persona-D3VL9Rg1.js} +2 -2
- package/dist/web/public/assets/{persona-CWug2GLR.js.map → persona-D3VL9Rg1.js.map} +1 -1
- package/dist/web/public/assets/{plans-CZoEs5SY.js → plans-BBB5e9my.js} +2 -2
- package/dist/web/public/assets/{plans-CZoEs5SY.js.map → plans-BBB5e9my.js.map} +1 -1
- package/dist/web/public/assets/{play-CfSn5Vdl.js → play-7-Wd369f.js} +2 -2
- package/dist/web/public/assets/{play-CfSn5Vdl.js.map → play-7-Wd369f.js.map} +1 -1
- package/dist/web/public/assets/{plus-Z8l4CiqJ.js → plus-B0sfZy-j.js} +2 -2
- package/dist/web/public/assets/{plus-Z8l4CiqJ.js.map → plus-B0sfZy-j.js.map} +1 -1
- package/dist/web/public/assets/{policy-CutDSEPW.js → policy-BM1WRXH0.js} +2 -2
- package/dist/web/public/assets/{policy-CutDSEPW.js.map → policy-BM1WRXH0.js.map} +1 -1
- package/dist/web/public/assets/{qr-code-DgU5aiM6.js → qr-code-DcKs5fi3.js} +2 -2
- package/dist/web/public/assets/{qr-code-DgU5aiM6.js.map → qr-code-DcKs5fi3.js.map} +1 -1
- package/dist/web/public/assets/{react-Cb2sDjhD.js → react-DlP5eolq.js} +2 -2
- package/dist/web/public/assets/{react-Cb2sDjhD.js.map → react-DlP5eolq.js.map} +1 -1
- package/dist/web/public/assets/{refresh-ccw-D2CWiyU_.js → refresh-ccw-uNKeBeRl.js} +2 -2
- package/dist/web/public/assets/{refresh-ccw-D2CWiyU_.js.map → refresh-ccw-uNKeBeRl.js.map} +1 -1
- package/dist/web/public/assets/{reminders-Cb6Izedg.js → reminders-DHM8K0_O.js} +2 -2
- package/dist/web/public/assets/{reminders-Cb6Izedg.js.map → reminders-DHM8K0_O.js.map} +1 -1
- package/dist/web/public/assets/{save-DB0BDYTs.js → save-qwJa5_SA.js} +2 -2
- package/dist/web/public/assets/{save-DB0BDYTs.js.map → save-qwJa5_SA.js.map} +1 -1
- package/dist/web/public/assets/{schedules-8mSjE14D.js → schedules-Bcd0wbT4.js} +2 -2
- package/dist/web/public/assets/{schedules-8mSjE14D.js.map → schedules-Bcd0wbT4.js.map} +1 -1
- package/dist/web/public/assets/{search-Con69NhG.js → search-BUlzNWrj.js} +2 -2
- package/dist/web/public/assets/{search-Con69NhG.js.map → search-BUlzNWrj.js.map} +1 -1
- package/dist/web/public/assets/{search-B4fHilZ0.js → search-i1tP2maJ.js} +2 -2
- package/dist/web/public/assets/{search-B4fHilZ0.js.map → search-i1tP2maJ.js.map} +1 -1
- package/dist/web/public/assets/{security-BTe3zUg8.js → security-DgJyTT4g.js} +2 -2
- package/dist/web/public/assets/{security-BTe3zUg8.js.map → security-DgJyTT4g.js.map} +1 -1
- package/dist/web/public/assets/{service-C7SqcwfL.js → service-A0Hzear0.js} +2 -2
- package/dist/web/public/assets/{service-C7SqcwfL.js.map → service-A0Hzear0.js.map} +1 -1
- package/dist/web/public/assets/{shield-alert-CKFVsGgI.js → shield-alert-DrnN6fz_.js} +2 -2
- package/dist/web/public/assets/{shield-alert-CKFVsGgI.js.map → shield-alert-DrnN6fz_.js.map} +1 -1
- package/dist/web/public/assets/{status-badge-BSkpyN4D.js → status-badge-Ryzf96Pl.js} +2 -2
- package/dist/web/public/assets/{status-badge-BSkpyN4D.js.map → status-badge-Ryzf96Pl.js.map} +1 -1
- package/dist/web/public/assets/{subtasks-Bel-I1Sk.js → subtasks-Bzh3o3EF.js} +2 -2
- package/dist/web/public/assets/{subtasks-Bel-I1Sk.js.map → subtasks-Bzh3o3EF.js.map} +1 -1
- package/dist/web/public/assets/{table-CPn1MRcy.js → table-BbAOSyc8.js} +2 -2
- package/dist/web/public/assets/{table-CPn1MRcy.js.map → table-BbAOSyc8.js.map} +1 -1
- package/dist/web/public/assets/{topn-Ba3RjcK1.js → topn-DkhYw-Gp.js} +2 -2
- package/dist/web/public/assets/{topn-Ba3RjcK1.js.map → topn-DkhYw-Gp.js.map} +1 -1
- package/dist/web/public/assets/{trash-2-Dfov8aHD.js → trash-2-CA0cLpnU.js} +2 -2
- package/dist/web/public/assets/{trash-2-Dfov8aHD.js.map → trash-2-CA0cLpnU.js.map} +1 -1
- package/dist/web/public/assets/{use-background-tasks-BQrEeUwY.js → use-background-tasks-B64YjlA8.js} +2 -2
- package/dist/web/public/assets/{use-background-tasks-BQrEeUwY.js.map → use-background-tasks-B64YjlA8.js.map} +1 -1
- package/dist/web/public/assets/{use-event-stream-DgGpGKop.js → use-event-stream-I1lMFEfh.js} +2 -2
- package/dist/web/public/assets/{use-event-stream-DgGpGKop.js.map → use-event-stream-I1lMFEfh.js.map} +1 -1
- package/dist/web/public/assets/{use-llm-admin-DYekqogG.js → use-llm-admin-DY2axI4D.js} +2 -2
- package/dist/web/public/assets/{use-llm-admin-DYekqogG.js.map → use-llm-admin-DY2axI4D.js.map} +1 -1
- package/dist/web/public/assets/{use-memory-DbJ4pP2Z.js → use-memory-BYEjVWbU.js} +2 -2
- package/dist/web/public/assets/{use-memory-DbJ4pP2Z.js.map → use-memory-BYEjVWbU.js.map} +1 -1
- package/dist/web/public/assets/{use-observability-C2M6WZ9W.js → use-observability-Coj02yDo.js} +2 -2
- package/dist/web/public/assets/{use-observability-C2M6WZ9W.js.map → use-observability-Coj02yDo.js.map} +1 -1
- package/dist/web/public/assets/{use-settings-DMdaoWsB.js → use-settings-i1MhlkyC.js} +2 -2
- package/dist/web/public/assets/{use-settings-DMdaoWsB.js.map → use-settings-i1MhlkyC.js.map} +1 -1
- package/dist/web/public/assets/{use-workspace-BHG7h3jQ.js → use-workspace-DgEM35PY.js} +2 -2
- package/dist/web/public/assets/{use-workspace-BHG7h3jQ.js.map → use-workspace-DgEM35PY.js.map} +1 -1
- package/dist/web/public/assets/{useQuery-PdiC7-sY.js → useQuery-CY2iazjN.js} +2 -2
- package/dist/web/public/assets/{useQuery-PdiC7-sY.js.map → useQuery-CY2iazjN.js.map} +1 -1
- package/dist/web/public/assets/{vector-DnZM3OXU.js → vector-Ic76u2hY.js} +2 -2
- package/dist/web/public/assets/{vector-DnZM3OXU.js.map → vector-Ic76u2hY.js.map} +1 -1
- package/dist/web/public/assets/{viewer-Dz6k0YKp.js → viewer-BXbUN1Rl.js} +2 -2
- package/dist/web/public/assets/{viewer-Dz6k0YKp.js.map → viewer-BXbUN1Rl.js.map} +1 -1
- package/dist/web/public/assets/{workspace-BnXrWS3j.js → workspace-CUg0JPn6.js} +3 -3
- package/dist/web/public/assets/{workspace-BnXrWS3j.js.map → workspace-CUg0JPn6.js.map} +1 -1
- package/dist/web/public/assets/{workspaces-CSS_UBEi.js → workspaces-C-wb5FQj.js} +2 -2
- package/dist/web/public/assets/{workspaces-CSS_UBEi.js.map → workspaces-C-wb5FQj.js.map} +1 -1
- package/dist/web/public/assets/{x-DG-JKVw_.js → x-D1iSuoqg.js} +2 -2
- package/dist/web/public/assets/{x-DG-JKVw_.js.map → x-D1iSuoqg.js.map} +1 -1
- package/dist/web/public/index.html +2 -2
- package/dist/web/server.d.ts +23 -0
- package/dist/web/server.d.ts.map +1 -1
- package/dist/web/server.js +109 -20
- package/dist/web/server.js.map +1 -1
- package/package.json +3 -2
- package/dist/web/public/assets/dialog-bAIDaO-6.js +0 -6
- package/dist/web/public/assets/dialog-bAIDaO-6.js.map +0 -1
- package/dist/web/public/assets/index-O0BQoyzo.js +0 -199
- package/dist/web/public/assets/index-O0BQoyzo.js.map +0 -1
- package/dist/web/public/assets/llm-CPIRNQU2.js +0 -7
- package/dist/web/public/assets/llm-CPIRNQU2.js.map +0 -1
- package/dist/web/public/assets/memos-CfneX9DH.js +0 -12
- package/dist/web/public/assets/memos-CfneX9DH.js.map +0 -1
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"persona-CWug2GLR.js","sources":["../../src/routes/memory/persona.tsx"],"sourcesContent":["/**\n * /memory/persona — view + edit the per-user persona summary +\n * trigger the consolidation pass.\n *\n * Layout: status strip (last consolidate run + button) on top, then\n * the persona editor (textarea + Save + Delete). The editor enters\n * an \"unsaved changes\" state when the textarea diverges from the\n * server-rendered summary; Save flips back to clean.\n *\n * Consolidate flow:\n * * Trigger button POSTs /api/memory/consolidate; the backend\n * replies 202 with a jobId.\n * * /api/memory/consolidate/status is polled every 3s by the\n * hook so the operator sees phase transitions live (running →\n * done / failed) without manual refresh.\n * * On `done`, the persona query is invalidated — the new\n * summary appears in the textarea automatically.\n */\n\nimport { useEffect, useState } from 'react'\nimport { useSearchParams } from 'react-router-dom'\nimport { useTranslation } from 'react-i18next'\nimport { toast } from 'sonner'\nimport { Brain, CheckCircle, Loader2, Play, RefreshCcw, Trash2, XCircle } from 'lucide-react'\n\nimport { EmptyState } from '@/components/common/empty-state'\nimport { ConfirmDialog } from '@/components/common/confirm-dialog'\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport { Label } from '@/components/ui/label'\nimport {\n useMemoryPersona,\n useUpdatePersona,\n useDeletePersona,\n useConsolidateStatus,\n useTriggerConsolidate,\n} from '@/hooks/use-memory'\nimport { describeError } from '@/lib/api/errors'\nimport { cn } from '@/lib/utils'\nimport type { ConsolidateJob } from '@/types/api'\n\nexport default function MemoryPersonaRoute(): JSX.Element {\n const { t } = useTranslation(['memory', 'common'])\n const [params] = useSearchParams()\n const userKey = params.get('user') ?? ''\n\n if (!userKey) {\n return (\n <div className=\"mx-auto max-w-3xl\">\n <EmptyState\n icon={<Brain />}\n title={t('noUserSelected.title')}\n description={t('noUserSelected.description')}\n />\n </div>\n )\n }\n\n return <PersonaEditor userKey={userKey} />\n}\n\ninterface PersonaEditorProps {\n userKey: string\n}\n\nfunction PersonaEditor({ userKey }: PersonaEditorProps): JSX.Element {\n const { t } = useTranslation(['memory', 'common'])\n const personaQuery = useMemoryPersona(userKey)\n const persona = personaQuery.data\n\n const consolidate = useTriggerConsolidate()\n const status = useConsolidateStatus()\n const latestJob = status.data?.jobs[0]\n\n const updatePersona = useUpdatePersona()\n const deletePersona = useDeletePersona()\n const [confirmDelete, setConfirmDelete] = useState(false)\n\n /** Editor state — initialised from the server summary; tracks\n * dirtiness via reference comparison after each save. */\n const [draft, setDraft] = useState(persona?.summary ?? '')\n useEffect(() => {\n setDraft(persona?.summary ?? '')\n }, [persona?.summary])\n const dirty = draft !== (persona?.summary ?? '')\n\n async function onSave(): Promise<void> {\n const trimmed = draft.trim()\n if (!trimmed) return\n try {\n await updatePersona.mutateAsync({ user_key: userKey, body: { summary: trimmed } })\n toast.success(t('persona.saved'))\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n }\n }\n\n async function onConfirmDelete(): Promise<void> {\n try {\n await deletePersona.mutateAsync(userKey)\n toast.success(t('common:actions.delete'))\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n throw err\n }\n }\n\n async function onTrigger(): Promise<void> {\n try {\n await consolidate.mutateAsync()\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n }\n }\n\n return (\n <div className=\"mx-auto flex max-w-4xl flex-col gap-4\">\n <header className=\"flex flex-col gap-1\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <h1 className=\"text-xl font-semibold\">{t('persona.title')}</h1>\n <Button\n variant=\"ghost\"\n size=\"sm\"\n className=\"ml-auto\"\n onClick={() => personaQuery.refetch()}\n disabled={personaQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {personaQuery.isFetching ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('actions.refresh', { ns: 'common' })}</span>\n </Button>\n </div>\n <p className=\"text-sm text-text-dim\">{t('persona.subtitle')}</p>\n </header>\n\n {/* Consolidate strip */}\n <div className=\"rounded-md border border-border bg-surface p-3\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <span className=\"font-medium text-sm text-text\">{t('persona.consolidate.trigger')}</span>\n <ConsolidateBadge job={latestJob} />\n <Button\n variant=\"default\"\n size=\"sm\"\n onClick={() => void onTrigger()}\n disabled={consolidate.isPending || latestJob?.phase === 'running'}\n className=\"ml-auto\"\n >\n {consolidate.isPending\n ? <Loader2 className=\"h-4 w-4 animate-spin\" />\n : <Play className=\"h-4 w-4\" />}\n {consolidate.isPending\n ? t('persona.consolidate.triggering')\n : t('persona.consolidate.trigger')}\n </Button>\n </div>\n {latestJob?.phase === 'done' && (latestJob.result.users != null || latestJob.result.updated != null) && (\n <p className=\"mt-2 text-xs text-text-dim\">\n {t('persona.consolidate.result', {\n users: latestJob.result.users ?? 0,\n updated: latestJob.result.updated ?? 0,\n })}\n </p>\n )}\n {latestJob?.phase === 'failed' && latestJob.result.error && (\n <p className=\"mt-2 text-xs text-danger\">{latestJob.result.error}</p>\n )}\n </div>\n\n {/* Editor */}\n {personaQuery.isLoading ? (\n <div className=\"h-48 w-full rounded-md bg-surface-2 animate-pulse\" />\n ) : !persona ? (\n <>\n <EmptyState\n icon={<Brain />}\n title={t('persona.empty.title')}\n description={t('persona.empty.description')}\n />\n {/* Even with no persona, the operator can still type one in\n and save — the upsert handler creates a new row. */}\n <PersonaTextarea\n draft={draft}\n onChange={setDraft}\n onSave={() => void onSave()}\n saving={updatePersona.isPending}\n dirty={dirty}\n canDelete={false}\n onDelete={() => setConfirmDelete(true)}\n />\n </>\n ) : (\n <>\n {persona.updated_at > 0 && (\n <div className=\"text-xs text-text-dim\">\n {t('persona.updated', { at: formatEpoch(persona.updated_at) })}\n </div>\n )}\n <PersonaTextarea\n draft={draft}\n onChange={setDraft}\n onSave={() => void onSave()}\n saving={updatePersona.isPending}\n dirty={dirty}\n canDelete\n onDelete={() => setConfirmDelete(true)}\n />\n </>\n )}\n\n <ConfirmDialog\n open={confirmDelete}\n onOpenChange={setConfirmDelete}\n title={t('persona.confirmDelete')}\n description={t('persona.confirmDeleteDesc')}\n intent=\"danger\"\n confirmLabel={t('persona.delete')}\n onConfirm={onConfirmDelete}\n />\n </div>\n )\n}\n\ninterface PersonaTextareaProps {\n draft: string\n onChange: (next: string) => void\n onSave: () => void\n saving: boolean\n dirty: boolean\n canDelete: boolean\n onDelete: () => void\n}\n\nfunction PersonaTextarea({\n draft, onChange, onSave, saving, dirty, canDelete, onDelete,\n}: PersonaTextareaProps): JSX.Element {\n const { t } = useTranslation('memory')\n return (\n <div className=\"flex flex-col gap-2\">\n <Label htmlFor=\"persona-editor\" className=\"text-sm text-text-dim\">\n {t('persona.editorLabel')}\n </Label>\n <textarea\n id=\"persona-editor\"\n value={draft}\n onChange={(e) => onChange(e.target.value)}\n rows={12}\n className={cn(\n 'w-full resize-y rounded-md border bg-bg px-3 py-2',\n 'font-mono text-sm leading-6',\n 'focus:outline-none focus:ring-2 focus:ring-accent focus:ring-offset-1 focus:ring-offset-bg',\n dirty ? 'border-accent' : 'border-border',\n )}\n />\n <div className=\"flex flex-wrap items-center gap-2\">\n {canDelete && (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n onClick={onDelete}\n >\n <Trash2 className=\"h-3 w-3\" />\n {t('persona.delete')}\n </Button>\n )}\n <Button\n type=\"button\"\n size=\"sm\"\n className=\"ml-auto\"\n disabled={!dirty || saving || draft.trim().length === 0}\n onClick={onSave}\n >\n {saving ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : null}\n {t('persona.save')}\n </Button>\n </div>\n </div>\n )\n}\n\ninterface ConsolidateBadgeProps {\n job: ConsolidateJob | undefined\n}\n\nfunction ConsolidateBadge({ job }: ConsolidateBadgeProps): JSX.Element | null {\n const { t } = useTranslation('memory')\n if (!job) return null\n if (job.phase === 'running') {\n return (\n <Badge variant=\"info\">\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n {t('persona.consolidate.running')}\n </Badge>\n )\n }\n if (job.phase === 'done') {\n return (\n <Badge variant=\"success\">\n <CheckCircle className=\"h-3 w-3\" />\n {t('persona.consolidate.lastRun', { at: formatEpoch(job.finishedAt ?? job.startedAt) })}\n </Badge>\n )\n }\n return (\n <Badge variant=\"danger\">\n <XCircle className=\"h-3 w-3\" />\n {t('persona.consolidate.doneFailed')}\n </Badge>\n )\n}\n\nfunction formatEpoch(ms: number): string {\n try {\n const d = new Date(ms)\n if (Number.isNaN(d.getTime())) return String(ms)\n return d.toLocaleString(undefined, { month: 'short', day: 'numeric', hour: '2-digit', minute: '2-digit' })\n } catch {\n return String(ms)\n }\n}\n"],"names":["MemoryPersonaRoute","useTranslation","params","useSearchParams","userKey","jsx","PersonaEditor","EmptyState","Brain","t","personaQuery","useMemoryPersona","persona","consolidate","useTriggerConsolidate","latestJob","useConsolidateStatus","updatePersona","useUpdatePersona","deletePersona","useDeletePersona","confirmDelete","setConfirmDelete","useState","draft","setDraft","useEffect","dirty","onSave","trimmed","toast","err","message","describeError","onConfirmDelete","onTrigger","jsxs","Button","Loader2","RefreshCcw","ConsolidateBadge","Play","Fragment","formatEpoch","PersonaTextarea","ConfirmDialog","onChange","saving","canDelete","onDelete","Label","e","cn","Trash2","job","Badge","CheckCircle","XCircle","ms","d"],"mappings":"yrBAyCA,SAAwBA,IAAkC,CACxD,KAAM,CAAE,CAAA,EAAMC,EAAe,CAAC,SAAU,QAAQ,CAAC,EAC3C,CAACC,CAAM,EAAIC,EAAA,EACXC,EAAUF,EAAO,IAAI,MAAM,GAAK,GAEtC,OAAKE,EAYEC,MAACC,GAAc,QAAAF,EAAkB,EAVpCC,EAAAA,IAAC,MAAA,CAAI,UAAU,oBACb,SAAAA,EAAAA,IAACE,EAAA,CACC,WAAOC,EAAA,EAAM,EACb,MAAO,EAAE,sBAAsB,EAC/B,YAAa,EAAE,4BAA4B,CAAA,CAAA,EAE/C,CAKN,CAMA,SAASF,EAAc,CAAE,QAAAF,GAA4C,CACnE,KAAM,CAAE,EAAAK,CAAA,EAAMR,EAAe,CAAC,SAAU,QAAQ,CAAC,EAC3CS,EAAeC,EAAiBP,CAAO,EACvCQ,EAAUF,EAAa,KAEvBG,EAAcC,EAAA,EAEdC,EADSC,EAAA,EACU,MAAM,KAAK,CAAC,EAE/BC,EAAgBC,EAAA,EAChBC,EAAgBC,EAAA,EAChB,CAACC,EAAeC,CAAgB,EAAIC,EAAAA,SAAS,EAAK,EAIlD,CAACC,EAAOC,CAAQ,EAAIF,EAAAA,SAASX,GAAS,SAAW,EAAE,EACzDc,EAAAA,UAAU,IAAM,CACdD,EAASb,GAAS,SAAW,EAAE,CACjC,EAAG,CAACA,GAAS,OAAO,CAAC,EACrB,MAAMe,EAAQH,KAAWZ,GAAS,SAAW,IAE7C,eAAegB,GAAwB,CACrC,MAAMC,EAAUL,EAAM,KAAA,EACtB,GAAKK,EACL,GAAI,CACF,MAAMZ,EAAc,YAAY,CAAE,SAAUb,EAAS,KAAM,CAAE,QAASyB,CAAA,EAAW,EACjFC,EAAM,QAAQrB,EAAE,eAAe,CAAC,CAClC,OAASsB,EAAK,CACZ,KAAM,CAAE,QAAAC,CAAA,EAAYC,EAAcF,EAAKtB,CAAC,EACxCqB,EAAM,MAAME,CAAO,CACrB,CACF,CAEA,eAAeE,GAAiC,CAC9C,GAAI,CACF,MAAMf,EAAc,YAAYf,CAAO,EACvC0B,EAAM,QAAQrB,EAAE,uBAAuB,CAAC,CAC1C,OAASsB,EAAK,CACZ,KAAM,CAAE,QAAAC,CAAA,EAAYC,EAAcF,EAAKtB,CAAC,EACxCqB,MAAAA,EAAM,MAAME,CAAO,EACbD,CACR,CACF,CAEA,eAAeI,GAA2B,CACxC,GAAI,CACF,MAAMtB,EAAY,YAAA,CACpB,OAASkB,EAAK,CACZ,KAAM,CAAE,QAAAC,CAAA,EAAYC,EAAcF,EAAKtB,CAAC,EACxCqB,EAAM,MAAME,CAAO,CACrB,CACF,CAEA,OACEI,EAAAA,KAAC,MAAA,CAAI,UAAU,wCACb,SAAA,CAAAA,EAAAA,KAAC,SAAA,CAAO,UAAU,sBAChB,SAAA,CAAAA,EAAAA,KAAC,MAAA,CAAI,UAAU,oCACb,SAAA,CAAA/B,MAAC,KAAA,CAAG,UAAU,wBAAyB,SAAAI,EAAE,eAAe,EAAE,EAC1D2B,EAAAA,KAACC,EAAA,CACC,QAAQ,QACR,KAAK,KACL,UAAU,UACV,QAAS,IAAM3B,EAAa,QAAA,EAC5B,SAAUA,EAAa,WACvB,aAAYD,EAAE,kBAAmB,CAAE,GAAI,SAAU,EAEhD,SAAA,CAAAC,EAAa,iBAAc4B,EAAA,CAAQ,UAAU,uBAAuB,EAAKjC,EAAAA,IAACkC,EAAA,CAAW,UAAU,SAAA,CAAU,EAC1GlC,EAAAA,IAAC,OAAA,CAAK,UAAU,mBAAoB,SAAAI,EAAE,kBAAmB,CAAE,GAAI,QAAA,CAAU,CAAA,CAAE,CAAA,CAAA,CAAA,CAC7E,EACF,QACC,IAAA,CAAE,UAAU,wBAAyB,SAAAA,EAAE,kBAAkB,CAAA,CAAE,CAAA,EAC9D,EAGA2B,EAAAA,KAAC,MAAA,CAAI,UAAU,iDACb,SAAA,CAAAA,EAAAA,KAAC,MAAA,CAAI,UAAU,oCACb,SAAA,CAAA/B,MAAC,OAAA,CAAK,UAAU,gCAAiC,SAAAI,EAAE,6BAA6B,EAAE,EAClFJ,EAAAA,IAACmC,EAAA,CAAiB,IAAKzB,CAAA,CAAW,EAClCqB,EAAAA,KAACC,EAAA,CACC,QAAQ,UACR,KAAK,KACL,QAAS,IAAM,KAAKF,EAAA,EACpB,SAAUtB,EAAY,WAAaE,GAAW,QAAU,UACxD,UAAU,UAET,SAAA,CAAAF,EAAY,gBACRyB,EAAA,CAAQ,UAAU,uBAAuB,EAC1CjC,EAAAA,IAACoC,EAAA,CAAK,UAAU,SAAA,CAAU,EAC7B5B,EAAY,UACTJ,EAAE,gCAAgC,EAClCA,EAAE,6BAA6B,CAAA,CAAA,CAAA,CACrC,EACF,EACCM,GAAW,QAAU,SAAWA,EAAU,OAAO,OAAS,MAAQA,EAAU,OAAO,SAAW,OAC7FV,EAAAA,IAAC,IAAA,CAAE,UAAU,6BACV,WAAE,6BAA8B,CAC/B,MAASU,EAAU,OAAO,OAAS,EACnC,QAASA,EAAU,OAAO,SAAW,CAAA,CACtC,EACH,EAEDA,GAAW,QAAU,UAAYA,EAAU,OAAO,OACjDV,EAAAA,IAAC,IAAA,CAAE,UAAU,2BAA4B,SAAAU,EAAU,OAAO,KAAA,CAAM,CAAA,EAEpE,EAGCL,EAAa,UACZL,EAAAA,IAAC,MAAA,CAAI,UAAU,oDAAoD,EAChEO,EAoBHwB,EAAAA,KAAAM,EAAAA,SAAA,CACG,SAAA,CAAA9B,EAAQ,WAAa,GACpBP,EAAAA,IAAC,MAAA,CAAI,UAAU,wBACZ,SAAAI,EAAE,kBAAmB,CAAE,GAAIkC,EAAY/B,EAAQ,UAAU,CAAA,CAAG,EAC/D,EAEFP,EAAAA,IAACuC,EAAA,CACC,MAAApB,EACA,SAAUC,EACV,OAAQ,IAAM,KAAKG,EAAA,EACnB,OAAQX,EAAc,UACtB,MAAAU,EACA,UAAS,GACT,SAAU,IAAML,EAAiB,EAAI,CAAA,CAAA,CACvC,EACF,EAlCAc,EAAAA,KAAAM,EAAAA,SAAA,CACE,SAAA,CAAArC,EAAAA,IAACE,EAAA,CACC,WAAOC,EAAA,EAAM,EACb,MAAOC,EAAE,qBAAqB,EAC9B,YAAaA,EAAE,2BAA2B,CAAA,CAAA,EAI5CJ,EAAAA,IAACuC,EAAA,CACC,MAAApB,EACA,SAAUC,EACV,OAAQ,IAAM,KAAKG,EAAA,EACnB,OAAQX,EAAc,UACtB,MAAAU,EACA,UAAW,GACX,SAAU,IAAML,EAAiB,EAAI,CAAA,CAAA,CACvC,CAAA,CACF,EAoBFjB,EAAAA,IAACwC,EAAA,CACC,KAAMxB,EACN,aAAcC,EACd,MAAOb,EAAE,uBAAuB,EAChC,YAAaA,EAAE,2BAA2B,EAC1C,OAAO,SACP,aAAcA,EAAE,gBAAgB,EAChC,UAAWyB,CAAA,CAAA,CACb,EACF,CAEJ,CAYA,SAASU,EAAgB,CACvB,MAAApB,EAAO,SAAAsB,EAAU,OAAAlB,EAAQ,OAAAmB,EAAQ,MAAApB,EAAO,UAAAqB,EAAW,SAAAC,CACrD,EAAsC,CACpC,KAAM,CAAE,EAAAxC,CAAA,EAAMR,EAAe,QAAQ,EACrC,OACEmC,EAAAA,KAAC,MAAA,CAAI,UAAU,sBACb,SAAA,CAAA/B,EAAAA,IAAC6C,GAAM,QAAQ,iBAAiB,UAAU,wBACvC,SAAAzC,EAAE,qBAAqB,EAC1B,EACAJ,EAAAA,IAAC,WAAA,CACC,GAAG,iBACH,MAAOmB,EACP,SAAW2B,GAAML,EAASK,EAAE,OAAO,KAAK,EACxC,KAAM,GACN,UAAWC,EACT,oDACA,8BACA,6FACAzB,EAAQ,gBAAkB,eAAA,CAC5B,CAAA,EAEFS,EAAAA,KAAC,MAAA,CAAI,UAAU,oCACZ,SAAA,CAAAY,GACCZ,EAAAA,KAACC,EAAA,CACC,KAAK,SACL,QAAQ,UACR,KAAK,KACL,QAASY,EAET,SAAA,CAAA5C,EAAAA,IAACgD,EAAA,CAAO,UAAU,SAAA,CAAU,EAC3B5C,EAAE,gBAAgB,CAAA,CAAA,CAAA,EAGvB2B,EAAAA,KAACC,EAAA,CACC,KAAK,SACL,KAAK,KACL,UAAU,UACV,SAAU,CAACV,GAASoB,GAAUvB,EAAM,KAAA,EAAO,SAAW,EACtD,QAASI,EAER,SAAA,CAAAmB,EAAS1C,EAAAA,IAACiC,EAAA,CAAQ,UAAU,sBAAA,CAAuB,EAAK,KACxD7B,EAAE,cAAc,CAAA,CAAA,CAAA,CACnB,CAAA,CACF,CAAA,EACF,CAEJ,CAMA,SAAS+B,EAAiB,CAAE,IAAAc,GAAkD,CAC5E,KAAM,CAAE,EAAA7C,CAAA,EAAMR,EAAe,QAAQ,EACrC,OAAKqD,EACDA,EAAI,QAAU,UAEdlB,EAAAA,KAACmB,EAAA,CAAM,QAAQ,OACb,SAAA,CAAAlD,EAAAA,IAACiC,EAAA,CAAQ,UAAU,sBAAA,CAAuB,EACzC7B,EAAE,6BAA6B,CAAA,EAClC,EAGA6C,EAAI,QAAU,OAEdlB,EAAAA,KAACmB,EAAA,CAAM,QAAQ,UACb,SAAA,CAAAlD,EAAAA,IAACmD,EAAA,CAAY,UAAU,SAAA,CAAU,EAChC/C,EAAE,8BAA+B,CAAE,GAAIkC,EAAYW,EAAI,YAAcA,EAAI,SAAS,CAAA,CAAG,CAAA,EACxF,EAIFlB,EAAAA,KAACmB,EAAA,CAAM,QAAQ,SACb,SAAA,CAAAlD,EAAAA,IAACoD,EAAA,CAAQ,UAAU,SAAA,CAAU,EAC5BhD,EAAE,gCAAgC,CAAA,EACrC,EArBe,IAuBnB,CAEA,SAASkC,EAAYe,EAAoB,CACvC,GAAI,CACF,MAAMC,EAAI,IAAI,KAAKD,CAAE,EACrB,OAAI,OAAO,MAAMC,EAAE,QAAA,CAAS,EAAU,OAAOD,CAAE,EACxCC,EAAE,eAAe,OAAW,CAAE,MAAO,QAAS,IAAK,UAAW,KAAM,UAAW,OAAQ,SAAA,CAAW,CAC3G,MAAQ,CACN,OAAO,OAAOD,CAAE,CAClB,CACF"}
|
|
1
|
+
{"version":3,"file":"persona-D3VL9Rg1.js","sources":["../../src/routes/memory/persona.tsx"],"sourcesContent":["/**\n * /memory/persona — view + edit the per-user persona summary +\n * trigger the consolidation pass.\n *\n * Layout: status strip (last consolidate run + button) on top, then\n * the persona editor (textarea + Save + Delete). The editor enters\n * an \"unsaved changes\" state when the textarea diverges from the\n * server-rendered summary; Save flips back to clean.\n *\n * Consolidate flow:\n * * Trigger button POSTs /api/memory/consolidate; the backend\n * replies 202 with a jobId.\n * * /api/memory/consolidate/status is polled every 3s by the\n * hook so the operator sees phase transitions live (running →\n * done / failed) without manual refresh.\n * * On `done`, the persona query is invalidated — the new\n * summary appears in the textarea automatically.\n */\n\nimport { useEffect, useState } from 'react'\nimport { useSearchParams } from 'react-router-dom'\nimport { useTranslation } from 'react-i18next'\nimport { toast } from 'sonner'\nimport { Brain, CheckCircle, Loader2, Play, RefreshCcw, Trash2, XCircle } from 'lucide-react'\n\nimport { EmptyState } from '@/components/common/empty-state'\nimport { ConfirmDialog } from '@/components/common/confirm-dialog'\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport { Label } from '@/components/ui/label'\nimport {\n useMemoryPersona,\n useUpdatePersona,\n useDeletePersona,\n useConsolidateStatus,\n useTriggerConsolidate,\n} from '@/hooks/use-memory'\nimport { describeError } from '@/lib/api/errors'\nimport { cn } from '@/lib/utils'\nimport type { ConsolidateJob } from '@/types/api'\n\nexport default function MemoryPersonaRoute(): JSX.Element {\n const { t } = useTranslation(['memory', 'common'])\n const [params] = useSearchParams()\n const userKey = params.get('user') ?? ''\n\n if (!userKey) {\n return (\n <div className=\"mx-auto max-w-3xl\">\n <EmptyState\n icon={<Brain />}\n title={t('noUserSelected.title')}\n description={t('noUserSelected.description')}\n />\n </div>\n )\n }\n\n return <PersonaEditor userKey={userKey} />\n}\n\ninterface PersonaEditorProps {\n userKey: string\n}\n\nfunction PersonaEditor({ userKey }: PersonaEditorProps): JSX.Element {\n const { t } = useTranslation(['memory', 'common'])\n const personaQuery = useMemoryPersona(userKey)\n const persona = personaQuery.data\n\n const consolidate = useTriggerConsolidate()\n const status = useConsolidateStatus()\n const latestJob = status.data?.jobs[0]\n\n const updatePersona = useUpdatePersona()\n const deletePersona = useDeletePersona()\n const [confirmDelete, setConfirmDelete] = useState(false)\n\n /** Editor state — initialised from the server summary; tracks\n * dirtiness via reference comparison after each save. */\n const [draft, setDraft] = useState(persona?.summary ?? '')\n useEffect(() => {\n setDraft(persona?.summary ?? '')\n }, [persona?.summary])\n const dirty = draft !== (persona?.summary ?? '')\n\n async function onSave(): Promise<void> {\n const trimmed = draft.trim()\n if (!trimmed) return\n try {\n await updatePersona.mutateAsync({ user_key: userKey, body: { summary: trimmed } })\n toast.success(t('persona.saved'))\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n }\n }\n\n async function onConfirmDelete(): Promise<void> {\n try {\n await deletePersona.mutateAsync(userKey)\n toast.success(t('common:actions.delete'))\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n throw err\n }\n }\n\n async function onTrigger(): Promise<void> {\n try {\n await consolidate.mutateAsync()\n } catch (err) {\n const { message } = describeError(err, t)\n toast.error(message)\n }\n }\n\n return (\n <div className=\"mx-auto flex max-w-4xl flex-col gap-4\">\n <header className=\"flex flex-col gap-1\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <h1 className=\"text-xl font-semibold\">{t('persona.title')}</h1>\n <Button\n variant=\"ghost\"\n size=\"sm\"\n className=\"ml-auto\"\n onClick={() => personaQuery.refetch()}\n disabled={personaQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {personaQuery.isFetching ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('actions.refresh', { ns: 'common' })}</span>\n </Button>\n </div>\n <p className=\"text-sm text-text-dim\">{t('persona.subtitle')}</p>\n </header>\n\n {/* Consolidate strip */}\n <div className=\"rounded-md border border-border bg-surface p-3\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <span className=\"font-medium text-sm text-text\">{t('persona.consolidate.trigger')}</span>\n <ConsolidateBadge job={latestJob} />\n <Button\n variant=\"default\"\n size=\"sm\"\n onClick={() => void onTrigger()}\n disabled={consolidate.isPending || latestJob?.phase === 'running'}\n className=\"ml-auto\"\n >\n {consolidate.isPending\n ? <Loader2 className=\"h-4 w-4 animate-spin\" />\n : <Play className=\"h-4 w-4\" />}\n {consolidate.isPending\n ? t('persona.consolidate.triggering')\n : t('persona.consolidate.trigger')}\n </Button>\n </div>\n {latestJob?.phase === 'done' && (latestJob.result.users != null || latestJob.result.updated != null) && (\n <p className=\"mt-2 text-xs text-text-dim\">\n {t('persona.consolidate.result', {\n users: latestJob.result.users ?? 0,\n updated: latestJob.result.updated ?? 0,\n })}\n </p>\n )}\n {latestJob?.phase === 'failed' && latestJob.result.error && (\n <p className=\"mt-2 text-xs text-danger\">{latestJob.result.error}</p>\n )}\n </div>\n\n {/* Editor */}\n {personaQuery.isLoading ? (\n <div className=\"h-48 w-full rounded-md bg-surface-2 animate-pulse\" />\n ) : !persona ? (\n <>\n <EmptyState\n icon={<Brain />}\n title={t('persona.empty.title')}\n description={t('persona.empty.description')}\n />\n {/* Even with no persona, the operator can still type one in\n and save — the upsert handler creates a new row. */}\n <PersonaTextarea\n draft={draft}\n onChange={setDraft}\n onSave={() => void onSave()}\n saving={updatePersona.isPending}\n dirty={dirty}\n canDelete={false}\n onDelete={() => setConfirmDelete(true)}\n />\n </>\n ) : (\n <>\n {persona.updated_at > 0 && (\n <div className=\"text-xs text-text-dim\">\n {t('persona.updated', { at: formatEpoch(persona.updated_at) })}\n </div>\n )}\n <PersonaTextarea\n draft={draft}\n onChange={setDraft}\n onSave={() => void onSave()}\n saving={updatePersona.isPending}\n dirty={dirty}\n canDelete\n onDelete={() => setConfirmDelete(true)}\n />\n </>\n )}\n\n <ConfirmDialog\n open={confirmDelete}\n onOpenChange={setConfirmDelete}\n title={t('persona.confirmDelete')}\n description={t('persona.confirmDeleteDesc')}\n intent=\"danger\"\n confirmLabel={t('persona.delete')}\n onConfirm={onConfirmDelete}\n />\n </div>\n )\n}\n\ninterface PersonaTextareaProps {\n draft: string\n onChange: (next: string) => void\n onSave: () => void\n saving: boolean\n dirty: boolean\n canDelete: boolean\n onDelete: () => void\n}\n\nfunction PersonaTextarea({\n draft, onChange, onSave, saving, dirty, canDelete, onDelete,\n}: PersonaTextareaProps): JSX.Element {\n const { t } = useTranslation('memory')\n return (\n <div className=\"flex flex-col gap-2\">\n <Label htmlFor=\"persona-editor\" className=\"text-sm text-text-dim\">\n {t('persona.editorLabel')}\n </Label>\n <textarea\n id=\"persona-editor\"\n value={draft}\n onChange={(e) => onChange(e.target.value)}\n rows={12}\n className={cn(\n 'w-full resize-y rounded-md border bg-bg px-3 py-2',\n 'font-mono text-sm leading-6',\n 'focus:outline-none focus:ring-2 focus:ring-accent focus:ring-offset-1 focus:ring-offset-bg',\n dirty ? 'border-accent' : 'border-border',\n )}\n />\n <div className=\"flex flex-wrap items-center gap-2\">\n {canDelete && (\n <Button\n type=\"button\"\n variant=\"outline\"\n size=\"sm\"\n onClick={onDelete}\n >\n <Trash2 className=\"h-3 w-3\" />\n {t('persona.delete')}\n </Button>\n )}\n <Button\n type=\"button\"\n size=\"sm\"\n className=\"ml-auto\"\n disabled={!dirty || saving || draft.trim().length === 0}\n onClick={onSave}\n >\n {saving ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : null}\n {t('persona.save')}\n </Button>\n </div>\n </div>\n )\n}\n\ninterface ConsolidateBadgeProps {\n job: ConsolidateJob | undefined\n}\n\nfunction ConsolidateBadge({ job }: ConsolidateBadgeProps): JSX.Element | null {\n const { t } = useTranslation('memory')\n if (!job) return null\n if (job.phase === 'running') {\n return (\n <Badge variant=\"info\">\n <Loader2 className=\"h-3 w-3 animate-spin\" />\n {t('persona.consolidate.running')}\n </Badge>\n )\n }\n if (job.phase === 'done') {\n return (\n <Badge variant=\"success\">\n <CheckCircle className=\"h-3 w-3\" />\n {t('persona.consolidate.lastRun', { at: formatEpoch(job.finishedAt ?? job.startedAt) })}\n </Badge>\n )\n }\n return (\n <Badge variant=\"danger\">\n <XCircle className=\"h-3 w-3\" />\n {t('persona.consolidate.doneFailed')}\n </Badge>\n )\n}\n\nfunction formatEpoch(ms: number): string {\n try {\n const d = new Date(ms)\n if (Number.isNaN(d.getTime())) return String(ms)\n return d.toLocaleString(undefined, { month: 'short', day: 'numeric', hour: '2-digit', minute: '2-digit' })\n } catch {\n return String(ms)\n }\n}\n"],"names":["MemoryPersonaRoute","useTranslation","params","useSearchParams","userKey","jsx","PersonaEditor","EmptyState","Brain","t","personaQuery","useMemoryPersona","persona","consolidate","useTriggerConsolidate","latestJob","useConsolidateStatus","updatePersona","useUpdatePersona","deletePersona","useDeletePersona","confirmDelete","setConfirmDelete","useState","draft","setDraft","useEffect","dirty","onSave","trimmed","toast","err","message","describeError","onConfirmDelete","onTrigger","jsxs","Button","Loader2","RefreshCcw","ConsolidateBadge","Play","Fragment","formatEpoch","PersonaTextarea","ConfirmDialog","onChange","saving","canDelete","onDelete","Label","e","cn","Trash2","job","Badge","CheckCircle","XCircle","ms","d"],"mappings":"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"}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import{n as u,u as f,j as e,k as j,B as p,L as g,I as N,C as b}from"./index-
|
|
1
|
+
import{n as u,u as f,j as e,k as j,B as p,L as g,I as N,C as b}from"./index-DEWFfW_Z.js";import{r as c}from"./react-DlP5eolq.js";import{T as y,a as v,b as m,c as i,d as k,e as l}from"./table-BbAOSyc8.js";import{f as C}from"./use-background-tasks-B64YjlA8.js";import{L as w}from"./loader-circle-Bbw4pEyE.js";import{R as V}from"./refresh-ccw-uNKeBeRl.js";import{C as F}from"./chevron-right-CtelqacW.js";import{C as L}from"./clock-CG5dlBGB.js";import{C as M}from"./circle-x-rUxzIz5P.js";import{C as T}from"./circle-check-8dbL-u7O.js";import"./useQuery-CY2iazjN.js";/**
|
|
2
2
|
* @license lucide-react v0.469.0 - ISC
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the ISC license.
|
|
@@ -9,4 +9,4 @@ import{n as u,u as f,j as e,k as j,B as p,L as g,I as N,C as b}from"./index-O0BQ
|
|
|
9
9
|
* This source code is licensed under the ISC license.
|
|
10
10
|
* See the LICENSE file in the root directory of this source tree.
|
|
11
11
|
*/const P=u("PenLine",[["path",{d:"M12 20h9",key:"t2du7b"}],["path",{d:"M16.376 3.622a1 1 0 0 1 3.002 3.002L7.368 18.635a2 2 0 0 1-.855.506l-2.872.838a.5.5 0 0 1-.62-.62l.838-2.872a2 2 0 0 1 .506-.854z",key:"1ykcvy"}]]),E={approved:e.jsx(T,{className:"h-3 w-3"}),rejected:e.jsx(M,{className:"h-3 w-3"}),edited:e.jsx(P,{className:"h-3 w-3"}),expired:e.jsx(L,{className:"h-3 w-3"})},O={approved:"success",rejected:"warning",edited:"info",expired:"outline"};function A(a){if(a==null)return"—";if(a<1e3)return`${a}ms`;const s=a/1e3;return s<60?`${s.toFixed(1)}s`:`${(s/60).toFixed(1)}min`}function X(){const{t:a}=f(["tasks","common"]),[s,r]=c.useState(""),[d,o]=c.useState(""),t=C({threadKey:d||void 0,limit:200}),h=c.useMemo(()=>t.data?.plans??[],[t.data]);function x(){o(s.trim())}return e.jsxs("div",{className:"mx-auto flex max-w-6xl flex-col gap-4 p-4",children:[e.jsxs("header",{className:"flex items-center gap-3",children:[e.jsx(R,{className:"h-5 w-5 text-text-dim"}),e.jsx("h1",{className:"text-xl font-semibold",children:a("plans.title",{defaultValue:"Plan history"})}),e.jsx(j,{variant:"info",children:h.length}),e.jsxs(p,{variant:"ghost",size:"sm",className:"ml-auto",onClick:()=>void t.refetch(),disabled:t.isFetching,"aria-label":a("actions.refresh",{ns:"common"}),children:[t.isFetching?e.jsx(w,{className:"h-4 w-4 animate-spin"}):e.jsx(V,{className:"h-4 w-4"}),e.jsx("span",{className:"hidden sm:inline",children:a("plans.refresh",{defaultValue:"Refresh"})})]})]}),e.jsx("p",{className:"text-sm text-text-dim",children:a("plans.subtitle",{defaultValue:"Every native_exit_plan_mode handshake (v1.2.131) lands here with outcome + the plan markdown the model proposed."})}),e.jsxs("section",{className:"flex items-end gap-2 rounded-md border border-border bg-surface p-3",children:[e.jsxs("div",{className:"flex flex-1 flex-col gap-1",children:[e.jsx(g,{className:"text-xs font-medium",children:a("plans.filterLabel",{defaultValue:"Filter by thread key (optional)"})}),e.jsx(N,{value:s,onChange:n=>r(n.target.value),onKeyDown:n=>{n.key==="Enter"&&x()},placeholder:"tg:8754479311:default",className:"font-mono text-xs"})]}),e.jsx(p,{size:"sm",onClick:x,disabled:t.isFetching,children:a("plans.applyFilter",{defaultValue:"Apply"})}),d&&e.jsx(p,{size:"sm",variant:"ghost",onClick:()=>{r(""),o("")},children:a("plans.clearFilter",{defaultValue:"Clear"})})]}),t.isLoading?e.jsx("div",{className:"h-32 rounded-md bg-surface-2 animate-pulse"}):h.length===0?e.jsx("section",{className:"rounded-md border border-border bg-surface p-6 text-center text-sm text-text-dim",children:d?a("plans.emptyFiltered",{defaultValue:"No plan history for this thread. Either the thread never entered plan mode, or it was approved without going through the exit handshake (e.g. /plan off manually)."}):a("plans.empty",{defaultValue:"No plans yet. Try /plan on in an IM thread and let the model build a plan."})}):e.jsxs(y,{children:[e.jsx(v,{children:e.jsxs(m,{children:[e.jsx(i,{className:"w-8"}),e.jsx(i,{children:a("plans.col.outcome",{defaultValue:"Outcome"})}),e.jsx(i,{children:a("plans.col.thread",{defaultValue:"Thread"})}),e.jsx(i,{children:a("plans.col.resolvedAt",{defaultValue:"Resolved"})}),e.jsx(i,{children:a("plans.col.pending",{defaultValue:"Wait"})}),e.jsx(i,{children:a("plans.col.detail",{defaultValue:"Detail"})})]})}),e.jsx(k,{children:h.map(n=>e.jsx(I,{row:n},n.id))})]})]})}function I({row:a}){const{t:s}=f(["tasks"]),[r,d]=c.useState(!1);return e.jsxs(e.Fragment,{children:[e.jsxs(m,{className:"cursor-pointer hover:bg-surface-hover",onClick:()=>d(o=>!o),children:[e.jsx(l,{className:"p-1 align-top text-text-dim",children:r?e.jsx(b,{className:"h-4 w-4"}):e.jsx(F,{className:"h-4 w-4"})}),e.jsx(l,{className:"align-top",children:e.jsxs(j,{variant:O[a.outcome],children:[E[a.outcome],e.jsx("span",{className:"ml-1",children:a.outcome})]})}),e.jsx(l,{className:"align-top",children:e.jsx("code",{className:"text-[11px]",children:a.threadKey})}),e.jsx(l,{className:"align-top text-[11px] text-text-dim",children:a.resolvedAt}),e.jsx(l,{className:"align-top text-[11px] text-text-dim",children:A(a.pendingMs)}),e.jsx(l,{className:"align-top text-xs",children:a.detail?e.jsxs("span",{title:a.detail,children:[a.detail.slice(0,80),a.detail.length>80?"…":""]}):e.jsx("span",{className:"text-text-dim",children:"—"})})]}),r&&e.jsx(m,{children:e.jsxs(l,{colSpan:6,className:"bg-surface-2 p-3",children:[e.jsx("div",{className:"text-[11px] text-text-dim",children:s("plans.planMdLabel",{defaultValue:"Plan markdown the model proposed:"})}),e.jsx("pre",{className:"mt-1 max-h-96 overflow-y-auto whitespace-pre-wrap rounded border border-border bg-surface p-3 text-[12px]",children:a.planMd})]})})]})}export{X as default};
|
|
12
|
-
//# sourceMappingURL=plans-
|
|
12
|
+
//# sourceMappingURL=plans-BBB5e9my.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"plans-CZoEs5SY.js","sources":["../../node_modules/lucide-react/dist/esm/icons/clipboard-list.js","../../node_modules/lucide-react/dist/esm/icons/pen-line.js","../../src/routes/tasks/plans.tsx"],"sourcesContent":["/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst ClipboardList = createLucideIcon(\"ClipboardList\", [\n [\"rect\", { width: \"8\", height: \"4\", x: \"8\", y: \"2\", rx: \"1\", ry: \"1\", key: \"tgr4d6\" }],\n [\n \"path\",\n {\n d: \"M16 4h2a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2h2\",\n key: \"116196\"\n }\n ],\n [\"path\", { d: \"M12 11h4\", key: \"1jrz19\" }],\n [\"path\", { d: \"M12 16h4\", key: \"n85exb\" }],\n [\"path\", { d: \"M8 11h.01\", key: \"1dfujw\" }],\n [\"path\", { d: \"M8 16h.01\", key: \"18s6g9\" }]\n]);\n\nexport { ClipboardList as default };\n//# sourceMappingURL=clipboard-list.js.map\n","/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst PenLine = createLucideIcon(\"PenLine\", [\n [\"path\", { d: \"M12 20h9\", key: \"t2du7b\" }],\n [\n \"path\",\n {\n d: \"M16.376 3.622a1 1 0 0 1 3.002 3.002L7.368 18.635a2 2 0 0 1-.855.506l-2.872.838a.5.5 0 0 1-.62-.62l.838-2.872a2 2 0 0 1 .506-.854z\",\n key: \"1ykcvy\"\n }\n ]\n]);\n\nexport { PenLine as default };\n//# sourceMappingURL=pen-line.js.map\n","/**\n * /tasks/plans — admin view of native_exit_plan_mode handshakes\n * (v1.2.133).\n *\n * Surfaces the plan_history sqlite table populated by v1.2.131's\n * exit-plan-mode dispatcher. Each row shows what plan the model\n * proposed, what outcome the user picked (approved / rejected /\n * edited / expired), how long the operator took to decide, and\n * the rejection / edit reason if any.\n *\n * Layout mirrors /tasks/asks: header with title + count + refresh +\n * optional thread filter, then a table. Each row's plan markdown\n * is collapsed by default — click to expand into a fenced markdown\n * block (no live render; that's a v1.2.134 idea once we know\n * operators actually use this surface).\n */\n\nimport { useMemo, useState } from 'react'\nimport { useTranslation } from 'react-i18next'\nimport {\n CheckCircle2, ChevronDown, ChevronRight, ClipboardList,\n Edit3, Loader2, RefreshCcw, XCircle, Clock,\n} from 'lucide-react'\n\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport { Input } from '@/components/ui/input'\nimport { Label } from '@/components/ui/label'\nimport {\n Table, TableBody, TableCell, TableHead, TableHeader, TableRow,\n} from '@/components/ui/table'\nimport { usePlansList, type PlanHistoryRow, type PlanOutcome } from '@/hooks/use-background-tasks'\n\nconst OUTCOME_ICONS: Record<PlanOutcome, JSX.Element> = {\n approved: <CheckCircle2 className=\"h-3 w-3\" />,\n rejected: <XCircle className=\"h-3 w-3\" />,\n edited: <Edit3 className=\"h-3 w-3\" />,\n expired: <Clock className=\"h-3 w-3\" />,\n}\n\nconst OUTCOME_VARIANT: Record<PlanOutcome, 'success' | 'warning' | 'info' | 'outline'> = {\n approved: 'success',\n rejected: 'warning',\n edited: 'info',\n expired: 'outline',\n}\n\nfunction fmtPending(ms: number | null): string {\n if (ms == null) return '—'\n if (ms < 1000) return `${ms}ms`\n const s = ms / 1000\n if (s < 60) return `${s.toFixed(1)}s`\n return `${(s / 60).toFixed(1)}min`\n}\n\nexport default function TasksPlansRoute(): JSX.Element {\n const { t } = useTranslation(['tasks', 'common'])\n const [filter, setFilter] = useState('')\n const [appliedFilter, setAppliedFilter] = useState('')\n const listQuery = usePlansList({ threadKey: appliedFilter || undefined, limit: 200 })\n\n const rows = useMemo(() => listQuery.data?.plans ?? [], [listQuery.data])\n\n function applyFilter(): void {\n setAppliedFilter(filter.trim())\n }\n\n return (\n <div className=\"mx-auto flex max-w-6xl flex-col gap-4 p-4\">\n <header className=\"flex items-center gap-3\">\n <ClipboardList className=\"h-5 w-5 text-text-dim\" />\n <h1 className=\"text-xl font-semibold\">{t('plans.title', { defaultValue: 'Plan history' })}</h1>\n <Badge variant=\"info\">{rows.length}</Badge>\n <Button\n variant=\"ghost\" size=\"sm\" className=\"ml-auto\"\n onClick={() => void listQuery.refetch()}\n disabled={listQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {listQuery.isFetching\n ? <Loader2 className=\"h-4 w-4 animate-spin\" />\n : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('plans.refresh', { defaultValue: 'Refresh' })}</span>\n </Button>\n </header>\n <p className=\"text-sm text-text-dim\">\n {t('plans.subtitle', {\n defaultValue:\n 'Every native_exit_plan_mode handshake (v1.2.131) lands here with outcome + the plan markdown the model proposed.',\n })}\n </p>\n\n <section className=\"flex items-end gap-2 rounded-md border border-border bg-surface p-3\">\n <div className=\"flex flex-1 flex-col gap-1\">\n <Label className=\"text-xs font-medium\">\n {t('plans.filterLabel', { defaultValue: 'Filter by thread key (optional)' })}\n </Label>\n <Input\n value={filter}\n onChange={(e) => setFilter(e.target.value)}\n onKeyDown={(e) => { if (e.key === 'Enter') applyFilter() }}\n placeholder=\"tg:8754479311:default\"\n className=\"font-mono text-xs\"\n />\n </div>\n <Button size=\"sm\" onClick={applyFilter} disabled={listQuery.isFetching}>\n {t('plans.applyFilter', { defaultValue: 'Apply' })}\n </Button>\n {appliedFilter && (\n <Button\n size=\"sm\" variant=\"ghost\"\n onClick={() => { setFilter(''); setAppliedFilter('') }}\n >\n {t('plans.clearFilter', { defaultValue: 'Clear' })}\n </Button>\n )}\n </section>\n\n {listQuery.isLoading ? (\n <div className=\"h-32 rounded-md bg-surface-2 animate-pulse\" />\n ) : rows.length === 0 ? (\n <section className=\"rounded-md border border-border bg-surface p-6 text-center text-sm text-text-dim\">\n {appliedFilter\n ? t('plans.emptyFiltered', {\n defaultValue: 'No plan history for this thread. Either the thread never entered plan mode, or it was approved without going through the exit handshake (e.g. /plan off manually).',\n })\n : t('plans.empty', {\n defaultValue: 'No plans yet. Try /plan on in an IM thread and let the model build a plan.',\n })}\n </section>\n ) : (\n <Table>\n <TableHeader>\n <TableRow>\n <TableHead className=\"w-8\" />\n <TableHead>{t('plans.col.outcome', { defaultValue: 'Outcome' })}</TableHead>\n <TableHead>{t('plans.col.thread', { defaultValue: 'Thread' })}</TableHead>\n <TableHead>{t('plans.col.resolvedAt', { defaultValue: 'Resolved' })}</TableHead>\n <TableHead>{t('plans.col.pending', { defaultValue: 'Wait' })}</TableHead>\n <TableHead>{t('plans.col.detail', { defaultValue: 'Detail' })}</TableHead>\n </TableRow>\n </TableHeader>\n <TableBody>\n {rows.map((r) => <PlanRow key={r.id} row={r} />)}\n </TableBody>\n </Table>\n )}\n </div>\n )\n}\n\nfunction PlanRow({ row }: { row: PlanHistoryRow }): JSX.Element {\n const { t } = useTranslation(['tasks'])\n const [open, setOpen] = useState(false)\n return (\n <>\n <TableRow className=\"cursor-pointer hover:bg-surface-hover\" onClick={() => setOpen((v) => !v)}>\n <TableCell className=\"p-1 align-top text-text-dim\">\n {open ? <ChevronDown className=\"h-4 w-4\" /> : <ChevronRight className=\"h-4 w-4\" />}\n </TableCell>\n <TableCell className=\"align-top\">\n <Badge variant={OUTCOME_VARIANT[row.outcome]}>\n {OUTCOME_ICONS[row.outcome]}\n <span className=\"ml-1\">{row.outcome}</span>\n </Badge>\n </TableCell>\n <TableCell className=\"align-top\">\n <code className=\"text-[11px]\">{row.threadKey}</code>\n </TableCell>\n <TableCell className=\"align-top text-[11px] text-text-dim\">{row.resolvedAt}</TableCell>\n <TableCell className=\"align-top text-[11px] text-text-dim\">{fmtPending(row.pendingMs)}</TableCell>\n <TableCell className=\"align-top text-xs\">\n {row.detail\n ? <span title={row.detail}>{row.detail.slice(0, 80)}{row.detail.length > 80 ? '…' : ''}</span>\n : <span className=\"text-text-dim\">—</span>}\n </TableCell>\n </TableRow>\n {open && (\n <TableRow>\n <TableCell colSpan={6} className=\"bg-surface-2 p-3\">\n <div className=\"text-[11px] text-text-dim\">\n {t('plans.planMdLabel', { defaultValue: 'Plan markdown the model proposed:' })}\n </div>\n <pre className=\"mt-1 max-h-96 overflow-y-auto whitespace-pre-wrap rounded border border-border bg-surface p-3 text-[12px]\">\n {row.planMd}\n </pre>\n </TableCell>\n </TableRow>\n )}\n </>\n )\n}\n"],"names":["ClipboardList","createLucideIcon","PenLine","OUTCOME_ICONS","jsx","CheckCircle2","XCircle","Edit3","Clock","OUTCOME_VARIANT","fmtPending","ms","TasksPlansRoute","t","useTranslation","filter","setFilter","useState","appliedFilter","setAppliedFilter","listQuery","usePlansList","rows","useMemo","applyFilter","jsxs","Badge","Button","Loader2","RefreshCcw","Label","Input","e","Table","TableHeader","TableRow","TableHead","TableBody","r","PlanRow","row","open","setOpen","Fragment","v","TableCell","ChevronDown","ChevronRight"],"mappings":"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","x_google_ignoreList":[0,1]}
|
|
1
|
+
{"version":3,"file":"plans-BBB5e9my.js","sources":["../../node_modules/lucide-react/dist/esm/icons/clipboard-list.js","../../node_modules/lucide-react/dist/esm/icons/pen-line.js","../../src/routes/tasks/plans.tsx"],"sourcesContent":["/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst ClipboardList = createLucideIcon(\"ClipboardList\", [\n [\"rect\", { width: \"8\", height: \"4\", x: \"8\", y: \"2\", rx: \"1\", ry: \"1\", key: \"tgr4d6\" }],\n [\n \"path\",\n {\n d: \"M16 4h2a2 2 0 0 1 2 2v14a2 2 0 0 1-2 2H6a2 2 0 0 1-2-2V6a2 2 0 0 1 2-2h2\",\n key: \"116196\"\n }\n ],\n [\"path\", { d: \"M12 11h4\", key: \"1jrz19\" }],\n [\"path\", { d: \"M12 16h4\", key: \"n85exb\" }],\n [\"path\", { d: \"M8 11h.01\", key: \"1dfujw\" }],\n [\"path\", { d: \"M8 16h.01\", key: \"18s6g9\" }]\n]);\n\nexport { ClipboardList as default };\n//# sourceMappingURL=clipboard-list.js.map\n","/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst PenLine = createLucideIcon(\"PenLine\", [\n [\"path\", { d: \"M12 20h9\", key: \"t2du7b\" }],\n [\n \"path\",\n {\n d: \"M16.376 3.622a1 1 0 0 1 3.002 3.002L7.368 18.635a2 2 0 0 1-.855.506l-2.872.838a.5.5 0 0 1-.62-.62l.838-2.872a2 2 0 0 1 .506-.854z\",\n key: \"1ykcvy\"\n }\n ]\n]);\n\nexport { PenLine as default };\n//# sourceMappingURL=pen-line.js.map\n","/**\n * /tasks/plans — admin view of native_exit_plan_mode handshakes\n * (v1.2.133).\n *\n * Surfaces the plan_history sqlite table populated by v1.2.131's\n * exit-plan-mode dispatcher. Each row shows what plan the model\n * proposed, what outcome the user picked (approved / rejected /\n * edited / expired), how long the operator took to decide, and\n * the rejection / edit reason if any.\n *\n * Layout mirrors /tasks/asks: header with title + count + refresh +\n * optional thread filter, then a table. Each row's plan markdown\n * is collapsed by default — click to expand into a fenced markdown\n * block (no live render; that's a v1.2.134 idea once we know\n * operators actually use this surface).\n */\n\nimport { useMemo, useState } from 'react'\nimport { useTranslation } from 'react-i18next'\nimport {\n CheckCircle2, ChevronDown, ChevronRight, ClipboardList,\n Edit3, Loader2, RefreshCcw, XCircle, Clock,\n} from 'lucide-react'\n\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport { Input } from '@/components/ui/input'\nimport { Label } from '@/components/ui/label'\nimport {\n Table, TableBody, TableCell, TableHead, TableHeader, TableRow,\n} from '@/components/ui/table'\nimport { usePlansList, type PlanHistoryRow, type PlanOutcome } from '@/hooks/use-background-tasks'\n\nconst OUTCOME_ICONS: Record<PlanOutcome, JSX.Element> = {\n approved: <CheckCircle2 className=\"h-3 w-3\" />,\n rejected: <XCircle className=\"h-3 w-3\" />,\n edited: <Edit3 className=\"h-3 w-3\" />,\n expired: <Clock className=\"h-3 w-3\" />,\n}\n\nconst OUTCOME_VARIANT: Record<PlanOutcome, 'success' | 'warning' | 'info' | 'outline'> = {\n approved: 'success',\n rejected: 'warning',\n edited: 'info',\n expired: 'outline',\n}\n\nfunction fmtPending(ms: number | null): string {\n if (ms == null) return '—'\n if (ms < 1000) return `${ms}ms`\n const s = ms / 1000\n if (s < 60) return `${s.toFixed(1)}s`\n return `${(s / 60).toFixed(1)}min`\n}\n\nexport default function TasksPlansRoute(): JSX.Element {\n const { t } = useTranslation(['tasks', 'common'])\n const [filter, setFilter] = useState('')\n const [appliedFilter, setAppliedFilter] = useState('')\n const listQuery = usePlansList({ threadKey: appliedFilter || undefined, limit: 200 })\n\n const rows = useMemo(() => listQuery.data?.plans ?? [], [listQuery.data])\n\n function applyFilter(): void {\n setAppliedFilter(filter.trim())\n }\n\n return (\n <div className=\"mx-auto flex max-w-6xl flex-col gap-4 p-4\">\n <header className=\"flex items-center gap-3\">\n <ClipboardList className=\"h-5 w-5 text-text-dim\" />\n <h1 className=\"text-xl font-semibold\">{t('plans.title', { defaultValue: 'Plan history' })}</h1>\n <Badge variant=\"info\">{rows.length}</Badge>\n <Button\n variant=\"ghost\" size=\"sm\" className=\"ml-auto\"\n onClick={() => void listQuery.refetch()}\n disabled={listQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {listQuery.isFetching\n ? <Loader2 className=\"h-4 w-4 animate-spin\" />\n : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('plans.refresh', { defaultValue: 'Refresh' })}</span>\n </Button>\n </header>\n <p className=\"text-sm text-text-dim\">\n {t('plans.subtitle', {\n defaultValue:\n 'Every native_exit_plan_mode handshake (v1.2.131) lands here with outcome + the plan markdown the model proposed.',\n })}\n </p>\n\n <section className=\"flex items-end gap-2 rounded-md border border-border bg-surface p-3\">\n <div className=\"flex flex-1 flex-col gap-1\">\n <Label className=\"text-xs font-medium\">\n {t('plans.filterLabel', { defaultValue: 'Filter by thread key (optional)' })}\n </Label>\n <Input\n value={filter}\n onChange={(e) => setFilter(e.target.value)}\n onKeyDown={(e) => { if (e.key === 'Enter') applyFilter() }}\n placeholder=\"tg:8754479311:default\"\n className=\"font-mono text-xs\"\n />\n </div>\n <Button size=\"sm\" onClick={applyFilter} disabled={listQuery.isFetching}>\n {t('plans.applyFilter', { defaultValue: 'Apply' })}\n </Button>\n {appliedFilter && (\n <Button\n size=\"sm\" variant=\"ghost\"\n onClick={() => { setFilter(''); setAppliedFilter('') }}\n >\n {t('plans.clearFilter', { defaultValue: 'Clear' })}\n </Button>\n )}\n </section>\n\n {listQuery.isLoading ? (\n <div className=\"h-32 rounded-md bg-surface-2 animate-pulse\" />\n ) : rows.length === 0 ? (\n <section className=\"rounded-md border border-border bg-surface p-6 text-center text-sm text-text-dim\">\n {appliedFilter\n ? t('plans.emptyFiltered', {\n defaultValue: 'No plan history for this thread. Either the thread never entered plan mode, or it was approved without going through the exit handshake (e.g. /plan off manually).',\n })\n : t('plans.empty', {\n defaultValue: 'No plans yet. Try /plan on in an IM thread and let the model build a plan.',\n })}\n </section>\n ) : (\n <Table>\n <TableHeader>\n <TableRow>\n <TableHead className=\"w-8\" />\n <TableHead>{t('plans.col.outcome', { defaultValue: 'Outcome' })}</TableHead>\n <TableHead>{t('plans.col.thread', { defaultValue: 'Thread' })}</TableHead>\n <TableHead>{t('plans.col.resolvedAt', { defaultValue: 'Resolved' })}</TableHead>\n <TableHead>{t('plans.col.pending', { defaultValue: 'Wait' })}</TableHead>\n <TableHead>{t('plans.col.detail', { defaultValue: 'Detail' })}</TableHead>\n </TableRow>\n </TableHeader>\n <TableBody>\n {rows.map((r) => <PlanRow key={r.id} row={r} />)}\n </TableBody>\n </Table>\n )}\n </div>\n )\n}\n\nfunction PlanRow({ row }: { row: PlanHistoryRow }): JSX.Element {\n const { t } = useTranslation(['tasks'])\n const [open, setOpen] = useState(false)\n return (\n <>\n <TableRow className=\"cursor-pointer hover:bg-surface-hover\" onClick={() => setOpen((v) => !v)}>\n <TableCell className=\"p-1 align-top text-text-dim\">\n {open ? <ChevronDown className=\"h-4 w-4\" /> : <ChevronRight className=\"h-4 w-4\" />}\n </TableCell>\n <TableCell className=\"align-top\">\n <Badge variant={OUTCOME_VARIANT[row.outcome]}>\n {OUTCOME_ICONS[row.outcome]}\n <span className=\"ml-1\">{row.outcome}</span>\n </Badge>\n </TableCell>\n <TableCell className=\"align-top\">\n <code className=\"text-[11px]\">{row.threadKey}</code>\n </TableCell>\n <TableCell className=\"align-top text-[11px] text-text-dim\">{row.resolvedAt}</TableCell>\n <TableCell className=\"align-top text-[11px] text-text-dim\">{fmtPending(row.pendingMs)}</TableCell>\n <TableCell className=\"align-top text-xs\">\n {row.detail\n ? <span title={row.detail}>{row.detail.slice(0, 80)}{row.detail.length > 80 ? '…' : ''}</span>\n : <span className=\"text-text-dim\">—</span>}\n </TableCell>\n </TableRow>\n {open && (\n <TableRow>\n <TableCell colSpan={6} className=\"bg-surface-2 p-3\">\n <div className=\"text-[11px] text-text-dim\">\n {t('plans.planMdLabel', { defaultValue: 'Plan markdown the model proposed:' })}\n </div>\n <pre className=\"mt-1 max-h-96 overflow-y-auto whitespace-pre-wrap rounded border border-border bg-surface p-3 text-[12px]\">\n {row.planMd}\n </pre>\n </TableCell>\n </TableRow>\n )}\n </>\n )\n}\n"],"names":["ClipboardList","createLucideIcon","PenLine","OUTCOME_ICONS","jsx","CheckCircle2","XCircle","Edit3","Clock","OUTCOME_VARIANT","fmtPending","ms","TasksPlansRoute","t","useTranslation","filter","setFilter","useState","appliedFilter","setAppliedFilter","listQuery","usePlansList","rows","useMemo","applyFilter","jsxs","Badge","Button","Loader2","RefreshCcw","Label","Input","e","Table","TableHeader","TableRow","TableHead","TableBody","r","PlanRow","row","open","setOpen","Fragment","v","TableCell","ChevronDown","ChevronRight"],"mappings":"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","x_google_ignoreList":[0,1]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import{n as o}from"./index-
|
|
1
|
+
import{n as o}from"./index-DEWFfW_Z.js";/**
|
|
2
2
|
* @license lucide-react v0.469.0 - ISC
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the ISC license.
|
|
5
5
|
* See the LICENSE file in the root directory of this source tree.
|
|
6
6
|
*/const e=o("Play",[["polygon",{points:"6 3 20 12 6 21 6 3",key:"1oa8hb"}]]);export{e as P};
|
|
7
|
-
//# sourceMappingURL=play-
|
|
7
|
+
//# sourceMappingURL=play-7-Wd369f.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"play-
|
|
1
|
+
{"version":3,"file":"play-7-Wd369f.js","sources":["../../node_modules/lucide-react/dist/esm/icons/play.js"],"sourcesContent":["/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst Play = createLucideIcon(\"Play\", [\n [\"polygon\", { points: \"6 3 20 12 6 21 6 3\", key: \"1oa8hb\" }]\n]);\n\nexport { Play as default };\n//# sourceMappingURL=play.js.map\n"],"names":["Play","createLucideIcon"],"mappings":"wCAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GASK,MAACA,EAAOC,EAAiB,OAAQ,CACpC,CAAC,UAAW,CAAE,OAAQ,qBAAsB,IAAK,QAAQ,CAAE,CAC7D,CAAC","x_google_ignoreList":[0]}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import{n as e}from"./index-
|
|
1
|
+
import{n as e}from"./index-DEWFfW_Z.js";/**
|
|
2
2
|
* @license lucide-react v0.469.0 - ISC
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the ISC license.
|
|
5
5
|
* See the LICENSE file in the root directory of this source tree.
|
|
6
6
|
*/const a=e("Plus",[["path",{d:"M5 12h14",key:"1ays0h"}],["path",{d:"M12 5v14",key:"s699le"}]]);export{a as P};
|
|
7
|
-
//# sourceMappingURL=plus-
|
|
7
|
+
//# sourceMappingURL=plus-B0sfZy-j.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"plus-
|
|
1
|
+
{"version":3,"file":"plus-B0sfZy-j.js","sources":["../../node_modules/lucide-react/dist/esm/icons/plus.js"],"sourcesContent":["/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst Plus = createLucideIcon(\"Plus\", [\n [\"path\", { d: \"M5 12h14\", key: \"1ays0h\" }],\n [\"path\", { d: \"M12 5v14\", key: \"s699le\" }]\n]);\n\nexport { Plus as default };\n//# sourceMappingURL=plus.js.map\n"],"names":["Plus","createLucideIcon"],"mappings":"wCAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GASK,MAACA,EAAOC,EAAiB,OAAQ,CACpC,CAAC,OAAQ,CAAE,EAAG,WAAY,IAAK,QAAQ,CAAE,EACzC,CAAC,OAAQ,CAAE,EAAG,WAAY,IAAK,QAAQ,CAAE,CAC3C,CAAC","x_google_ignoreList":[0]}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import{u as r,j as e,B as d,l as m,m as E,k as u,p as w,c as x,S as _,f as I,g as M,h as A,i as c}from"./index-
|
|
2
|
-
//# sourceMappingURL=policy-
|
|
1
|
+
import{u as r,j as e,B as d,l as m,m as E,k as u,p as w,c as x,S as _,f as I,g as M,h as A,i as c}from"./index-DEWFfW_Z.js";import{u as C,a as B}from"./use-settings-i1MhlkyC.js";import{L as S}from"./loader-circle-Bbw4pEyE.js";import{R as U}from"./refresh-ccw-uNKeBeRl.js";import"./react-DlP5eolq.js";import"./useQuery-CY2iazjN.js";function o(s){if(s==null)return!1;const a=s.toLowerCase();return a==="1"||a==="true"||a==="yes"||a==="on"}function K(){const{t:s}=r(["settings","common"]),a=C(),i=B();async function t(n,v){try{await i.mutateAsync({updates:{[n]:v}}),m.success(s("policy.savingToast"))}catch(y){m.error(E(y,s).message)}}const l=a.data?.env??{},h=o(l.IMHUB_DANGEROUSLY_SKIP_PERMISSIONS),g=o(l.IMHUB_MEMORY_ENABLED),j=o(l.IMHUB_VIEWER_ENABLED),N=(l.IMHUB_TIMEOUT_DEFAULT??"").toLowerCase()==="allow",b=(l.IMHUB_A2A_NOTIFY_MODE??"essential").toLowerCase();return e.jsxs("div",{className:"mx-auto flex max-w-4xl flex-col gap-4",children:[e.jsxs("header",{className:"flex flex-col gap-1",children:[e.jsxs("div",{className:"flex flex-wrap items-center gap-3",children:[e.jsx("h1",{className:"text-xl font-semibold",children:s("policy.title")}),e.jsxs(d,{variant:"ghost",size:"sm",className:"ml-auto",onClick:()=>a.refetch(),disabled:a.isFetching,"aria-label":s("actions.refresh",{ns:"common"}),children:[a.isFetching?e.jsx(S,{className:"h-4 w-4 animate-spin"}):e.jsx(U,{className:"h-4 w-4"}),e.jsx("span",{className:"hidden sm:inline",children:s("actions.refresh",{ns:"common"})})]})]}),e.jsx("p",{className:"text-sm text-text-dim",children:s("policy.subtitle")})]}),a.isLoading?e.jsx("div",{className:"h-96 rounded-md bg-surface-2 animate-pulse"}):e.jsxs("div",{className:"flex flex-col gap-3",children:[e.jsx(O,{value:h,disabled:i.isPending,onChange:n=>void t("IMHUB_DANGEROUSLY_SKIP_PERMISSIONS",n?"1":"0")}),e.jsx(L,{allowOnTimeout:N,disabled:i.isPending,onChange:n=>void t("IMHUB_TIMEOUT_DEFAULT",n)}),e.jsx(p,{sectionKey:"memory",value:g,disabled:i.isPending,onChange:n=>void t("IMHUB_MEMORY_ENABLED",n?"1":"0")}),e.jsx(p,{sectionKey:"viewer",value:j,disabled:i.isPending,onChange:n=>void t("IMHUB_VIEWER_ENABLED",n?"1":"0")}),e.jsx(T,{value:b,disabled:i.isPending,onChange:n=>void t("IMHUB_A2A_NOTIFY_MODE",n)})]})]})}function O({value:s,disabled:a,onChange:i}){const{t}=r("settings");return e.jsx("section",{className:x("rounded-md border p-4",s?"border-danger/60 bg-danger-bg/30":"border-border bg-surface"),children:e.jsxs("div",{className:"flex items-start gap-3",children:[e.jsxs("div",{className:"flex-1",children:[e.jsxs("div",{className:"flex flex-wrap items-center gap-2",children:[e.jsx("span",{className:"font-medium text-text",children:t("policy.safety.title")}),s&&e.jsxs(u,{variant:"danger",children:[e.jsx(w,{className:"h-3 w-3"}),"ON"]})]}),e.jsx("p",{className:"mt-1 text-sm text-text-dim",children:t("policy.safety.description")}),!s&&e.jsx("p",{className:"mt-1 text-xs text-text-muted",children:t("policy.safety.tagWarn")}),e.jsx("code",{className:"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted",children:t("policy.safety.envKey")})]}),e.jsx(f,{value:s,disabled:a,onChange:i})]})})}function L({allowOnTimeout:s,disabled:a,onChange:i}){const{t}=r("settings");return e.jsx("section",{className:"rounded-md border border-border bg-surface p-4",children:e.jsxs("div",{className:"flex flex-col gap-2",children:[e.jsx("span",{className:"font-medium text-text",children:t("policy.approval.title")}),e.jsx("p",{className:"text-sm text-text-dim",children:t("policy.approval.description")}),e.jsx("code",{className:"self-start rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted",children:t("policy.approval.envKey")}),e.jsxs("div",{className:"mt-2 flex flex-wrap gap-2",children:[e.jsx(d,{type:"button",variant:s?"outline":"default",size:"sm",disabled:a,onClick:()=>i("deny"),children:t("policy.approval.valDeny")}),e.jsx(d,{type:"button",variant:s?"default":"outline",size:"sm",disabled:a,onClick:()=>i("allow"),children:t("policy.approval.valAllow")})]})]})})}function p({sectionKey:s,value:a,disabled:i,onChange:t}){const{t:l}=r("settings");return e.jsx("section",{className:"rounded-md border border-border bg-surface p-4",children:e.jsxs("div",{className:"flex items-start gap-3",children:[e.jsxs("div",{className:"flex-1",children:[e.jsxs("div",{className:"flex flex-wrap items-center gap-2",children:[e.jsx("span",{className:"font-medium text-text",children:l(`policy.${s}.title`)}),e.jsx(u,{variant:a?"success":"outline",children:a?"ON":"OFF"})]}),e.jsx("p",{className:"mt-1 text-sm text-text-dim",children:l(`policy.${s}.description`)}),e.jsx("code",{className:"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted",children:l(`policy.${s}.envKey`)})]}),e.jsx(f,{value:a,disabled:i,onChange:t})]})})}function T({value:s,disabled:a,onChange:i}){const{t}=r("settings");return e.jsx("section",{className:"rounded-md border border-border bg-surface p-4",children:e.jsxs("div",{className:"flex items-start gap-3",children:[e.jsxs("div",{className:"flex-1",children:[e.jsx("span",{className:"font-medium text-text",children:t("policy.a2aNotify.title")}),e.jsx("p",{className:"mt-1 text-sm text-text-dim",children:t("policy.a2aNotify.description")}),e.jsx("code",{className:"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted",children:t("policy.a2aNotify.envKey")})]}),e.jsxs(_,{value:s,onValueChange:i,disabled:a,children:[e.jsx(I,{className:"w-36",children:e.jsx(M,{})}),e.jsxs(A,{children:[e.jsx(c,{value:"essential",children:t("policy.a2aNotify.valEssential")}),e.jsx(c,{value:"verbose",children:t("policy.a2aNotify.valVerbose")}),e.jsx(c,{value:"off",children:t("policy.a2aNotify.valOff")})]})]})]})})}function f({value:s,disabled:a,onChange:i}){return e.jsx("button",{type:"button",role:"switch","aria-checked":s,disabled:a,onClick:()=>i(!s),className:x("relative inline-flex h-6 w-11 shrink-0 cursor-pointer items-center rounded-full transition-colors","focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-accent focus-visible:ring-offset-2 focus-visible:ring-offset-bg","disabled:cursor-not-allowed disabled:opacity-50",s?"bg-accent":"bg-surface-2 border border-border"),children:e.jsx("span",{className:x("inline-block h-5 w-5 rounded-full bg-white shadow transition-transform",s?"translate-x-5":"translate-x-0.5")})})}export{K as default};
|
|
2
|
+
//# sourceMappingURL=policy-BM1WRXH0.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"policy-CutDSEPW.js","sources":["../../src/routes/settings/policy.tsx"],"sourcesContent":["/**\n * /settings/policy — dedicated UI for the highest-frequency env\n * toggles. Each is a one-click switch (or 2-3 option select) that\n * persists to `~/.agim/.env` via PUT /api/env immediately.\n *\n * Surfaced here:\n * * IMHUB_DANGEROUSLY_SKIP_PERMISSIONS (safety)\n * * IMHUB_TIMEOUT_DEFAULT (approval bus default)\n * * IMHUB_MEMORY_ENABLED (memory subsystem)\n * * IMHUB_VIEWER_ENABLED (long-message viewer)\n * * IMHUB_A2A_NOTIFY_MODE (cross-agent notify verbosity)\n *\n * All five are still editable in /settings/env. This page exists\n * because:\n * 1. They're the ones operators flip most often\n * 2. The env editor's table doesn't communicate \"this is a\n * boolean / 2-state / 3-state value\" — operators have to\n * know the literal strings \"1\"/\"0\"/\"allow\"/\"deny\"/etc.\n * 3. Safety toggle deserves a visible warning + danger color\n */\n\nimport { useTranslation } from 'react-i18next'\nimport { toast } from 'sonner'\nimport { AlertTriangle, Loader2, RefreshCcw } from 'lucide-react'\n\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport {\n Select,\n SelectContent,\n SelectItem,\n SelectTrigger,\n SelectValue,\n} from '@/components/ui/select'\nimport { useEnv, useUpdateEnv } from '@/hooks/use-settings'\nimport { describeError } from '@/lib/api/errors'\nimport { cn } from '@/lib/utils'\n\n/** Treat the env value as a boolean — '1' / 'true' / 'yes' / 'on'\n * → true; everything else → false. Matches the backend's casual\n * truthy parsing in core/* modules. */\nfunction envBool(v: string | undefined): boolean {\n if (v == null) return false\n const t = v.toLowerCase()\n return t === '1' || t === 'true' || t === 'yes' || t === 'on'\n}\n\nexport default function SettingsPolicyRoute(): JSX.Element {\n const { t } = useTranslation(['settings', 'common'])\n const envQuery = useEnv()\n const updateEnv = useUpdateEnv()\n\n async function setValue(key: string, value: string | null): Promise<void> {\n try {\n await updateEnv.mutateAsync({ updates: { [key]: value } })\n toast.success(t('policy.savingToast'))\n } catch (err) {\n toast.error(describeError(err, t).message)\n }\n }\n\n const env = envQuery.data?.env ?? {}\n const skipPerms = envBool(env.IMHUB_DANGEROUSLY_SKIP_PERMISSIONS)\n const memEnabled = envBool(env.IMHUB_MEMORY_ENABLED)\n const viewerEnabled = envBool(env.IMHUB_VIEWER_ENABLED)\n const timeoutAllow = (env.IMHUB_TIMEOUT_DEFAULT ?? '').toLowerCase() === 'allow'\n const a2aMode = (env.IMHUB_A2A_NOTIFY_MODE ?? 'essential').toLowerCase()\n\n return (\n <div className=\"mx-auto flex max-w-4xl flex-col gap-4\">\n <header className=\"flex flex-col gap-1\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <h1 className=\"text-xl font-semibold\">{t('policy.title')}</h1>\n <Button\n variant=\"ghost\"\n size=\"sm\"\n className=\"ml-auto\"\n onClick={() => envQuery.refetch()}\n disabled={envQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {envQuery.isFetching ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('actions.refresh', { ns: 'common' })}</span>\n </Button>\n </div>\n <p className=\"text-sm text-text-dim\">{t('policy.subtitle')}</p>\n </header>\n\n {envQuery.isLoading ? (\n <div className=\"h-96 rounded-md bg-surface-2 animate-pulse\" />\n ) : (\n <div className=\"flex flex-col gap-3\">\n <SafetyCard\n value={skipPerms}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_DANGEROUSLY_SKIP_PERMISSIONS', v ? '1' : '0')}\n />\n <ApprovalCard\n allowOnTimeout={timeoutAllow}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_TIMEOUT_DEFAULT', v)}\n />\n <ToggleCard\n sectionKey=\"memory\"\n value={memEnabled}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_MEMORY_ENABLED', v ? '1' : '0')}\n />\n <ToggleCard\n sectionKey=\"viewer\"\n value={viewerEnabled}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_VIEWER_ENABLED', v ? '1' : '0')}\n />\n <A2ANotifyCard\n value={a2aMode}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_A2A_NOTIFY_MODE', v)}\n />\n </div>\n )}\n </div>\n )\n}\n\n/* ─────────────── Cards ─────────────── */\n\ninterface SafetyCardProps {\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\nfunction SafetyCard({ value, disabled, onChange }: SafetyCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section\n className={cn(\n 'rounded-md border p-4',\n value ? 'border-danger/60 bg-danger-bg/30' : 'border-border bg-surface',\n )}\n >\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <div className=\"flex flex-wrap items-center gap-2\">\n <span className=\"font-medium text-text\">{t('policy.safety.title')}</span>\n {value && (\n <Badge variant=\"danger\">\n <AlertTriangle className=\"h-3 w-3\" />\n ON\n </Badge>\n )}\n </div>\n <p className=\"mt-1 text-sm text-text-dim\">{t('policy.safety.description')}</p>\n {!value && (\n <p className=\"mt-1 text-xs text-text-muted\">{t('policy.safety.tagWarn')}</p>\n )}\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.safety.envKey')}\n </code>\n </div>\n <Toggle value={value} disabled={disabled} onChange={onChange} />\n </div>\n </section>\n )\n}\n\ninterface ApprovalCardProps {\n allowOnTimeout: boolean\n disabled: boolean\n onChange: (value: 'allow' | 'deny') => void\n}\n\nfunction ApprovalCard({ allowOnTimeout, disabled, onChange }: ApprovalCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex flex-col gap-2\">\n <span className=\"font-medium text-text\">{t('policy.approval.title')}</span>\n <p className=\"text-sm text-text-dim\">{t('policy.approval.description')}</p>\n <code className=\"self-start rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.approval.envKey')}\n </code>\n <div className=\"mt-2 flex flex-wrap gap-2\">\n <Button\n type=\"button\"\n variant={!allowOnTimeout ? 'default' : 'outline'}\n size=\"sm\"\n disabled={disabled}\n onClick={() => onChange('deny')}\n >\n {t('policy.approval.valDeny')}\n </Button>\n <Button\n type=\"button\"\n variant={allowOnTimeout ? 'default' : 'outline'}\n size=\"sm\"\n disabled={disabled}\n onClick={() => onChange('allow')}\n >\n {t('policy.approval.valAllow')}\n </Button>\n </div>\n </div>\n </section>\n )\n}\n\ninterface ToggleCardProps {\n sectionKey: 'memory' | 'viewer'\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\nfunction ToggleCard({ sectionKey, value, disabled, onChange }: ToggleCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <div className=\"flex flex-wrap items-center gap-2\">\n <span className=\"font-medium text-text\">{t(`policy.${sectionKey}.title`)}</span>\n <Badge variant={value ? 'success' : 'outline'}>{value ? 'ON' : 'OFF'}</Badge>\n </div>\n <p className=\"mt-1 text-sm text-text-dim\">{t(`policy.${sectionKey}.description`)}</p>\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t(`policy.${sectionKey}.envKey`)}\n </code>\n </div>\n <Toggle value={value} disabled={disabled} onChange={onChange} />\n </div>\n </section>\n )\n}\n\ninterface A2ANotifyCardProps {\n value: string\n disabled: boolean\n onChange: (v: string) => void\n}\n\nfunction A2ANotifyCard({ value, disabled, onChange }: A2ANotifyCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <span className=\"font-medium text-text\">{t('policy.a2aNotify.title')}</span>\n <p className=\"mt-1 text-sm text-text-dim\">{t('policy.a2aNotify.description')}</p>\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.a2aNotify.envKey')}\n </code>\n </div>\n <Select value={value} onValueChange={onChange} disabled={disabled}>\n <SelectTrigger className=\"w-36\">\n <SelectValue />\n </SelectTrigger>\n <SelectContent>\n <SelectItem value=\"essential\">{t('policy.a2aNotify.valEssential')}</SelectItem>\n <SelectItem value=\"verbose\">{t('policy.a2aNotify.valVerbose')}</SelectItem>\n <SelectItem value=\"off\">{t('policy.a2aNotify.valOff')}</SelectItem>\n </SelectContent>\n </Select>\n </div>\n </section>\n )\n}\n\ninterface ToggleProps {\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\n/** Thumb-style switch styled to the agim accent. Tailwind-only,\n * no Radix dep — keeps the click feel snappy. */\nfunction Toggle({ value, disabled, onChange }: ToggleProps): JSX.Element {\n return (\n <button\n type=\"button\"\n role=\"switch\"\n aria-checked={value}\n disabled={disabled}\n onClick={() => onChange(!value)}\n className={cn(\n 'relative inline-flex h-6 w-11 shrink-0 cursor-pointer items-center rounded-full transition-colors',\n 'focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-accent focus-visible:ring-offset-2 focus-visible:ring-offset-bg',\n 'disabled:cursor-not-allowed disabled:opacity-50',\n value ? 'bg-accent' : 'bg-surface-2 border border-border',\n )}\n >\n <span\n className={cn(\n 'inline-block h-5 w-5 rounded-full bg-white shadow transition-transform',\n value ? 'translate-x-5' : 'translate-x-0.5',\n )}\n />\n </button>\n )\n}\n"],"names":["envBool","v","t","SettingsPolicyRoute","useTranslation","envQuery","useEnv","updateEnv","useUpdateEnv","setValue","key","value","toast","err","describeError","env","skipPerms","memEnabled","viewerEnabled","timeoutAllow","a2aMode","jsxs","jsx","Button","Loader2","RefreshCcw","SafetyCard","ApprovalCard","ToggleCard","A2ANotifyCard","disabled","onChange","cn","Badge","AlertTriangle","Toggle","allowOnTimeout","sectionKey","Select","SelectTrigger","SelectValue","SelectContent","SelectItem"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"policy-BM1WRXH0.js","sources":["../../src/routes/settings/policy.tsx"],"sourcesContent":["/**\n * /settings/policy — dedicated UI for the highest-frequency env\n * toggles. Each is a one-click switch (or 2-3 option select) that\n * persists to `~/.agim/.env` via PUT /api/env immediately.\n *\n * Surfaced here:\n * * IMHUB_DANGEROUSLY_SKIP_PERMISSIONS (safety)\n * * IMHUB_TIMEOUT_DEFAULT (approval bus default)\n * * IMHUB_MEMORY_ENABLED (memory subsystem)\n * * IMHUB_VIEWER_ENABLED (long-message viewer)\n * * IMHUB_A2A_NOTIFY_MODE (cross-agent notify verbosity)\n *\n * All five are still editable in /settings/env. This page exists\n * because:\n * 1. They're the ones operators flip most often\n * 2. The env editor's table doesn't communicate \"this is a\n * boolean / 2-state / 3-state value\" — operators have to\n * know the literal strings \"1\"/\"0\"/\"allow\"/\"deny\"/etc.\n * 3. Safety toggle deserves a visible warning + danger color\n */\n\nimport { useTranslation } from 'react-i18next'\nimport { toast } from 'sonner'\nimport { AlertTriangle, Loader2, RefreshCcw } from 'lucide-react'\n\nimport { Badge } from '@/components/ui/badge'\nimport { Button } from '@/components/ui/button'\nimport {\n Select,\n SelectContent,\n SelectItem,\n SelectTrigger,\n SelectValue,\n} from '@/components/ui/select'\nimport { useEnv, useUpdateEnv } from '@/hooks/use-settings'\nimport { describeError } from '@/lib/api/errors'\nimport { cn } from '@/lib/utils'\n\n/** Treat the env value as a boolean — '1' / 'true' / 'yes' / 'on'\n * → true; everything else → false. Matches the backend's casual\n * truthy parsing in core/* modules. */\nfunction envBool(v: string | undefined): boolean {\n if (v == null) return false\n const t = v.toLowerCase()\n return t === '1' || t === 'true' || t === 'yes' || t === 'on'\n}\n\nexport default function SettingsPolicyRoute(): JSX.Element {\n const { t } = useTranslation(['settings', 'common'])\n const envQuery = useEnv()\n const updateEnv = useUpdateEnv()\n\n async function setValue(key: string, value: string | null): Promise<void> {\n try {\n await updateEnv.mutateAsync({ updates: { [key]: value } })\n toast.success(t('policy.savingToast'))\n } catch (err) {\n toast.error(describeError(err, t).message)\n }\n }\n\n const env = envQuery.data?.env ?? {}\n const skipPerms = envBool(env.IMHUB_DANGEROUSLY_SKIP_PERMISSIONS)\n const memEnabled = envBool(env.IMHUB_MEMORY_ENABLED)\n const viewerEnabled = envBool(env.IMHUB_VIEWER_ENABLED)\n const timeoutAllow = (env.IMHUB_TIMEOUT_DEFAULT ?? '').toLowerCase() === 'allow'\n const a2aMode = (env.IMHUB_A2A_NOTIFY_MODE ?? 'essential').toLowerCase()\n\n return (\n <div className=\"mx-auto flex max-w-4xl flex-col gap-4\">\n <header className=\"flex flex-col gap-1\">\n <div className=\"flex flex-wrap items-center gap-3\">\n <h1 className=\"text-xl font-semibold\">{t('policy.title')}</h1>\n <Button\n variant=\"ghost\"\n size=\"sm\"\n className=\"ml-auto\"\n onClick={() => envQuery.refetch()}\n disabled={envQuery.isFetching}\n aria-label={t('actions.refresh', { ns: 'common' })}\n >\n {envQuery.isFetching ? <Loader2 className=\"h-4 w-4 animate-spin\" /> : <RefreshCcw className=\"h-4 w-4\" />}\n <span className=\"hidden sm:inline\">{t('actions.refresh', { ns: 'common' })}</span>\n </Button>\n </div>\n <p className=\"text-sm text-text-dim\">{t('policy.subtitle')}</p>\n </header>\n\n {envQuery.isLoading ? (\n <div className=\"h-96 rounded-md bg-surface-2 animate-pulse\" />\n ) : (\n <div className=\"flex flex-col gap-3\">\n <SafetyCard\n value={skipPerms}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_DANGEROUSLY_SKIP_PERMISSIONS', v ? '1' : '0')}\n />\n <ApprovalCard\n allowOnTimeout={timeoutAllow}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_TIMEOUT_DEFAULT', v)}\n />\n <ToggleCard\n sectionKey=\"memory\"\n value={memEnabled}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_MEMORY_ENABLED', v ? '1' : '0')}\n />\n <ToggleCard\n sectionKey=\"viewer\"\n value={viewerEnabled}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_VIEWER_ENABLED', v ? '1' : '0')}\n />\n <A2ANotifyCard\n value={a2aMode}\n disabled={updateEnv.isPending}\n onChange={(v) => void setValue('IMHUB_A2A_NOTIFY_MODE', v)}\n />\n </div>\n )}\n </div>\n )\n}\n\n/* ─────────────── Cards ─────────────── */\n\ninterface SafetyCardProps {\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\nfunction SafetyCard({ value, disabled, onChange }: SafetyCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section\n className={cn(\n 'rounded-md border p-4',\n value ? 'border-danger/60 bg-danger-bg/30' : 'border-border bg-surface',\n )}\n >\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <div className=\"flex flex-wrap items-center gap-2\">\n <span className=\"font-medium text-text\">{t('policy.safety.title')}</span>\n {value && (\n <Badge variant=\"danger\">\n <AlertTriangle className=\"h-3 w-3\" />\n ON\n </Badge>\n )}\n </div>\n <p className=\"mt-1 text-sm text-text-dim\">{t('policy.safety.description')}</p>\n {!value && (\n <p className=\"mt-1 text-xs text-text-muted\">{t('policy.safety.tagWarn')}</p>\n )}\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.safety.envKey')}\n </code>\n </div>\n <Toggle value={value} disabled={disabled} onChange={onChange} />\n </div>\n </section>\n )\n}\n\ninterface ApprovalCardProps {\n allowOnTimeout: boolean\n disabled: boolean\n onChange: (value: 'allow' | 'deny') => void\n}\n\nfunction ApprovalCard({ allowOnTimeout, disabled, onChange }: ApprovalCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex flex-col gap-2\">\n <span className=\"font-medium text-text\">{t('policy.approval.title')}</span>\n <p className=\"text-sm text-text-dim\">{t('policy.approval.description')}</p>\n <code className=\"self-start rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.approval.envKey')}\n </code>\n <div className=\"mt-2 flex flex-wrap gap-2\">\n <Button\n type=\"button\"\n variant={!allowOnTimeout ? 'default' : 'outline'}\n size=\"sm\"\n disabled={disabled}\n onClick={() => onChange('deny')}\n >\n {t('policy.approval.valDeny')}\n </Button>\n <Button\n type=\"button\"\n variant={allowOnTimeout ? 'default' : 'outline'}\n size=\"sm\"\n disabled={disabled}\n onClick={() => onChange('allow')}\n >\n {t('policy.approval.valAllow')}\n </Button>\n </div>\n </div>\n </section>\n )\n}\n\ninterface ToggleCardProps {\n sectionKey: 'memory' | 'viewer'\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\nfunction ToggleCard({ sectionKey, value, disabled, onChange }: ToggleCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <div className=\"flex flex-wrap items-center gap-2\">\n <span className=\"font-medium text-text\">{t(`policy.${sectionKey}.title`)}</span>\n <Badge variant={value ? 'success' : 'outline'}>{value ? 'ON' : 'OFF'}</Badge>\n </div>\n <p className=\"mt-1 text-sm text-text-dim\">{t(`policy.${sectionKey}.description`)}</p>\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t(`policy.${sectionKey}.envKey`)}\n </code>\n </div>\n <Toggle value={value} disabled={disabled} onChange={onChange} />\n </div>\n </section>\n )\n}\n\ninterface A2ANotifyCardProps {\n value: string\n disabled: boolean\n onChange: (v: string) => void\n}\n\nfunction A2ANotifyCard({ value, disabled, onChange }: A2ANotifyCardProps): JSX.Element {\n const { t } = useTranslation('settings')\n return (\n <section className=\"rounded-md border border-border bg-surface p-4\">\n <div className=\"flex items-start gap-3\">\n <div className=\"flex-1\">\n <span className=\"font-medium text-text\">{t('policy.a2aNotify.title')}</span>\n <p className=\"mt-1 text-sm text-text-dim\">{t('policy.a2aNotify.description')}</p>\n <code className=\"mt-2 inline-block rounded bg-surface-2 px-1.5 py-0.5 text-xs text-text-muted\">\n {t('policy.a2aNotify.envKey')}\n </code>\n </div>\n <Select value={value} onValueChange={onChange} disabled={disabled}>\n <SelectTrigger className=\"w-36\">\n <SelectValue />\n </SelectTrigger>\n <SelectContent>\n <SelectItem value=\"essential\">{t('policy.a2aNotify.valEssential')}</SelectItem>\n <SelectItem value=\"verbose\">{t('policy.a2aNotify.valVerbose')}</SelectItem>\n <SelectItem value=\"off\">{t('policy.a2aNotify.valOff')}</SelectItem>\n </SelectContent>\n </Select>\n </div>\n </section>\n )\n}\n\ninterface ToggleProps {\n value: boolean\n disabled: boolean\n onChange: (v: boolean) => void\n}\n\n/** Thumb-style switch styled to the agim accent. Tailwind-only,\n * no Radix dep — keeps the click feel snappy. */\nfunction Toggle({ value, disabled, onChange }: ToggleProps): JSX.Element {\n return (\n <button\n type=\"button\"\n role=\"switch\"\n aria-checked={value}\n disabled={disabled}\n onClick={() => onChange(!value)}\n className={cn(\n 'relative inline-flex h-6 w-11 shrink-0 cursor-pointer items-center rounded-full transition-colors',\n 'focus-visible:outline-none focus-visible:ring-2 focus-visible:ring-accent focus-visible:ring-offset-2 focus-visible:ring-offset-bg',\n 'disabled:cursor-not-allowed disabled:opacity-50',\n value ? 'bg-accent' : 'bg-surface-2 border border-border',\n )}\n >\n <span\n className={cn(\n 'inline-block h-5 w-5 rounded-full bg-white shadow transition-transform',\n value ? 'translate-x-5' : 'translate-x-0.5',\n )}\n />\n </button>\n )\n}\n"],"names":["envBool","v","t","SettingsPolicyRoute","useTranslation","envQuery","useEnv","updateEnv","useUpdateEnv","setValue","key","value","toast","err","describeError","env","skipPerms","memEnabled","viewerEnabled","timeoutAllow","a2aMode","jsxs","jsx","Button","Loader2","RefreshCcw","SafetyCard","ApprovalCard","ToggleCard","A2ANotifyCard","disabled","onChange","cn","Badge","AlertTriangle","Toggle","allowOnTimeout","sectionKey","Select","SelectTrigger","SelectValue","SelectContent","SelectItem"],"mappings":"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"}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
|
-
import{n as t}from"./index-
|
|
1
|
+
import{n as t}from"./index-DEWFfW_Z.js";/**
|
|
2
2
|
* @license lucide-react v0.469.0 - ISC
|
|
3
3
|
*
|
|
4
4
|
* This source code is licensed under the ISC license.
|
|
5
5
|
* See the LICENSE file in the root directory of this source tree.
|
|
6
6
|
*/const h=t("QrCode",[["rect",{width:"5",height:"5",x:"3",y:"3",rx:"1",key:"1tu5fj"}],["rect",{width:"5",height:"5",x:"16",y:"3",rx:"1",key:"1v8r4q"}],["rect",{width:"5",height:"5",x:"3",y:"16",rx:"1",key:"1x03jg"}],["path",{d:"M21 16h-3a2 2 0 0 0-2 2v3",key:"177gqh"}],["path",{d:"M21 21v.01",key:"ents32"}],["path",{d:"M12 7v3a2 2 0 0 1-2 2H7",key:"8crl2c"}],["path",{d:"M3 12h.01",key:"nlz23k"}],["path",{d:"M12 3h.01",key:"n36tog"}],["path",{d:"M12 16v.01",key:"133mhm"}],["path",{d:"M16 12h1",key:"1slzba"}],["path",{d:"M21 12v.01",key:"1lwtk9"}],["path",{d:"M12 21v-1",key:"1880an"}]]);export{h as Q};
|
|
7
|
-
//# sourceMappingURL=qr-code-
|
|
7
|
+
//# sourceMappingURL=qr-code-DcKs5fi3.js.map
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"qr-code-
|
|
1
|
+
{"version":3,"file":"qr-code-DcKs5fi3.js","sources":["../../node_modules/lucide-react/dist/esm/icons/qr-code.js"],"sourcesContent":["/**\n * @license lucide-react v0.469.0 - ISC\n *\n * This source code is licensed under the ISC license.\n * See the LICENSE file in the root directory of this source tree.\n */\n\nimport createLucideIcon from '../createLucideIcon.js';\n\nconst QrCode = createLucideIcon(\"QrCode\", [\n [\"rect\", { width: \"5\", height: \"5\", x: \"3\", y: \"3\", rx: \"1\", key: \"1tu5fj\" }],\n [\"rect\", { width: \"5\", height: \"5\", x: \"16\", y: \"3\", rx: \"1\", key: \"1v8r4q\" }],\n [\"rect\", { width: \"5\", height: \"5\", x: \"3\", y: \"16\", rx: \"1\", key: \"1x03jg\" }],\n [\"path\", { d: \"M21 16h-3a2 2 0 0 0-2 2v3\", key: \"177gqh\" }],\n [\"path\", { d: \"M21 21v.01\", key: \"ents32\" }],\n [\"path\", { d: \"M12 7v3a2 2 0 0 1-2 2H7\", key: \"8crl2c\" }],\n [\"path\", { d: \"M3 12h.01\", key: \"nlz23k\" }],\n [\"path\", { d: \"M12 3h.01\", key: \"n36tog\" }],\n [\"path\", { d: \"M12 16v.01\", key: \"133mhm\" }],\n [\"path\", { d: \"M16 12h1\", key: \"1slzba\" }],\n [\"path\", { d: \"M21 12v.01\", key: \"1lwtk9\" }],\n [\"path\", { d: \"M12 21v-1\", key: \"1880an\" }]\n]);\n\nexport { QrCode as default };\n//# sourceMappingURL=qr-code.js.map\n"],"names":["QrCode","createLucideIcon"],"mappings":"wCAAA;AAAA;AAAA;AAAA;AAAA;AAAA,GASK,MAACA,EAASC,EAAiB,SAAU,CACxC,CAAC,OAAQ,CAAE,MAAO,IAAK,OAAQ,IAAK,EAAG,IAAK,EAAG,IAAK,GAAI,IAAK,IAAK,QAAQ,CAAE,EAC5E,CAAC,OAAQ,CAAE,MAAO,IAAK,OAAQ,IAAK,EAAG,KAAM,EAAG,IAAK,GAAI,IAAK,IAAK,QAAQ,CAAE,EAC7E,CAAC,OAAQ,CAAE,MAAO,IAAK,OAAQ,IAAK,EAAG,IAAK,EAAG,KAAM,GAAI,IAAK,IAAK,QAAQ,CAAE,EAC7E,CAAC,OAAQ,CAAE,EAAG,4BAA6B,IAAK,QAAQ,CAAE,EAC1D,CAAC,OAAQ,CAAE,EAAG,aAAc,IAAK,QAAQ,CAAE,EAC3C,CAAC,OAAQ,CAAE,EAAG,0BAA2B,IAAK,QAAQ,CAAE,EACxD,CAAC,OAAQ,CAAE,EAAG,YAAa,IAAK,QAAQ,CAAE,EAC1C,CAAC,OAAQ,CAAE,EAAG,YAAa,IAAK,QAAQ,CAAE,EAC1C,CAAC,OAAQ,CAAE,EAAG,aAAc,IAAK,QAAQ,CAAE,EAC3C,CAAC,OAAQ,CAAE,EAAG,WAAY,IAAK,QAAQ,CAAE,EACzC,CAAC,OAAQ,CAAE,EAAG,aAAc,IAAK,QAAQ,CAAE,EAC3C,CAAC,OAAQ,CAAE,EAAG,YAAa,IAAK,QAAQ,CAAE,CAC5C,CAAC","x_google_ignoreList":[0]}
|