agim-cli 1.2.74 → 1.2.82

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (173) hide show
  1. package/CHANGELOG.md +215 -0
  2. package/dist/cli-ui/tui/app.d.ts +22 -0
  3. package/dist/cli-ui/tui/app.d.ts.map +1 -0
  4. package/dist/cli-ui/tui/app.js +578 -0
  5. package/dist/cli-ui/tui/app.js.map +1 -0
  6. package/dist/cli-ui/tui/index.d.ts +7 -0
  7. package/dist/cli-ui/tui/index.d.ts.map +1 -0
  8. package/dist/cli-ui/tui/index.js +125 -0
  9. package/dist/cli-ui/tui/index.js.map +1 -0
  10. package/dist/cli-ui/tui/markdown.d.ts +5 -0
  11. package/dist/cli-ui/tui/markdown.d.ts.map +1 -0
  12. package/dist/cli-ui/tui/markdown.js +145 -0
  13. package/dist/cli-ui/tui/markdown.js.map +1 -0
  14. package/dist/cli-ui/tui/sessions.d.ts +31 -0
  15. package/dist/cli-ui/tui/sessions.d.ts.map +1 -0
  16. package/dist/cli-ui/tui/sessions.js +107 -0
  17. package/dist/cli-ui/tui/sessions.js.map +1 -0
  18. package/dist/cli.js +12 -0
  19. package/dist/cli.js.map +1 -1
  20. package/dist/web/public/assets/{a2a-BbtW9q1L.js → a2a-CWXsu7Oz.js} +2 -2
  21. package/dist/web/public/assets/{a2a-BbtW9q1L.js.map → a2a-CWXsu7Oz.js.map} +1 -1
  22. package/dist/web/public/assets/{activity-CJmQLZ6_.js → activity-CQ_aoBSr.js} +2 -2
  23. package/dist/web/public/assets/{activity-CJmQLZ6_.js.map → activity-CQ_aoBSr.js.map} +1 -1
  24. package/dist/web/public/assets/{admins-BJP9koxS.js → admins-eP0x1_cs.js} +2 -2
  25. package/dist/web/public/assets/{admins-BJP9koxS.js.map → admins-eP0x1_cs.js.map} +1 -1
  26. package/dist/web/public/assets/{agents-DC0XFC6e.js → agents-CS9zwgxI.js} +2 -2
  27. package/dist/web/public/assets/{agents-DC0XFC6e.js.map → agents-CS9zwgxI.js.map} +1 -1
  28. package/dist/web/public/assets/{approvals-DiPkpPN4.js → approvals-ngCeTrqa.js} +2 -2
  29. package/dist/web/public/assets/{approvals-DiPkpPN4.js.map → approvals-ngCeTrqa.js.map} +1 -1
  30. package/dist/web/public/assets/{asks-CG9chQgT.js → asks-CIJyUfTW.js} +2 -2
  31. package/dist/web/public/assets/{asks-CG9chQgT.js.map → asks-CIJyUfTW.js.map} +1 -1
  32. package/dist/web/public/assets/{audit-B40mxlW1.js → audit-ATQxEzuW.js} +2 -2
  33. package/dist/web/public/assets/{audit-B40mxlW1.js.map → audit-ATQxEzuW.js.map} +1 -1
  34. package/dist/web/public/assets/{bell-BC8Jqt9f.js → bell-aelaDeaH.js} +2 -2
  35. package/dist/web/public/assets/{bell-BC8Jqt9f.js.map → bell-aelaDeaH.js.map} +1 -1
  36. package/dist/web/public/assets/{bgjobs-ClrQ2jzx.js → bgjobs-Dte-HLN1.js} +2 -2
  37. package/dist/web/public/assets/{bgjobs-ClrQ2jzx.js.map → bgjobs-Dte-HLN1.js.map} +1 -1
  38. package/dist/web/public/assets/{brain-BBx7RF2j.js → brain-9-qx3BG8.js} +2 -2
  39. package/dist/web/public/assets/{brain-BBx7RF2j.js.map → brain-9-qx3BG8.js.map} +1 -1
  40. package/dist/web/public/assets/{briefcase-TihsRkSy.js → briefcase-B7t6pp3X.js} +2 -2
  41. package/dist/web/public/assets/{briefcase-TihsRkSy.js.map → briefcase-B7t6pp3X.js.map} +1 -1
  42. package/dist/web/public/assets/{chevron-right-DTLZLXDP.js → chevron-right-Bz8nTKHc.js} +2 -2
  43. package/dist/web/public/assets/{chevron-right-DTLZLXDP.js.map → chevron-right-Bz8nTKHc.js.map} +1 -1
  44. package/dist/web/public/assets/{circle-check-EHM2OMD5.js → circle-check-BMeq4ILK.js} +2 -2
  45. package/dist/web/public/assets/{circle-check-EHM2OMD5.js.map → circle-check-BMeq4ILK.js.map} +1 -1
  46. package/dist/web/public/assets/{circle-check-big-DJXNAZ3u.js → circle-check-big-BboRrbmc.js} +2 -2
  47. package/dist/web/public/assets/{circle-check-big-DJXNAZ3u.js.map → circle-check-big-BboRrbmc.js.map} +1 -1
  48. package/dist/web/public/assets/{circle-x-DsaHSb_C.js → circle-x-D_Y7XPyr.js} +2 -2
  49. package/dist/web/public/assets/{circle-x-DsaHSb_C.js.map → circle-x-D_Y7XPyr.js.map} +1 -1
  50. package/dist/web/public/assets/{confirm-dialog-DezSK6wB.js → confirm-dialog-K2ZSoNw3.js} +2 -2
  51. package/dist/web/public/assets/{confirm-dialog-DezSK6wB.js.map → confirm-dialog-K2ZSoNw3.js.map} +1 -1
  52. package/dist/web/public/assets/{data-table-DdSnbgyt.js → data-table-DAxlDpJz.js} +2 -2
  53. package/dist/web/public/assets/{data-table-DdSnbgyt.js.map → data-table-DAxlDpJz.js.map} +1 -1
  54. package/dist/web/public/assets/{dialog-45x-p0sR.js → dialog-DVgp7mMc.js} +2 -2
  55. package/dist/web/public/assets/{dialog-45x-p0sR.js.map → dialog-DVgp7mMc.js.map} +1 -1
  56. package/dist/web/public/assets/{download-BL4jeu4M.js → download-ylGDouA1.js} +2 -2
  57. package/dist/web/public/assets/{download-BL4jeu4M.js.map → download-ylGDouA1.js.map} +1 -1
  58. package/dist/web/public/assets/{email-BGUO-gme.js → email-TTd5YGoQ.js} +2 -2
  59. package/dist/web/public/assets/{email-BGUO-gme.js.map → email-TTd5YGoQ.js.map} +1 -1
  60. package/dist/web/public/assets/{empty-state-n-LfHo6N.js → empty-state-Dl99CYKJ.js} +2 -2
  61. package/dist/web/public/assets/{empty-state-n-LfHo6N.js.map → empty-state-Dl99CYKJ.js.map} +1 -1
  62. package/dist/web/public/assets/{external-link-CZd6ma6Y.js → external-link-CHOJij7R.js} +2 -2
  63. package/dist/web/public/assets/{external-link-CZd6ma6Y.js.map → external-link-CHOJij7R.js.map} +1 -1
  64. package/dist/web/public/assets/{eye-LsErAgqh.js → eye-BgiwYmz5.js} +2 -2
  65. package/dist/web/public/assets/{eye-LsErAgqh.js.map → eye-BgiwYmz5.js.map} +1 -1
  66. package/dist/web/public/assets/{facts-CxZ3L_7a.js → facts-BC2xi2cn.js} +2 -2
  67. package/dist/web/public/assets/{facts-CxZ3L_7a.js.map → facts-BC2xi2cn.js.map} +1 -1
  68. package/dist/web/public/assets/{goals-BjzgqVnW.js → goals-Cdv7CH0b.js} +2 -2
  69. package/dist/web/public/assets/{goals-BjzgqVnW.js.map → goals-Cdv7CH0b.js.map} +1 -1
  70. package/dist/web/public/assets/{health-BYX5IK98.js → health-CODeqKI3.js} +2 -2
  71. package/dist/web/public/assets/{health-BYX5IK98.js.map → health-CODeqKI3.js.map} +1 -1
  72. package/dist/web/public/assets/{heart-pulse-D_xUK9r0.js → heart-pulse-CaKtJESB.js} +2 -2
  73. package/dist/web/public/assets/{heart-pulse-D_xUK9r0.js.map → heart-pulse-CaKtJESB.js.map} +1 -1
  74. package/dist/web/public/assets/{heartbeat-DnSegIYS.js → heartbeat-DGznBjhs.js} +2 -2
  75. package/dist/web/public/assets/{heartbeat-DnSegIYS.js.map → heartbeat-DGznBjhs.js.map} +1 -1
  76. package/dist/web/public/assets/{hot-C5TxCTVL.js → hot-CNKZjFmQ.js} +2 -2
  77. package/dist/web/public/assets/{hot-C5TxCTVL.js.map → hot-CNKZjFmQ.js.map} +1 -1
  78. package/dist/web/public/assets/{index-CbWhcThC.js → index-SwfCEbMh.js} +3 -3
  79. package/dist/web/public/assets/{index-CbWhcThC.js.map → index-SwfCEbMh.js.map} +1 -1
  80. package/dist/web/public/assets/{installed-D_Hjs7uj.js → installed-DqE0CqJD.js} +2 -2
  81. package/dist/web/public/assets/{installed-D_Hjs7uj.js.map → installed-DqE0CqJD.js.map} +1 -1
  82. package/dist/web/public/assets/{jobs-DWtjJIAD.js → jobs-BlVHvUJL.js} +2 -2
  83. package/dist/web/public/assets/{jobs-DWtjJIAD.js.map → jobs-BlVHvUJL.js.map} +1 -1
  84. package/dist/web/public/assets/{layout-BLK9XuQB.js → layout-BiUaeLWY.js} +2 -2
  85. package/dist/web/public/assets/{layout-BLK9XuQB.js.map → layout-BiUaeLWY.js.map} +1 -1
  86. package/dist/web/public/assets/{layout-CvvZcaiO.js → layout-CIDMPUGA.js} +2 -2
  87. package/dist/web/public/assets/{layout-CvvZcaiO.js.map → layout-CIDMPUGA.js.map} +1 -1
  88. package/dist/web/public/assets/{layout-CTyy2kgf.js → layout-CdoRXtfJ.js} +2 -2
  89. package/dist/web/public/assets/{layout-CTyy2kgf.js.map → layout-CdoRXtfJ.js.map} +1 -1
  90. package/dist/web/public/assets/{layout-D1-LnIA_.js → layout-CrgrlI3C.js} +2 -2
  91. package/dist/web/public/assets/{layout-D1-LnIA_.js.map → layout-CrgrlI3C.js.map} +1 -1
  92. package/dist/web/public/assets/{layout-54-PzplU.js → layout-DQcPGciJ.js} +2 -2
  93. package/dist/web/public/assets/{layout-54-PzplU.js.map → layout-DQcPGciJ.js.map} +1 -1
  94. package/dist/web/public/assets/{llm-D59Tv6ne.js → llm-C9WnjLdH.js} +2 -2
  95. package/dist/web/public/assets/{llm-D59Tv6ne.js.map → llm-C9WnjLdH.js.map} +1 -1
  96. package/dist/web/public/assets/{loader-circle-U64eR4W2.js → loader-circle-BYuiEgu1.js} +2 -2
  97. package/dist/web/public/assets/{loader-circle-U64eR4W2.js.map → loader-circle-BYuiEgu1.js.map} +1 -1
  98. package/dist/web/public/assets/{map-pin-D08YlPs3.js → map-pin-CSu279sg.js} +2 -2
  99. package/dist/web/public/assets/{map-pin-D08YlPs3.js.map → map-pin-CSu279sg.js.map} +1 -1
  100. package/dist/web/public/assets/{mcp-Br9fBIWu.js → mcp-DhEhDagh.js} +2 -2
  101. package/dist/web/public/assets/{mcp-Br9fBIWu.js.map → mcp-DhEhDagh.js.map} +1 -1
  102. package/dist/web/public/assets/{memos-nZKV3SLq.js → memos-CmWcQsqu.js} +2 -2
  103. package/dist/web/public/assets/{memos-nZKV3SLq.js.map → memos-CmWcQsqu.js.map} +1 -1
  104. package/dist/web/public/assets/{messengers-C8ss4WVx.js → messengers-Dzgy15aJ.js} +2 -2
  105. package/dist/web/public/assets/{messengers-C8ss4WVx.js.map → messengers-Dzgy15aJ.js.map} +1 -1
  106. package/dist/web/public/assets/{native-agent-BiiYK91m.js → native-agent-oxVczUVP.js} +2 -2
  107. package/dist/web/public/assets/{native-agent-BiiYK91m.js.map → native-agent-oxVczUVP.js.map} +1 -1
  108. package/dist/web/public/assets/{network-D9rhTHz5.js → network-VKawx_Mf.js} +2 -2
  109. package/dist/web/public/assets/{network-D9rhTHz5.js.map → network-VKawx_Mf.js.map} +1 -1
  110. package/dist/web/public/assets/{outbox-BS_gla4W.js → outbox-tCNMec-W.js} +2 -2
  111. package/dist/web/public/assets/{outbox-BS_gla4W.js.map → outbox-tCNMec-W.js.map} +1 -1
  112. package/dist/web/public/assets/{pagination-CSuYj-hv.js → pagination-CoFiNhmI.js} +2 -2
  113. package/dist/web/public/assets/{pagination-CSuYj-hv.js.map → pagination-CoFiNhmI.js.map} +1 -1
  114. package/dist/web/public/assets/{persona-BByKd8Zd.js → persona-BPM9r0mz.js} +2 -2
  115. package/dist/web/public/assets/{persona-BByKd8Zd.js.map → persona-BPM9r0mz.js.map} +1 -1
  116. package/dist/web/public/assets/{play-B_11jKz_.js → play-AQXMreBP.js} +2 -2
  117. package/dist/web/public/assets/{play-B_11jKz_.js.map → play-AQXMreBP.js.map} +1 -1
  118. package/dist/web/public/assets/{plus-BxhCliGV.js → plus-Dxn0-UrW.js} +2 -2
  119. package/dist/web/public/assets/{plus-BxhCliGV.js.map → plus-Dxn0-UrW.js.map} +1 -1
  120. package/dist/web/public/assets/{policy-CHbUM0MU.js → policy-B3OVFhEU.js} +2 -2
  121. package/dist/web/public/assets/{policy-CHbUM0MU.js.map → policy-B3OVFhEU.js.map} +1 -1
  122. package/dist/web/public/assets/{refresh-ccw-BKw5Agez.js → refresh-ccw-BCY32ruL.js} +2 -2
  123. package/dist/web/public/assets/{refresh-ccw-BKw5Agez.js.map → refresh-ccw-BCY32ruL.js.map} +1 -1
  124. package/dist/web/public/assets/{reminders-_MsAKlS7.js → reminders-CE8FDfs4.js} +2 -2
  125. package/dist/web/public/assets/{reminders-_MsAKlS7.js.map → reminders-CE8FDfs4.js.map} +1 -1
  126. package/dist/web/public/assets/{save-DznSJZGN.js → save-DL2CVfM9.js} +2 -2
  127. package/dist/web/public/assets/{save-DznSJZGN.js.map → save-DL2CVfM9.js.map} +1 -1
  128. package/dist/web/public/assets/{schedules-CiRZXonB.js → schedules-QI2R8JnP.js} +2 -2
  129. package/dist/web/public/assets/{schedules-CiRZXonB.js.map → schedules-QI2R8JnP.js.map} +1 -1
  130. package/dist/web/public/assets/{search-CXr_r7L8.js → search-eX2P2oxa.js} +2 -2
  131. package/dist/web/public/assets/{search-CXr_r7L8.js.map → search-eX2P2oxa.js.map} +1 -1
  132. package/dist/web/public/assets/{security-CjySIq-k.js → security-DnuDl-Ua.js} +2 -2
  133. package/dist/web/public/assets/{security-CjySIq-k.js.map → security-DnuDl-Ua.js.map} +1 -1
  134. package/dist/web/public/assets/{service-LXlgJooI.js → service-NBv0B47N.js} +2 -2
  135. package/dist/web/public/assets/{service-LXlgJooI.js.map → service-NBv0B47N.js.map} +1 -1
  136. package/dist/web/public/assets/{status-badge-BsPU9NHK.js → status-badge-BgYMOzvd.js} +2 -2
  137. package/dist/web/public/assets/{status-badge-BsPU9NHK.js.map → status-badge-BgYMOzvd.js.map} +1 -1
  138. package/dist/web/public/assets/{subtasks-DM8tJkC7.js → subtasks-Dc7MIwsy.js} +2 -2
  139. package/dist/web/public/assets/{subtasks-DM8tJkC7.js.map → subtasks-Dc7MIwsy.js.map} +1 -1
  140. package/dist/web/public/assets/{table-CQbO75bn.js → table-CwXBhLOR.js} +2 -2
  141. package/dist/web/public/assets/{table-CQbO75bn.js.map → table-CwXBhLOR.js.map} +1 -1
  142. package/dist/web/public/assets/{topn-CaCYQ1NI.js → topn-2VUdLMlv.js} +2 -2
  143. package/dist/web/public/assets/{topn-CaCYQ1NI.js.map → topn-2VUdLMlv.js.map} +1 -1
  144. package/dist/web/public/assets/{trash-2-CdgBbY1Z.js → trash-2-Dx3VvXKw.js} +2 -2
  145. package/dist/web/public/assets/{trash-2-CdgBbY1Z.js.map → trash-2-Dx3VvXKw.js.map} +1 -1
  146. package/dist/web/public/assets/{use-background-tasks-DUDxcbbl.js → use-background-tasks-DloEt5di.js} +2 -2
  147. package/dist/web/public/assets/{use-background-tasks-DUDxcbbl.js.map → use-background-tasks-DloEt5di.js.map} +1 -1
  148. package/dist/web/public/assets/{use-llm-admin-Bpy7nDu-.js → use-llm-admin-C1P5gnfI.js} +2 -2
  149. package/dist/web/public/assets/{use-llm-admin-Bpy7nDu-.js.map → use-llm-admin-C1P5gnfI.js.map} +1 -1
  150. package/dist/web/public/assets/{use-memory-B00AYXi0.js → use-memory-DvKK1Ss3.js} +2 -2
  151. package/dist/web/public/assets/{use-memory-B00AYXi0.js.map → use-memory-DvKK1Ss3.js.map} +1 -1
  152. package/dist/web/public/assets/{use-observability-7ETfQyEP.js → use-observability-3xbug_pm.js} +2 -2
  153. package/dist/web/public/assets/{use-observability-7ETfQyEP.js.map → use-observability-3xbug_pm.js.map} +1 -1
  154. package/dist/web/public/assets/{use-settings-tzqyzhw3.js → use-settings-DB1Hur3n.js} +2 -2
  155. package/dist/web/public/assets/{use-settings-tzqyzhw3.js.map → use-settings-DB1Hur3n.js.map} +1 -1
  156. package/dist/web/public/assets/{use-workspace-B5gbK4s5.js → use-workspace-CKh9LYh0.js} +2 -2
  157. package/dist/web/public/assets/{use-workspace-B5gbK4s5.js.map → use-workspace-CKh9LYh0.js.map} +1 -1
  158. package/dist/web/public/assets/{useQuery-wnQifGeZ.js → useQuery-DhsW2X2S.js} +2 -2
  159. package/dist/web/public/assets/{useQuery-wnQifGeZ.js.map → useQuery-DhsW2X2S.js.map} +1 -1
  160. package/dist/web/public/assets/vector-BqCkB0IG.js +2 -0
  161. package/dist/web/public/assets/vector-BqCkB0IG.js.map +1 -0
  162. package/dist/web/public/assets/{viewer-C0f5b5eT.js → viewer-Dk0E_ROf.js} +2 -2
  163. package/dist/web/public/assets/{viewer-C0f5b5eT.js.map → viewer-Dk0E_ROf.js.map} +1 -1
  164. package/dist/web/public/assets/{workspace-CGE46-O2.js → workspace-BvcEO_Bp.js} +2 -2
  165. package/dist/web/public/assets/{workspace-CGE46-O2.js.map → workspace-BvcEO_Bp.js.map} +1 -1
  166. package/dist/web/public/assets/{workspaces-CqDIcIXo.js → workspaces-NE7wQUjq.js} +2 -2
  167. package/dist/web/public/assets/{workspaces-CqDIcIXo.js.map → workspaces-NE7wQUjq.js.map} +1 -1
  168. package/dist/web/public/assets/{x-DBZPbfu3.js → x-C8V9ODI5.js} +2 -2
  169. package/dist/web/public/assets/{x-DBZPbfu3.js.map → x-C8V9ODI5.js.map} +1 -1
  170. package/dist/web/public/index.html +1 -1
  171. package/package.json +5 -1
  172. package/dist/web/public/assets/vector-or1-MfRX.js +0 -2
  173. package/dist/web/public/assets/vector-or1-MfRX.js.map +0 -1
@@ -0,0 +1,125 @@
1
+ // agim TUI entry — wired into `agim tui` subcommand.
2
+ //
3
+ // Modes:
4
+ // * fresh: agim tui [--agent <name>]
5
+ // * resume: agim tui --resume <session-id> (auto-picks last if --resume=)
6
+ // * list: agim tui --list-sessions
7
+ //
8
+ // Sessions persist to <AGIM_HOME>/tui-sessions/<id>.json after each
9
+ // agent turn and on graceful exit. On exit we print the resume hint
10
+ // + a trailing newline so the next shell prompt doesn't collide with
11
+ // the last rendered frame.
12
+ import React from 'react';
13
+ import { render } from 'ink';
14
+ import { TuiApp } from './app.js';
15
+ import { registry } from '../../core/registry.js';
16
+ import { loadConfig } from '../../core/onboarding.js';
17
+ import { logger as rootLogger } from '../../core/logger.js';
18
+ import { generateSessionId, listSessions, loadSession, } from './sessions.js';
19
+ const log = rootLogger.child({ component: 'tui' });
20
+ function formatSessionLine(s) {
21
+ const ts = s.updatedAt.replace('T', ' ').slice(0, 19);
22
+ const ag = s.agent ? ` · ${s.agent}` : '';
23
+ const msgs = s.messages > 0 ? ` · ${s.messages} 条` : '';
24
+ return `${s.id} ${ts}${ag}${msgs}`;
25
+ }
26
+ export async function runTui(opts = {}) {
27
+ // --list-sessions: print and exit (no TTY required for this).
28
+ if (opts.listSessions) {
29
+ const sessions = listSessions(50, true);
30
+ if (sessions.length === 0) {
31
+ console.log('(没有任何已保存的 TUI 会话)');
32
+ return;
33
+ }
34
+ console.log(`找到 ${sessions.length} 个 TUI 会话(最新在前):\n`);
35
+ for (const s of sessions)
36
+ console.log(' ' + formatSessionLine(s));
37
+ console.log('\n用法:agim tui --resume <id>');
38
+ return;
39
+ }
40
+ if (!process.stdout.isTTY) {
41
+ console.error('agim tui: stdout is not a TTY — TUI requires an interactive terminal.');
42
+ process.exit(1);
43
+ }
44
+ // Resolve --resume: empty string / "last" means pick most recent;
45
+ // explicit id means look that one up. Either way, returns null if
46
+ // we couldn't find it and we treat that as a fresh start with a
47
+ // warning.
48
+ let resumed;
49
+ let sessionId = generateSessionId();
50
+ let resumeWarning;
51
+ if (opts.resume !== undefined) {
52
+ const wantedId = opts.resume.trim();
53
+ if (!wantedId || wantedId === 'last') {
54
+ const sessions = listSessions(1, true);
55
+ if (sessions.length === 0) {
56
+ resumeWarning = '没有可恢复的会话,按新会话启动。';
57
+ }
58
+ else {
59
+ const s = loadSession(sessions[0].id);
60
+ if (s) {
61
+ resumed = { id: s.id, agent: s.agent, messages: s.messages };
62
+ sessionId = s.id;
63
+ }
64
+ else {
65
+ resumeWarning = `读取最新会话 ${sessions[0].id} 失败,按新会话启动。`;
66
+ }
67
+ }
68
+ }
69
+ else {
70
+ const s = loadSession(wantedId);
71
+ if (s) {
72
+ resumed = { id: s.id, agent: s.agent, messages: s.messages };
73
+ sessionId = s.id;
74
+ }
75
+ else {
76
+ resumeWarning = `没找到会话 "${wantedId}",按新会话启动。`;
77
+ }
78
+ }
79
+ }
80
+ const wantVerbose = process.env.IMHUB_TUI_VERBOSE === '1';
81
+ const savedLevel = rootLogger.level;
82
+ if (!wantVerbose)
83
+ rootLogger.level = 'silent';
84
+ // Clear screen + park cursor at top-left.
85
+ process.stdout.write('\x1b[2J\x1b[H');
86
+ try {
87
+ await registry.loadBuiltInPlugins();
88
+ const cfg = await loadConfig();
89
+ if (cfg.acpAgents && cfg.acpAgents.length > 0) {
90
+ await registry.loadACPAgents(cfg.acpAgents);
91
+ }
92
+ }
93
+ catch (err) {
94
+ log.warn({ event: 'tui.registry.load_failed', err: err instanceof Error ? err.message : String(err) }, 'registry / config load failed — proceeding best-effort');
95
+ }
96
+ let initialAgent = opts.agent ?? resumed?.agent;
97
+ if (initialAgent) {
98
+ const found = registry.findAgent(initialAgent);
99
+ if (!found) {
100
+ const list = registry.listAgents();
101
+ console.error(`agim tui: agent "${initialAgent}" not found. Available: ${list.join(', ') || '<none>'}`);
102
+ process.exit(1);
103
+ }
104
+ initialAgent = found.name;
105
+ }
106
+ const { waitUntilExit } = render(React.createElement(TuiApp, { initialAgent, resumed, sessionId }), { patchConsole: true, exitOnCtrlC: true });
107
+ try {
108
+ await waitUntilExit();
109
+ }
110
+ finally {
111
+ rootLogger.level = savedLevel;
112
+ // v1.2.78 — drop a clean newline and print the resume hint AFTER
113
+ // Ink relinquishes the screen. Without these the next shell
114
+ // prompt collides with the last rendered frame, and the user has
115
+ // no way to know they can pick up where they left off.
116
+ process.stdout.write('\n');
117
+ if (resumeWarning) {
118
+ console.warn('⚠ ' + resumeWarning);
119
+ }
120
+ console.log(`会话 ID:${sessionId}`);
121
+ console.log(`恢复命令:agim tui --resume ${sessionId}`);
122
+ console.log(`查看所有会话:agim tui --list-sessions`);
123
+ }
124
+ }
125
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../../src/cli-ui/tui/index.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,5 @@
1
+ /** Render arbitrary markdown source as Ink components. */
2
+ export declare function Markdown({ source }: {
3
+ source: string;
4
+ }): JSX.Element;
5
+ //# sourceMappingURL=markdown.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"markdown.d.ts","sourceRoot":"","sources":["../../../src/cli-ui/tui/markdown.tsx"],"names":[],"mappings":"AAmMA,0DAA0D;AAC1D,wBAAgB,QAAQ,CAAC,EAAE,MAAM,EAAE,EAAE;IAAE,MAAM,EAAE,MAAM,CAAA;CAAE,GAAG,GAAG,CAAC,OAAO,CAYpE"}
@@ -0,0 +1,145 @@
1
+ import { jsx as _jsx, jsxs as _jsxs, Fragment as _Fragment } from "react/jsx-runtime";
2
+ import { Box, Text } from 'ink';
3
+ import { marked } from 'marked';
4
+ const HEADING_COLORS = ['cyan', 'green', 'yellow', 'magenta', 'blue', 'red'];
5
+ // Tiny, dependency-free token-class colorizer for common languages.
6
+ // Goal: useful visual separation, NOT correctness. Anything we don't
7
+ // recognise renders unstyled.
8
+ const KEYWORDS = {
9
+ js: /\b(const|let|var|function|return|if|else|for|while|class|new|await|async|import|export|from|as|of|in|typeof|instanceof|this|super|extends|throw|try|catch|finally|switch|case|break|continue|null|undefined|true|false)\b/g,
10
+ ts: /\b(const|let|var|function|return|if|else|for|while|class|new|await|async|import|export|from|as|of|in|typeof|instanceof|this|super|extends|throw|try|catch|finally|switch|case|break|continue|null|undefined|true|false|interface|type|enum|public|private|protected|readonly|implements|namespace)\b/g,
11
+ py: /\b(def|class|return|if|elif|else|for|while|in|not|and|or|None|True|False|import|from|as|try|except|finally|raise|with|lambda|yield|global|nonlocal|pass|break|continue|async|await)\b/g,
12
+ sh: /\b(if|then|fi|else|elif|for|while|do|done|case|esac|in|function|return|exit|break|continue|local|export|readonly|set|unset)\b/g,
13
+ bash: /\b(if|then|fi|else|elif|for|while|do|done|case|esac|in|function|return|exit|break|continue|local|export|readonly|set|unset)\b/g,
14
+ go: /\b(func|var|const|type|struct|interface|return|if|else|for|range|switch|case|default|break|continue|go|defer|chan|select|package|import|map|nil|true|false)\b/g,
15
+ };
16
+ // marked emits `language-foo` from fences; common spellings to canonical
17
+ // keys above. Without this, ```typescript ``` blocks didn't colour
18
+ // because the lookup was for `typescript` not `ts`.
19
+ const LANG_ALIASES = {
20
+ javascript: 'js', jsx: 'js', node: 'js',
21
+ typescript: 'ts', tsx: 'ts',
22
+ python: 'py', python3: 'py',
23
+ shell: 'sh', bash: 'sh', zsh: 'sh',
24
+ golang: 'go',
25
+ };
26
+ function highlightCode(code, lang) {
27
+ const lc = lang?.toLowerCase();
28
+ const canon = lc ? (LANG_ALIASES[lc] ?? lc) : undefined;
29
+ const kw = canon ? KEYWORDS[canon] : undefined;
30
+ if (!kw)
31
+ return [{ text: code }];
32
+ const spans = [];
33
+ let last = 0;
34
+ // Reset lastIndex since we use the same RegExp instance.
35
+ kw.lastIndex = 0;
36
+ let m;
37
+ // biome-ignore lint/suspicious/noAssignInExpressions: standard regex.exec loop
38
+ while ((m = kw.exec(code)) !== null) {
39
+ if (m.index > last)
40
+ spans.push({ text: code.slice(last, m.index) });
41
+ spans.push({ text: m[0], kind: 'keyword' });
42
+ last = m.index + m[0].length;
43
+ }
44
+ if (last < code.length)
45
+ spans.push({ text: code.slice(last) });
46
+ return spans;
47
+ }
48
+ function spanColor(kind) {
49
+ if (kind === 'keyword')
50
+ return 'magenta';
51
+ if (kind === 'string')
52
+ return 'green';
53
+ if (kind === 'comment')
54
+ return 'gray';
55
+ if (kind === 'number')
56
+ return 'yellow';
57
+ return undefined;
58
+ }
59
+ function renderInline(tokens, keyPrefix) {
60
+ if (!tokens)
61
+ return [];
62
+ const out = [];
63
+ tokens.forEach((tok, i) => {
64
+ const k = `${keyPrefix}-${i}`;
65
+ switch (tok.type) {
66
+ case 'text':
67
+ out.push(_jsx(Text, { children: tok.text ?? '' }, k));
68
+ break;
69
+ case 'strong':
70
+ out.push(_jsx(Text, { bold: true, children: renderInline(tok.tokens, k) }, k));
71
+ break;
72
+ case 'em':
73
+ out.push(_jsx(Text, { italic: true, children: renderInline(tok.tokens, k) }, k));
74
+ break;
75
+ case 'del':
76
+ out.push(_jsx(Text, { strikethrough: true, children: renderInline(tok.tokens, k) }, k));
77
+ break;
78
+ case 'codespan':
79
+ out.push(_jsxs(Text, { color: "cyan", children: ["`", tok.text ?? '', "`"] }, k));
80
+ break;
81
+ case 'link':
82
+ out.push(_jsxs(Text, { children: [_jsx(Text, { underline: true, children: renderInline(tok.tokens, k) }), _jsxs(Text, { dimColor: true, children: [" (", tok.href ?? '', ")"] })] }, k));
83
+ break;
84
+ case 'br':
85
+ out.push(_jsx(Text, { children: '\n' }, k));
86
+ break;
87
+ default:
88
+ out.push(_jsx(Text, { children: tok.text ?? '' }, k));
89
+ }
90
+ });
91
+ return out;
92
+ }
93
+ function renderBlock(tok, key) {
94
+ switch (tok.type) {
95
+ case 'heading': {
96
+ const depth = Math.min((tok.depth ?? 1) - 1, HEADING_COLORS.length - 1);
97
+ const prefix = '#'.repeat(tok.depth ?? 1) + ' ';
98
+ return (_jsxs(Box, { marginBottom: 1, children: [_jsx(Text, { bold: true, color: HEADING_COLORS[depth], children: prefix }), _jsx(Text, { bold: true, color: HEADING_COLORS[depth], children: renderInline(tok.tokens, key) })] }, key));
99
+ }
100
+ case 'paragraph':
101
+ return (_jsx(Box, { marginBottom: 1, children: _jsx(Text, { children: renderInline(tok.tokens, key) }) }, key));
102
+ case 'code': {
103
+ const lang = tok.lang || '';
104
+ const spans = highlightCode(tok.text ?? '', lang);
105
+ return (_jsxs(Box, { flexDirection: "column", marginBottom: 1, borderStyle: "round", borderColor: "gray", paddingX: 1, children: [lang && _jsx(Text, { dimColor: true, children: lang }), _jsx(Text, { children: spans.map((s, i) => (_jsx(Text, { color: spanColor(s.kind), children: s.text }, i))) })] }, key));
106
+ }
107
+ case 'blockquote':
108
+ return (_jsx(Box, { marginBottom: 1, flexDirection: "column", children: (tok.tokens ?? []).map((inner, i) => (_jsxs(Box, { children: [_jsx(Text, { dimColor: true, children: "\u2502 " }), _jsx(Text, { dimColor: true, children: renderInline(inner.tokens, `${key}-${i}`) })] }, i))) }, key));
109
+ case 'list': {
110
+ const ordered = !!tok.ordered;
111
+ const items = (tok.items ?? []);
112
+ return (_jsx(Box, { flexDirection: "column", marginBottom: 1, children: items.map((item, i) => {
113
+ const marker = ordered ? `${i + 1}. ` : '• ';
114
+ // list_item tokens have nested tokens; flatten to inline text.
115
+ const itemTokens = item.tokens ?? [];
116
+ return (_jsxs(Box, { children: [_jsx(Text, { dimColor: true, children: marker }), _jsx(Text, { children: renderInline(itemTokens, `${key}-${i}`) })] }, i));
117
+ }) }, key));
118
+ }
119
+ case 'hr':
120
+ return _jsx(Box, { marginBottom: 1, children: _jsx(Text, { dimColor: true, children: '─'.repeat(40) }) }, key);
121
+ case 'space':
122
+ return null;
123
+ default:
124
+ // Tables / html / footnotes / etc. — fall back to raw text so
125
+ // nothing is silently dropped.
126
+ return (_jsx(Box, { marginBottom: 1, children: _jsx(Text, { dimColor: true, children: tok.text ?? '' }) }, key));
127
+ }
128
+ }
129
+ /** Render arbitrary markdown source as Ink components. */
130
+ export function Markdown({ source }) {
131
+ // Empty body: just nothing.
132
+ if (!source)
133
+ return _jsx(Text, {});
134
+ let tokens;
135
+ try {
136
+ tokens = marked.lexer(source);
137
+ }
138
+ catch {
139
+ // Fallback: render as plain text if the lexer chokes (e.g. partial
140
+ // mid-stream content with unbalanced backticks).
141
+ return _jsx(Text, { children: source });
142
+ }
143
+ return _jsx(_Fragment, { children: tokens.map((t, i) => renderBlock(t, `b-${i}`)) });
144
+ }
145
+ //# sourceMappingURL=markdown.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"markdown.js","sourceRoot":"","sources":["../../../src/cli-ui/tui/markdown.tsx"],"names":[],"mappings":"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"}
@@ -0,0 +1,31 @@
1
+ export declare const TUI_SESSIONS_DIR: string;
2
+ export interface StoredMessage {
3
+ role: 'user' | 'assistant' | 'system';
4
+ content: string;
5
+ elapsedMs?: number;
6
+ agentName?: string;
7
+ }
8
+ export interface StoredSession {
9
+ id: string;
10
+ agent: string | undefined;
11
+ cwd: string;
12
+ createdAt: string;
13
+ updatedAt: string;
14
+ messages: StoredMessage[];
15
+ }
16
+ /** Pretty timestamp prefix + 6 hex bytes — sortable by mtime AND id. */
17
+ export declare function generateSessionId(): string;
18
+ export declare function saveSession(s: StoredSession): void;
19
+ export declare function loadSession(id: string): StoredSession | null;
20
+ export interface SessionMeta {
21
+ id: string;
22
+ agent: string | undefined;
23
+ cwd: string;
24
+ updatedAt: string;
25
+ messages: number;
26
+ bytes: number;
27
+ }
28
+ /** Latest first. Cheap: only reads filenames + stat; doesn't open JSON.
29
+ * For richer info we open per-file (used by --list-sessions full path). */
30
+ export declare function listSessions(limit?: number, full?: boolean): SessionMeta[];
31
+ //# sourceMappingURL=sessions.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sessions.d.ts","sourceRoot":"","sources":["../../../src/cli-ui/tui/sessions.ts"],"names":[],"mappings":"AAuBA,eAAO,MAAM,gBAAgB,QAAkC,CAAA;AAE/D,MAAM,WAAW,aAAa;IAC5B,IAAI,EAAE,MAAM,GAAG,WAAW,GAAG,QAAQ,CAAA;IACrC,OAAO,EAAE,MAAM,CAAA;IACf,SAAS,CAAC,EAAE,MAAM,CAAA;IAClB,SAAS,CAAC,EAAE,MAAM,CAAA;CACnB;AAED,MAAM,WAAW,aAAa;IAC5B,EAAE,EAAE,MAAM,CAAA;IACV,KAAK,EAAE,MAAM,GAAG,SAAS,CAAA;IACzB,GAAG,EAAE,MAAM,CAAA;IACX,SAAS,EAAE,MAAM,CAAA;IACjB,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,aAAa,EAAE,CAAA;CAC1B;AAED,wEAAwE;AACxE,wBAAgB,iBAAiB,IAAI,MAAM,CAM1C;AAQD,wBAAgB,WAAW,CAAC,CAAC,EAAE,aAAa,GAAG,IAAI,CAYlD;AAED,wBAAgB,WAAW,CAAC,EAAE,EAAE,MAAM,GAAG,aAAa,GAAG,IAAI,CAS5D;AAED,MAAM,WAAW,WAAW;IAC1B,EAAE,EAAE,MAAM,CAAA;IACV,KAAK,EAAE,MAAM,GAAG,SAAS,CAAA;IACzB,GAAG,EAAE,MAAM,CAAA;IACX,SAAS,EAAE,MAAM,CAAA;IACjB,QAAQ,EAAE,MAAM,CAAA;IAChB,KAAK,EAAE,MAAM,CAAA;CACd;AAED;4EAC4E;AAC5E,wBAAgB,YAAY,CAAC,KAAK,SAAK,EAAE,IAAI,UAAQ,GAAG,WAAW,EAAE,CAgCpE"}
@@ -0,0 +1,107 @@
1
+ // agim TUI session persistence — saves chat transcript so the user
2
+ // can pick up where they left off with `agim tui --resume <id>`.
3
+ //
4
+ // Storage: <AGIM_HOME>/tui-sessions/<id>.json
5
+ // File shape: { id, agent, cwd, createdAt, updatedAt, messages: [...] }
6
+ //
7
+ // We save on:
8
+ // - graceful exit (TuiApp's onExit handler)
9
+ // - end of each agent turn (so SIGKILL still preserves the last
10
+ // full exchange)
11
+ //
12
+ // Failures are warned to the logger but never propagate — losing a
13
+ // session is a quality-of-life regression, not data corruption.
14
+ import { mkdirSync, writeFileSync, readFileSync, readdirSync, statSync, existsSync } from 'node:fs';
15
+ import { join } from 'node:path';
16
+ import { randomBytes } from 'node:crypto';
17
+ import { AGIM_HOME } from '../../core/agim-paths.js';
18
+ import { logger as rootLogger } from '../../core/logger.js';
19
+ const log = rootLogger.child({ component: 'tui.sessions' });
20
+ export const TUI_SESSIONS_DIR = join(AGIM_HOME, 'tui-sessions');
21
+ /** Pretty timestamp prefix + 6 hex bytes — sortable by mtime AND id. */
22
+ export function generateSessionId() {
23
+ const d = new Date();
24
+ const pad = (n, w = 2) => String(n).padStart(w, '0');
25
+ const stamp = `${d.getFullYear()}${pad(d.getMonth() + 1)}${pad(d.getDate())}-${pad(d.getHours())}${pad(d.getMinutes())}${pad(d.getSeconds())}`;
26
+ const rnd = randomBytes(3).toString('hex');
27
+ return `tui-${stamp}-${rnd}`;
28
+ }
29
+ function ensureDir() {
30
+ try {
31
+ mkdirSync(TUI_SESSIONS_DIR, { recursive: true });
32
+ }
33
+ catch (err) {
34
+ log.warn({ event: 'tui.sessions.mkdir_failed', err: err instanceof Error ? err.message : String(err) });
35
+ }
36
+ }
37
+ export function saveSession(s) {
38
+ // Empty + system-only sessions aren't worth a file — saves clutter
39
+ // when the user just launched and exited without chatting.
40
+ const meaningful = s.messages.filter((m) => m.role !== 'system').length > 0;
41
+ if (!meaningful)
42
+ return;
43
+ ensureDir();
44
+ const file = join(TUI_SESSIONS_DIR, `${s.id}.json`);
45
+ try {
46
+ writeFileSync(file, JSON.stringify(s, null, 2), { mode: 0o600 });
47
+ }
48
+ catch (err) {
49
+ log.warn({ event: 'tui.sessions.save_failed', file, err: err instanceof Error ? err.message : String(err) });
50
+ }
51
+ }
52
+ export function loadSession(id) {
53
+ const file = join(TUI_SESSIONS_DIR, `${id}.json`);
54
+ if (!existsSync(file))
55
+ return null;
56
+ try {
57
+ return JSON.parse(readFileSync(file, 'utf-8'));
58
+ }
59
+ catch (err) {
60
+ log.warn({ event: 'tui.sessions.load_failed', file, err: err instanceof Error ? err.message : String(err) });
61
+ return null;
62
+ }
63
+ }
64
+ /** Latest first. Cheap: only reads filenames + stat; doesn't open JSON.
65
+ * For richer info we open per-file (used by --list-sessions full path). */
66
+ export function listSessions(limit = 20, full = false) {
67
+ if (!existsSync(TUI_SESSIONS_DIR))
68
+ return [];
69
+ let names = [];
70
+ try {
71
+ names = readdirSync(TUI_SESSIONS_DIR).filter((n) => n.endsWith('.json'));
72
+ }
73
+ catch (err) {
74
+ log.warn({ event: 'tui.sessions.list_failed', err: err instanceof Error ? err.message : String(err) });
75
+ return [];
76
+ }
77
+ const out = [];
78
+ for (const n of names) {
79
+ const file = join(TUI_SESSIONS_DIR, n);
80
+ let st;
81
+ try {
82
+ st = statSync(file);
83
+ }
84
+ catch {
85
+ continue;
86
+ }
87
+ const id = n.replace(/\.json$/, '');
88
+ let agent;
89
+ let cwd = '';
90
+ let updatedAt = st.mtime.toISOString();
91
+ let msgCount = 0;
92
+ if (full) {
93
+ try {
94
+ const parsed = JSON.parse(readFileSync(file, 'utf-8'));
95
+ agent = parsed.agent;
96
+ cwd = parsed.cwd;
97
+ updatedAt = parsed.updatedAt || updatedAt;
98
+ msgCount = parsed.messages.length;
99
+ }
100
+ catch { /* ignore */ }
101
+ }
102
+ out.push({ id, agent, cwd, updatedAt, messages: msgCount, bytes: st.size });
103
+ }
104
+ out.sort((a, b) => (a.updatedAt < b.updatedAt ? 1 : -1));
105
+ return out.slice(0, limit);
106
+ }
107
+ //# sourceMappingURL=sessions.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"sessions.js","sourceRoot":"","sources":["../../../src/cli-ui/tui/sessions.ts"],"names":[],"mappings":"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"}
package/dist/cli.js CHANGED
@@ -1809,6 +1809,18 @@ program
1809
1809
  await saveConfig(config);
1810
1810
  console.log(`\n✅ Configuration saved to ${CONFIG_FILE}`);
1811
1811
  });
1812
+ program
1813
+ .command('tui')
1814
+ .description('Open the terminal chat UI (Ink-based). Pick an agent + chat in-process.')
1815
+ .option('-a, --agent <name>', 'Pre-select an agent by name (e.g. claude-code, codex, native)')
1816
+ .option('-r, --resume [id]', 'Resume a saved session by id; "last" or empty picks the most recent')
1817
+ .option('--list-sessions', 'Print saved TUI sessions (latest first) and exit')
1818
+ .action(async (opts) => {
1819
+ const { runTui } = await import('./cli-ui/tui/index.js');
1820
+ // commander gives `--resume` (no arg) as `true`; normalise to empty string
1821
+ const resume = opts.resume === true ? '' : opts.resume;
1822
+ await runTui({ agent: opts.agent, resume, listSessions: opts.listSessions });
1823
+ });
1812
1824
  program
1813
1825
  .command('agents')
1814
1826
  .description('List available agents')