botmux 2.107.0 → 2.108.0

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 (515) hide show
  1. package/README.en.md +17 -14
  2. package/README.md +19 -14
  3. package/dist/adapters/backend/sandbox.d.ts +3 -1
  4. package/dist/adapters/backend/sandbox.d.ts.map +1 -1
  5. package/dist/adapters/backend/sandbox.js +19 -3
  6. package/dist/adapters/backend/sandbox.js.map +1 -1
  7. package/dist/adapters/backend/tmux-backend.d.ts.map +1 -1
  8. package/dist/adapters/backend/tmux-backend.js +16 -1
  9. package/dist/adapters/backend/tmux-backend.js.map +1 -1
  10. package/dist/adapters/backend/tmux-pipe-backend.d.ts +24 -15
  11. package/dist/adapters/backend/tmux-pipe-backend.d.ts.map +1 -1
  12. package/dist/adapters/backend/tmux-pipe-backend.js +75 -43
  13. package/dist/adapters/backend/tmux-pipe-backend.js.map +1 -1
  14. package/dist/adapters/cli/genius.d.ts.map +1 -1
  15. package/dist/adapters/cli/genius.js +9 -15
  16. package/dist/adapters/cli/genius.js.map +1 -1
  17. package/dist/adapters/cli/grok.d.ts +73 -0
  18. package/dist/adapters/cli/grok.d.ts.map +1 -0
  19. package/dist/adapters/cli/grok.js +298 -0
  20. package/dist/adapters/cli/grok.js.map +1 -0
  21. package/dist/adapters/cli/oh-my-pi.d.ts.map +1 -1
  22. package/dist/adapters/cli/oh-my-pi.js +133 -12
  23. package/dist/adapters/cli/oh-my-pi.js.map +1 -1
  24. package/dist/adapters/cli/registry.d.ts +2 -1
  25. package/dist/adapters/cli/registry.d.ts.map +1 -1
  26. package/dist/adapters/cli/registry.js +3 -1
  27. package/dist/adapters/cli/registry.js.map +1 -1
  28. package/dist/adapters/cli/shared-hints.d.ts +8 -4
  29. package/dist/adapters/cli/shared-hints.d.ts.map +1 -1
  30. package/dist/adapters/cli/shared-hints.js +8 -4
  31. package/dist/adapters/cli/shared-hints.js.map +1 -1
  32. package/dist/adapters/cli/types.d.ts +18 -16
  33. package/dist/adapters/cli/types.d.ts.map +1 -1
  34. package/dist/adapters/hook-installer.d.ts +5 -4
  35. package/dist/adapters/hook-installer.d.ts.map +1 -1
  36. package/dist/adapters/hook-installer.js +42 -0
  37. package/dist/adapters/hook-installer.js.map +1 -1
  38. package/dist/cli/send-dispatch.d.ts +21 -0
  39. package/dist/cli/send-dispatch.d.ts.map +1 -1
  40. package/dist/cli/send-dispatch.js +159 -0
  41. package/dist/cli/send-dispatch.js.map +1 -1
  42. package/dist/cli/session-list-liveness.d.ts +22 -0
  43. package/dist/cli/session-list-liveness.d.ts.map +1 -0
  44. package/dist/cli/session-list-liveness.js +22 -0
  45. package/dist/cli/session-list-liveness.js.map +1 -0
  46. package/dist/cli.d.ts.map +1 -1
  47. package/dist/cli.js +182 -33
  48. package/dist/cli.js.map +1 -1
  49. package/dist/core/ask-types.d.ts +4 -0
  50. package/dist/core/ask-types.d.ts.map +1 -1
  51. package/dist/core/ask-types.js +10 -0
  52. package/dist/core/ask-types.js.map +1 -1
  53. package/dist/core/cost-calculator.d.ts.map +1 -1
  54. package/dist/core/cost-calculator.js +35 -13
  55. package/dist/core/cost-calculator.js.map +1 -1
  56. package/dist/core/dashboard-ipc-server.d.ts.map +1 -1
  57. package/dist/core/dashboard-ipc-server.js +89 -16
  58. package/dist/core/dashboard-ipc-server.js.map +1 -1
  59. package/dist/core/dashboard-rows.d.ts.map +1 -1
  60. package/dist/core/dashboard-rows.js +6 -2
  61. package/dist/core/dashboard-rows.js.map +1 -1
  62. package/dist/core/dashboard-url.d.ts +6 -5
  63. package/dist/core/dashboard-url.d.ts.map +1 -1
  64. package/dist/core/dashboard-url.js +11 -8
  65. package/dist/core/dashboard-url.js.map +1 -1
  66. package/dist/core/maintenance.d.ts +11 -8
  67. package/dist/core/maintenance.d.ts.map +1 -1
  68. package/dist/core/maintenance.js +45 -20
  69. package/dist/core/maintenance.js.map +1 -1
  70. package/dist/core/per-bot-env.d.ts.map +1 -1
  71. package/dist/core/per-bot-env.js +4 -0
  72. package/dist/core/per-bot-env.js.map +1 -1
  73. package/dist/core/session-discovery.d.ts.map +1 -1
  74. package/dist/core/session-discovery.js +4 -0
  75. package/dist/core/session-discovery.js.map +1 -1
  76. package/dist/core/skills/cli-admin-command.d.ts.map +1 -1
  77. package/dist/core/skills/cli-admin-command.js +8 -2
  78. package/dist/core/skills/cli-admin-command.js.map +1 -1
  79. package/dist/core/skills/im-command.d.ts.map +1 -1
  80. package/dist/core/skills/im-command.js +3 -1
  81. package/dist/core/skills/im-command.js.map +1 -1
  82. package/dist/core/skills/sources.d.ts +33 -1
  83. package/dist/core/skills/sources.d.ts.map +1 -1
  84. package/dist/core/skills/sources.js +97 -0
  85. package/dist/core/skills/sources.js.map +1 -1
  86. package/dist/core/skills/types.d.ts +8 -0
  87. package/dist/core/skills/types.d.ts.map +1 -1
  88. package/dist/core/terminal-url.d.ts.map +1 -1
  89. package/dist/core/terminal-url.js +12 -2
  90. package/dist/core/terminal-url.js.map +1 -1
  91. package/dist/core/terminal-write-auth.d.ts +34 -0
  92. package/dist/core/terminal-write-auth.d.ts.map +1 -0
  93. package/dist/core/terminal-write-auth.js +76 -0
  94. package/dist/core/terminal-write-auth.js.map +1 -0
  95. package/dist/core/tmux-recovery.d.ts +11 -0
  96. package/dist/core/tmux-recovery.d.ts.map +1 -0
  97. package/dist/core/tmux-recovery.js +19 -0
  98. package/dist/core/tmux-recovery.js.map +1 -0
  99. package/dist/core/types.d.ts +10 -4
  100. package/dist/core/types.d.ts.map +1 -1
  101. package/dist/core/types.js.map +1 -1
  102. package/dist/core/update-check.d.ts +2 -2
  103. package/dist/core/update-check.js +2 -2
  104. package/dist/core/worker-pool.d.ts +3 -0
  105. package/dist/core/worker-pool.d.ts.map +1 -1
  106. package/dist/core/worker-pool.js +70 -3
  107. package/dist/core/worker-pool.js.map +1 -1
  108. package/dist/daemon.d.ts.map +1 -1
  109. package/dist/daemon.js +15 -8
  110. package/dist/daemon.js.map +1 -1
  111. package/dist/dashboard/auth.d.ts +1 -1
  112. package/dist/dashboard/auth.d.ts.map +1 -1
  113. package/dist/dashboard/auth.js +7 -2
  114. package/dist/dashboard/auth.js.map +1 -1
  115. package/dist/dashboard/bot-payload.d.ts +3 -0
  116. package/dist/dashboard/bot-payload.d.ts.map +1 -1
  117. package/dist/dashboard/bot-payload.js +3 -0
  118. package/dist/dashboard/bot-payload.js.map +1 -1
  119. package/dist/dashboard/connector-api.d.ts.map +1 -1
  120. package/dist/dashboard/connector-api.js +39 -13
  121. package/dist/dashboard/connector-api.js.map +1 -1
  122. package/dist/dashboard/history-senders.d.ts +37 -0
  123. package/dist/dashboard/history-senders.d.ts.map +1 -0
  124. package/dist/dashboard/history-senders.js +60 -0
  125. package/dist/dashboard/history-senders.js.map +1 -0
  126. package/dist/dashboard/roles-batch.d.ts +31 -0
  127. package/dist/dashboard/roles-batch.d.ts.map +1 -0
  128. package/dist/dashboard/roles-batch.js +87 -0
  129. package/dist/dashboard/roles-batch.js.map +1 -0
  130. package/dist/dashboard/settings-card-model.d.ts +4 -2
  131. package/dist/dashboard/settings-card-model.d.ts.map +1 -1
  132. package/dist/dashboard/settings-card-model.js +13 -5
  133. package/dist/dashboard/settings-card-model.js.map +1 -1
  134. package/dist/dashboard/settings-write-applier.d.ts +4 -1
  135. package/dist/dashboard/settings-write-applier.d.ts.map +1 -1
  136. package/dist/dashboard/settings-write-applier.js +6 -1
  137. package/dist/dashboard/settings-write-applier.js.map +1 -1
  138. package/dist/dashboard/skill-install-request.d.ts +4 -0
  139. package/dist/dashboard/skill-install-request.d.ts.map +1 -1
  140. package/dist/dashboard/skill-install-request.js +11 -1
  141. package/dist/dashboard/skill-install-request.js.map +1 -1
  142. package/dist/dashboard/trigger-api.d.ts +9 -1
  143. package/dist/dashboard/trigger-api.d.ts.map +1 -1
  144. package/dist/dashboard/trigger-api.js +48 -10
  145. package/dist/dashboard/trigger-api.js.map +1 -1
  146. package/dist/dashboard/web/app.d.ts.map +1 -1
  147. package/dist/dashboard/web/app.js +286 -271
  148. package/dist/dashboard/web/app.js.map +1 -1
  149. package/dist/dashboard/web/bot-defaults-page.d.ts +26 -0
  150. package/dist/dashboard/web/bot-defaults-page.d.ts.map +1 -1
  151. package/dist/dashboard/web/bot-defaults-page.js +1408 -12
  152. package/dist/dashboard/web/bot-defaults-page.js.map +1 -1
  153. package/dist/dashboard/web/bot-defaults.d.ts +91 -4
  154. package/dist/dashboard/web/bot-defaults.d.ts.map +1 -1
  155. package/dist/dashboard/web/bot-defaults.js +43 -2141
  156. package/dist/dashboard/web/bot-defaults.js.map +1 -1
  157. package/dist/dashboard/web/bot-onboarding.d.ts +6 -1
  158. package/dist/dashboard/web/bot-onboarding.d.ts.map +1 -1
  159. package/dist/dashboard/web/bot-onboarding.js +261 -306
  160. package/dist/dashboard/web/bot-onboarding.js.map +1 -1
  161. package/dist/dashboard/web/connectors-page.d.ts +4 -0
  162. package/dist/dashboard/web/connectors-page.d.ts.map +1 -1
  163. package/dist/dashboard/web/connectors-page.js +228 -48
  164. package/dist/dashboard/web/connectors-page.js.map +1 -1
  165. package/dist/dashboard/web/dashboard-api.d.ts +9 -0
  166. package/dist/dashboard/web/dashboard-api.d.ts.map +1 -0
  167. package/dist/dashboard/web/dashboard-api.js +18 -0
  168. package/dist/dashboard/web/dashboard-api.js.map +1 -0
  169. package/dist/dashboard/web/dashboard-components.d.ts +92 -0
  170. package/dist/dashboard/web/dashboard-components.d.ts.map +1 -0
  171. package/dist/dashboard/web/dashboard-components.js +250 -0
  172. package/dist/dashboard/web/dashboard-components.js.map +1 -0
  173. package/dist/dashboard/web/dashboard-routes.d.ts.map +1 -1
  174. package/dist/dashboard/web/dashboard-routes.js +30 -183
  175. package/dist/dashboard/web/dashboard-routes.js.map +1 -1
  176. package/dist/dashboard/web/floating-scrollbars.d.ts +2 -0
  177. package/dist/dashboard/web/floating-scrollbars.d.ts.map +1 -0
  178. package/dist/dashboard/web/floating-scrollbars.js +264 -0
  179. package/dist/dashboard/web/floating-scrollbars.js.map +1 -0
  180. package/dist/dashboard/web/groups-api.d.ts +36 -0
  181. package/dist/dashboard/web/groups-api.d.ts.map +1 -0
  182. package/dist/dashboard/web/groups-api.js +44 -0
  183. package/dist/dashboard/web/groups-api.js.map +1 -0
  184. package/dist/dashboard/web/groups-page.d.ts.map +1 -1
  185. package/dist/dashboard/web/groups-page.js +746 -15
  186. package/dist/dashboard/web/groups-page.js.map +1 -1
  187. package/dist/dashboard/web/groups.d.ts +51 -18
  188. package/dist/dashboard/web/groups.d.ts.map +1 -1
  189. package/dist/dashboard/web/groups.js +145 -1096
  190. package/dist/dashboard/web/groups.js.map +1 -1
  191. package/dist/dashboard/web/i18n.d.ts.map +1 -1
  192. package/dist/dashboard/web/i18n.js +545 -255
  193. package/dist/dashboard/web/i18n.js.map +1 -1
  194. package/dist/dashboard/web/insights-page.d.ts.map +1 -1
  195. package/dist/dashboard/web/insights-page.js +1047 -14
  196. package/dist/dashboard/web/insights-page.js.map +1 -1
  197. package/dist/dashboard/web/insights.d.ts +177 -7
  198. package/dist/dashboard/web/insights.d.ts.map +1 -1
  199. package/dist/dashboard/web/insights.js +187 -1926
  200. package/dist/dashboard/web/insights.js.map +1 -1
  201. package/dist/dashboard/web/legacy-workflow-page.d.ts +3 -0
  202. package/dist/dashboard/web/legacy-workflow-page.d.ts.map +1 -0
  203. package/dist/dashboard/web/legacy-workflow-page.js +717 -0
  204. package/dist/dashboard/web/legacy-workflow-page.js.map +1 -0
  205. package/dist/dashboard/web/monitor-room.d.ts.map +1 -1
  206. package/dist/dashboard/web/monitor-room.js +10 -8
  207. package/dist/dashboard/web/monitor-room.js.map +1 -1
  208. package/dist/dashboard/web/monitoring-page.d.ts.map +1 -1
  209. package/dist/dashboard/web/monitoring-page.js +188 -14
  210. package/dist/dashboard/web/monitoring-page.js.map +1 -1
  211. package/dist/dashboard/web/office-page.d.ts.map +1 -1
  212. package/dist/dashboard/web/office-page.js +11 -23
  213. package/dist/dashboard/web/office-page.js.map +1 -1
  214. package/dist/dashboard/web/overview-page.d.ts.map +1 -1
  215. package/dist/dashboard/web/overview-page.js +141 -147
  216. package/dist/dashboard/web/overview-page.js.map +1 -1
  217. package/dist/dashboard/web/overview.d.ts +0 -1
  218. package/dist/dashboard/web/overview.d.ts.map +1 -1
  219. package/dist/dashboard/web/overview.js +3 -275
  220. package/dist/dashboard/web/overview.js.map +1 -1
  221. package/dist/dashboard/web/preferences.d.ts +1 -6
  222. package/dist/dashboard/web/preferences.d.ts.map +1 -1
  223. package/dist/dashboard/web/preferences.js +0 -21
  224. package/dist/dashboard/web/preferences.js.map +1 -1
  225. package/dist/dashboard/web/role-batch.d.ts +9 -0
  226. package/dist/dashboard/web/role-batch.d.ts.map +1 -0
  227. package/dist/dashboard/web/role-batch.js +42 -0
  228. package/dist/dashboard/web/role-batch.js.map +1 -0
  229. package/dist/dashboard/web/roles-page.d.ts.map +1 -1
  230. package/dist/dashboard/web/roles-page.js +538 -13
  231. package/dist/dashboard/web/roles-page.js.map +1 -1
  232. package/dist/dashboard/web/roles.d.ts +98 -1
  233. package/dist/dashboard/web/roles.d.ts.map +1 -1
  234. package/dist/dashboard/web/roles.js +117 -903
  235. package/dist/dashboard/web/roles.js.map +1 -1
  236. package/dist/dashboard/web/schedules-page.d.ts.map +1 -1
  237. package/dist/dashboard/web/schedules-page.js +82 -24
  238. package/dist/dashboard/web/schedules-page.js.map +1 -1
  239. package/dist/dashboard/web/sessions-kanban.d.ts +67 -0
  240. package/dist/dashboard/web/sessions-kanban.d.ts.map +1 -0
  241. package/dist/dashboard/web/sessions-kanban.js +481 -0
  242. package/dist/dashboard/web/sessions-kanban.js.map +1 -0
  243. package/dist/dashboard/web/sessions-page.d.ts +4 -0
  244. package/dist/dashboard/web/sessions-page.d.ts.map +1 -1
  245. package/dist/dashboard/web/sessions-page.js +1633 -18
  246. package/dist/dashboard/web/sessions-page.js.map +1 -1
  247. package/dist/dashboard/web/sessions.d.ts +45 -4
  248. package/dist/dashboard/web/sessions.d.ts.map +1 -1
  249. package/dist/dashboard/web/sessions.js +53 -2535
  250. package/dist/dashboard/web/sessions.js.map +1 -1
  251. package/dist/dashboard/web/settings-page.d.ts +0 -2
  252. package/dist/dashboard/web/settings-page.d.ts.map +1 -1
  253. package/dist/dashboard/web/settings-page.js +127 -117
  254. package/dist/dashboard/web/settings-page.js.map +1 -1
  255. package/dist/dashboard/web/skills-page.d.ts +10 -1
  256. package/dist/dashboard/web/skills-page.d.ts.map +1 -1
  257. package/dist/dashboard/web/skills-page.js +235 -93
  258. package/dist/dashboard/web/skills-page.js.map +1 -1
  259. package/dist/dashboard/web/team-federation-page.d.ts.map +1 -1
  260. package/dist/dashboard/web/team-federation-page.js +446 -28
  261. package/dist/dashboard/web/team-federation-page.js.map +1 -1
  262. package/dist/dashboard/web/team-federation.d.ts +91 -2
  263. package/dist/dashboard/web/team-federation.d.ts.map +1 -1
  264. package/dist/dashboard/web/team-federation.js +87 -474
  265. package/dist/dashboard/web/team-federation.js.map +1 -1
  266. package/dist/dashboard/web/theme-menu.d.ts +1 -0
  267. package/dist/dashboard/web/theme-menu.d.ts.map +1 -1
  268. package/dist/dashboard/web/theme-menu.js +79 -20
  269. package/dist/dashboard/web/theme-menu.js.map +1 -1
  270. package/dist/dashboard/web/ui.d.ts +1 -2
  271. package/dist/dashboard/web/ui.d.ts.map +1 -1
  272. package/dist/dashboard/web/ui.js +8 -20
  273. package/dist/dashboard/web/ui.js.map +1 -1
  274. package/dist/dashboard/web/v3-api.d.ts +16 -0
  275. package/dist/dashboard/web/v3-api.d.ts.map +1 -0
  276. package/dist/dashboard/web/v3-api.js +21 -0
  277. package/dist/dashboard/web/v3-api.js.map +1 -0
  278. package/dist/dashboard/web/v3-components.d.ts +2 -0
  279. package/dist/dashboard/web/v3-components.d.ts.map +1 -0
  280. package/dist/dashboard/web/v3-components.js +290 -0
  281. package/dist/dashboard/web/v3-components.js.map +1 -0
  282. package/dist/dashboard/web/v3-model.d.ts +80 -0
  283. package/dist/dashboard/web/v3-model.d.ts.map +1 -0
  284. package/dist/dashboard/web/v3-model.js +240 -0
  285. package/dist/dashboard/web/v3-model.js.map +1 -0
  286. package/dist/dashboard/web/v3-page.d.ts.map +1 -1
  287. package/dist/dashboard/web/v3-page.js +2 -22
  288. package/dist/dashboard/web/v3-page.js.map +1 -1
  289. package/dist/dashboard/web/v3-terminal.d.ts +14 -0
  290. package/dist/dashboard/web/v3-terminal.d.ts.map +1 -1
  291. package/dist/dashboard/web/v3-terminal.js +31 -19
  292. package/dist/dashboard/web/v3-terminal.js.map +1 -1
  293. package/dist/dashboard/web/webhook-logs-page.d.ts +16 -0
  294. package/dist/dashboard/web/webhook-logs-page.d.ts.map +1 -0
  295. package/dist/dashboard/web/webhook-logs-page.js +195 -0
  296. package/dist/dashboard/web/webhook-logs-page.js.map +1 -0
  297. package/dist/dashboard/web/whiteboards-page.d.ts.map +1 -1
  298. package/dist/dashboard/web/whiteboards-page.js +18 -23
  299. package/dist/dashboard/web/whiteboards-page.js.map +1 -1
  300. package/dist/dashboard/web/workflow-version-switch.d.ts +8 -0
  301. package/dist/dashboard/web/workflow-version-switch.d.ts.map +1 -0
  302. package/dist/dashboard/web/workflow-version-switch.js +9 -0
  303. package/dist/dashboard/web/workflow-version-switch.js.map +1 -0
  304. package/dist/dashboard/web/workflows.d.ts +272 -1
  305. package/dist/dashboard/web/workflows.d.ts.map +1 -1
  306. package/dist/dashboard/web/workflows.js +211 -1397
  307. package/dist/dashboard/web/workflows.js.map +1 -1
  308. package/dist/dashboard/webhook-routes.d.ts.map +1 -1
  309. package/dist/dashboard/webhook-routes.js +92 -39
  310. package/dist/dashboard/webhook-routes.js.map +1 -1
  311. package/dist/dashboard-web/app.js +1 -65
  312. package/dist/dashboard-web/brand-logo.png +0 -0
  313. package/dist/dashboard-web/chunks/bot-defaults-page-HSQ6HR3R.js +1 -0
  314. package/dist/dashboard-web/chunks/chunk-6TPODDDC.js +1 -0
  315. package/dist/dashboard-web/chunks/chunk-73EJP2MO.js +1 -0
  316. package/dist/dashboard-web/chunks/chunk-BRTZFELS.js +1 -0
  317. package/dist/dashboard-web/chunks/chunk-EVK77ASG.js +1 -0
  318. package/dist/dashboard-web/chunks/chunk-R3FXBFQH.js +1 -0
  319. package/dist/dashboard-web/chunks/chunk-VRLL7SNU.js +1 -0
  320. package/dist/dashboard-web/chunks/chunk-XCPSHD3G.js +37 -0
  321. package/dist/dashboard-web/chunks/chunk-XJ7BGPJH.js +1 -0
  322. package/dist/dashboard-web/chunks/chunk-YVRWYGXR.js +1 -0
  323. package/dist/dashboard-web/chunks/chunk-ZJING6FY.js +66 -0
  324. package/dist/dashboard-web/chunks/connectors-page-ODUA5UCW.js +1 -0
  325. package/dist/dashboard-web/chunks/groups-page-OYX5M6NK.js +8 -0
  326. package/dist/dashboard-web/chunks/insights-page-YCQO6OCR.js +22 -0
  327. package/dist/dashboard-web/chunks/legacy-workflow-page-XJAUNONP.js +2 -0
  328. package/dist/dashboard-web/chunks/{monitor-room-RFX4HPS5.js → monitor-room-WTZNYAFV.js} +17 -15
  329. package/dist/dashboard-web/chunks/monitoring-page-R6LJUK7G.js +2 -0
  330. package/dist/dashboard-web/chunks/office-page-4OXK3GNR.js +1 -0
  331. package/dist/dashboard-web/chunks/overview-page-4MVEJY6U.js +1 -0
  332. package/dist/dashboard-web/chunks/roles-page-NQDW27VV.js +1 -0
  333. package/dist/dashboard-web/chunks/schedules-page-JRNKYHOX.js +1 -0
  334. package/dist/dashboard-web/chunks/sessions-page-LF7UVI7B.js +3 -0
  335. package/dist/dashboard-web/chunks/settings-page-WGW7KQQS.js +2 -0
  336. package/dist/dashboard-web/chunks/skills-page-AMD4XP3T.js +3 -0
  337. package/dist/dashboard-web/chunks/team-federation-page-SYG3K4GG.js +1 -0
  338. package/dist/dashboard-web/chunks/v3-page-6NFFWNUK.js +94 -0
  339. package/dist/dashboard-web/chunks/whiteboards-page-FBRUK2AS.js +1 -0
  340. package/dist/dashboard-web/favicon.png +0 -0
  341. package/dist/dashboard-web/index.html +5 -69
  342. package/dist/dashboard-web/style.css +18835 -7211
  343. package/dist/dashboard.js +150 -32
  344. package/dist/dashboard.js.map +1 -1
  345. package/dist/global-config.d.ts +2 -2
  346. package/dist/global-config.d.ts.map +1 -1
  347. package/dist/i18n/en.d.ts.map +1 -1
  348. package/dist/i18n/en.js +3 -0
  349. package/dist/i18n/en.js.map +1 -1
  350. package/dist/i18n/zh.d.ts.map +1 -1
  351. package/dist/i18n/zh.js +3 -0
  352. package/dist/i18n/zh.js.map +1 -1
  353. package/dist/im/lark/card-builder.d.ts +7 -5
  354. package/dist/im/lark/card-builder.d.ts.map +1 -1
  355. package/dist/im/lark/card-builder.js +10 -7
  356. package/dist/im/lark/card-builder.js.map +1 -1
  357. package/dist/im/lark/card-handler.d.ts.map +1 -1
  358. package/dist/im/lark/card-handler.js +25 -1
  359. package/dist/im/lark/card-handler.js.map +1 -1
  360. package/dist/im/lark/event-dispatcher.d.ts.map +1 -1
  361. package/dist/im/lark/event-dispatcher.js +84 -0
  362. package/dist/im/lark/event-dispatcher.js.map +1 -1
  363. package/dist/platform/binding.d.ts +9 -0
  364. package/dist/platform/binding.d.ts.map +1 -1
  365. package/dist/platform/binding.js +14 -0
  366. package/dist/platform/binding.js.map +1 -1
  367. package/dist/platform/tunnel-client.d.ts.map +1 -1
  368. package/dist/platform/tunnel-client.js +9 -0
  369. package/dist/platform/tunnel-client.js.map +1 -1
  370. package/dist/services/bot-config-store.d.ts +1 -1
  371. package/dist/services/bot-config-store.d.ts.map +1 -1
  372. package/dist/services/bot-config-store.js +11 -5
  373. package/dist/services/bot-config-store.js.map +1 -1
  374. package/dist/services/file-bridge-path.d.ts +8 -0
  375. package/dist/services/file-bridge-path.d.ts.map +1 -0
  376. package/dist/services/file-bridge-path.js +75 -0
  377. package/dist/services/file-bridge-path.js.map +1 -0
  378. package/dist/services/grok-paths.d.ts +27 -0
  379. package/dist/services/grok-paths.d.ts.map +1 -0
  380. package/dist/services/grok-paths.js +106 -0
  381. package/dist/services/grok-paths.js.map +1 -0
  382. package/dist/services/grok-transcript.d.ts +67 -0
  383. package/dist/services/grok-transcript.d.ts.map +1 -0
  384. package/dist/services/grok-transcript.js +630 -0
  385. package/dist/services/grok-transcript.js.map +1 -0
  386. package/dist/services/hermes-session-filter.d.ts +28 -0
  387. package/dist/services/hermes-session-filter.d.ts.map +1 -0
  388. package/dist/services/hermes-session-filter.js +53 -0
  389. package/dist/services/hermes-session-filter.js.map +1 -0
  390. package/dist/services/hermes-transcript.d.ts +3 -0
  391. package/dist/services/hermes-transcript.d.ts.map +1 -1
  392. package/dist/services/hermes-transcript.js +20 -2
  393. package/dist/services/hermes-transcript.js.map +1 -1
  394. package/dist/services/resumable-session-discovery.d.ts +3 -0
  395. package/dist/services/resumable-session-discovery.d.ts.map +1 -1
  396. package/dist/services/resumable-session-discovery.js +6 -1
  397. package/dist/services/resumable-session-discovery.js.map +1 -1
  398. package/dist/services/skill-registry-store.d.ts +9 -0
  399. package/dist/services/skill-registry-store.d.ts.map +1 -1
  400. package/dist/services/skill-registry-store.js +304 -1
  401. package/dist/services/skill-registry-store.js.map +1 -1
  402. package/dist/services/structured-bridge-clis.d.ts +29 -0
  403. package/dist/services/structured-bridge-clis.d.ts.map +1 -0
  404. package/dist/services/structured-bridge-clis.js +76 -0
  405. package/dist/services/structured-bridge-clis.js.map +1 -0
  406. package/dist/services/trigger-log-store.d.ts +59 -0
  407. package/dist/services/trigger-log-store.d.ts.map +1 -1
  408. package/dist/services/trigger-log-store.js +81 -10
  409. package/dist/services/trigger-log-store.js.map +1 -1
  410. package/dist/services/usage-ledger.d.ts +4 -1
  411. package/dist/services/usage-ledger.d.ts.map +1 -1
  412. package/dist/services/usage-ledger.js +48 -10
  413. package/dist/services/usage-ledger.js.map +1 -1
  414. package/dist/services/webhook-audit.d.ts +10 -0
  415. package/dist/services/webhook-audit.d.ts.map +1 -0
  416. package/dist/services/webhook-audit.js +116 -0
  417. package/dist/services/webhook-audit.js.map +1 -0
  418. package/dist/setup/bot-config-editor.d.ts.map +1 -1
  419. package/dist/setup/bot-config-editor.js +2 -0
  420. package/dist/setup/bot-config-editor.js.map +1 -1
  421. package/dist/setup/ensure-tmux.d.ts +26 -12
  422. package/dist/setup/ensure-tmux.d.ts.map +1 -1
  423. package/dist/setup/ensure-tmux.js +85 -18
  424. package/dist/setup/ensure-tmux.js.map +1 -1
  425. package/dist/skills/definitions.d.ts.map +1 -1
  426. package/dist/skills/definitions.js +14 -1
  427. package/dist/skills/definitions.js.map +1 -1
  428. package/dist/skills/injection-mode.d.ts +16 -0
  429. package/dist/skills/injection-mode.d.ts.map +1 -1
  430. package/dist/skills/injection-mode.js +25 -0
  431. package/dist/skills/injection-mode.js.map +1 -1
  432. package/dist/types.d.ts +9 -0
  433. package/dist/types.d.ts.map +1 -1
  434. package/dist/utils/global-install.d.ts +22 -0
  435. package/dist/utils/global-install.d.ts.map +1 -0
  436. package/dist/utils/global-install.js +106 -0
  437. package/dist/utils/global-install.js.map +1 -0
  438. package/dist/utils/install-diagnostics.d.ts +1 -1
  439. package/dist/utils/install-diagnostics.d.ts.map +1 -1
  440. package/dist/utils/install-diagnostics.js +6 -4
  441. package/dist/utils/install-diagnostics.js.map +1 -1
  442. package/dist/utils/install-info.d.ts +2 -0
  443. package/dist/utils/install-info.d.ts.map +1 -1
  444. package/dist/utils/install-info.js +10 -4
  445. package/dist/utils/install-info.js.map +1 -1
  446. package/dist/worker.js +293 -172
  447. package/dist/worker.js.map +1 -1
  448. package/dist/workflows/events/payloads.d.ts +10 -10
  449. package/dist/workflows/events/schema.d.ts +28 -28
  450. package/package.json +8 -7
  451. package/dist/dashboard/web/connectors.d.ts +0 -2
  452. package/dist/dashboard/web/connectors.d.ts.map +0 -1
  453. package/dist/dashboard/web/connectors.js +0 -2
  454. package/dist/dashboard/web/connectors.js.map +0 -1
  455. package/dist/dashboard/web/office.d.ts +0 -2
  456. package/dist/dashboard/web/office.d.ts.map +0 -1
  457. package/dist/dashboard/web/office.js +0 -2
  458. package/dist/dashboard/web/office.js.map +0 -1
  459. package/dist/dashboard/web/schedules.d.ts +0 -2
  460. package/dist/dashboard/web/schedules.d.ts.map +0 -1
  461. package/dist/dashboard/web/schedules.js +0 -2
  462. package/dist/dashboard/web/schedules.js.map +0 -1
  463. package/dist/dashboard/web/settings.d.ts +0 -2
  464. package/dist/dashboard/web/settings.d.ts.map +0 -1
  465. package/dist/dashboard/web/settings.js +0 -2
  466. package/dist/dashboard/web/settings.js.map +0 -1
  467. package/dist/dashboard/web/skills.d.ts +0 -2
  468. package/dist/dashboard/web/skills.d.ts.map +0 -1
  469. package/dist/dashboard/web/skills.js +0 -2
  470. package/dist/dashboard/web/skills.js.map +0 -1
  471. package/dist/dashboard/web/skin-intro.d.ts +0 -4
  472. package/dist/dashboard/web/skin-intro.d.ts.map +0 -1
  473. package/dist/dashboard/web/skin-intro.js +0 -49
  474. package/dist/dashboard/web/skin-intro.js.map +0 -1
  475. package/dist/dashboard/web/v3.d.ts +0 -3
  476. package/dist/dashboard/web/v3.d.ts.map +0 -1
  477. package/dist/dashboard/web/v3.js +0 -539
  478. package/dist/dashboard/web/v3.js.map +0 -1
  479. package/dist/dashboard/web/whiteboards.d.ts +0 -2
  480. package/dist/dashboard/web/whiteboards.d.ts.map +0 -1
  481. package/dist/dashboard/web/whiteboards.js +0 -2
  482. package/dist/dashboard/web/whiteboards.js.map +0 -1
  483. package/dist/dashboard-web/chunks/bot-defaults-page-OCIHPGEU.js +0 -438
  484. package/dist/dashboard-web/chunks/chunk-3N2PPQVD.js +0 -1
  485. package/dist/dashboard-web/chunks/chunk-3UJYRR2Q.js +0 -37
  486. package/dist/dashboard-web/chunks/chunk-5E3MJJL4.js +0 -1
  487. package/dist/dashboard-web/chunks/chunk-7SZRL6FY.js +0 -1
  488. package/dist/dashboard-web/chunks/chunk-JTSE5VP6.js +0 -54
  489. package/dist/dashboard-web/chunks/chunk-LXIK7OUJ.js +0 -1
  490. package/dist/dashboard-web/chunks/chunk-PE6W3C2C.js +0 -1
  491. package/dist/dashboard-web/chunks/chunk-QW54DWU3.js +0 -325
  492. package/dist/dashboard-web/chunks/connectors-IGETYWCP.js +0 -1
  493. package/dist/dashboard-web/chunks/groups-page-MYBS4ZYJ.js +0 -207
  494. package/dist/dashboard-web/chunks/insights-page-UPA32V2S.js +0 -309
  495. package/dist/dashboard-web/chunks/monitoring-page-7T3BESZ2.js +0 -1
  496. package/dist/dashboard-web/chunks/office-page-6DXYOG55.js +0 -1
  497. package/dist/dashboard-web/chunks/overview-page-LJSBCQW4.js +0 -1
  498. package/dist/dashboard-web/chunks/roles-page-ESURTVQH.js +0 -98
  499. package/dist/dashboard-web/chunks/schedules-LML2ISOT.js +0 -1
  500. package/dist/dashboard-web/chunks/sessions-YB73XOTU.js +0 -1
  501. package/dist/dashboard-web/chunks/sessions-page-MCO5QR7Z.js +0 -1
  502. package/dist/dashboard-web/chunks/settings-page-OSDKNVS3.js +0 -2
  503. package/dist/dashboard-web/chunks/skills-page-PXBZJ6P6.js +0 -2
  504. package/dist/dashboard-web/chunks/team-federation-page-TTPVHFPX.js +0 -10
  505. package/dist/dashboard-web/chunks/v3-page-FVPUL665.js +0 -149
  506. package/dist/dashboard-web/chunks/whiteboards-page-HLCTYSSV.js +0 -1
  507. package/dist/dashboard-web/chunks/workflows-FCPM4S4D.js +0 -184
  508. package/dist/dashboard-web/skins/bluearchive-hero.webp +0 -0
  509. package/dist/dashboard-web/skins/dragonball-goku.webp +0 -0
  510. package/dist/dashboard-web/skins/dragonball-wukong.webp +0 -0
  511. package/dist/dashboard-web/skins/genshin-breeze.webp +0 -0
  512. package/dist/dashboard-web/skins/ikun-hero.webp +0 -0
  513. package/dist/dashboard-web/skins/prts-priestess.webp +0 -0
  514. package/dist/dashboard-web/skins/zzz-hero.webp +0 -0
  515. package/dist/dashboard-web/skins/zzz-pattern.svg +0 -25
@@ -6,18 +6,21 @@ const zh = {
6
6
  'time.secondsAgo': '{value} 秒前',
7
7
  'time.minutesAgo': '{value} 分钟前',
8
8
  'time.hoursAgo': '{value} 小时前',
9
- 'nav.overview': '总览',
10
- 'nav.monitoring': '监控',
11
- 'nav.sessions': '会话',
12
- 'nav.sidebarCollapse': '收起菜单栏',
13
- 'nav.sidebarExpand': '展开菜单栏',
14
- 'nav.groups': '群组',
15
- 'nav.schedules': '定时',
16
- 'nav.settings': '设置',
9
+ 'nav.overview': '工作台',
10
+ 'nav.monitoring': '监控看板',
11
+ 'nav.sessions': '会话控制',
12
+ 'nav.groups': '群组管理',
13
+ 'nav.schedules': '定时任务',
14
+ 'nav.settings': '全局设置',
17
15
  'nav.botDefaults': 'Bot 配置',
18
- 'nav.skills': 'Skills',
19
- 'status.live': '实时连接',
20
- 'status.disconnected': '连接断开',
16
+ 'nav.skills': 'Skill 管理',
17
+ 'nav.whiteboards': '白板',
18
+ 'nav.team': '团队协作',
19
+ 'nav.connectors': 'Webhook',
20
+ 'nav.webhookLogs': '调用日志',
21
+ 'nav.office': '办公室',
22
+ 'status.live': '实时链接',
23
+ 'status.disconnected': '链接断开',
21
24
  'status.system': '系统',
22
25
  'status.light': '浅色',
23
26
  'status.dark': '暗黑',
@@ -26,13 +29,7 @@ const zh = {
26
29
  'theme.base': '基础',
27
30
  'theme.skins': '主题皮肤',
28
31
  'skin.cyber': '2077',
29
- 'skin.genshin': '原神',
30
32
  'skin.fallout': 'Fallout',
31
- 'skin.prts': 'PRTS',
32
- 'skin.bluearchive': '蔚蓝档案',
33
- 'skin.zzz': '绝区零',
34
- 'skin.dragonball': '七龙珠',
35
- 'skin.ikun': 'ikun',
36
33
  'botOnboarding.add': '添加机器人',
37
34
  'botOnboarding.title': '添加机器人',
38
35
  'botOnboarding.intro': '选择 CLI 与工作目录,扫码创建 PersonalAgent 应用后写入本机 bots.json,并自动配置开放平台权限。',
@@ -76,16 +73,16 @@ const zh = {
76
73
  'botOnboarding.ownerInvalid': 'owner 校验失败,请检查后重试。',
77
74
  'botOnboarding.qrAlt': '飞书扫码添加机器人二维码',
78
75
  'overview.title': '工作台',
79
- 'overview.subtitle': '数字员工实时状态 · 同步飞书话题',
80
76
  'overview.team': 'AI 团队',
81
77
  'overview.teamHint': '每位数字员工的实时状态',
82
78
  'overview.attention': '需要你处理',
83
- 'overview.attentionHint': '卡住的任务,回个话就能继续跑',
84
79
  'overview.activeSessions': '活跃会话',
85
- 'overview.activeSessionsHint': '正在运转的会话',
86
- 'overview.today': '此刻概览',
87
- 'overview.todayHint': '活跃会话分布',
80
+ 'overview.sessionOverview': '会话概览',
88
81
  'overview.viewAll': '查看全部 →',
82
+ 'overview.viewAllPlain': '查看全部',
83
+ 'overview.sort': '排序',
84
+ 'overview.sortByTime': '按时间',
85
+ 'overview.sortAttentionFirst': '需要你处理优先',
89
86
  'overview.botIdle': '待命中,随时可接新任务',
90
87
  'overview.botOffline': '离线 — daemon 未上线',
91
88
  'overview.botBusy': '执行中 · {count} 会话',
@@ -94,14 +91,15 @@ const zh = {
94
91
  'overview.botOff': '离线',
95
92
  'overview.sessionsCount': '{count} 会话',
96
93
  'overview.lastActive': '{time}前活跃',
97
- 'overview.noAttention': '没有等你处理的事项',
98
- 'overview.teamExpand': '展开全部 {count} 位 ▾',
99
- 'overview.teamCollapse': '收起',
94
+ 'overview.teamCount': '{count} 位',
95
+ 'overview.teamExpand': '展开全部',
96
+ 'overview.teamCollapse': '收起',
100
97
  'strip.pending': '{count} 件待处理',
101
- 'strip.longest': '最久已等 {time} {bot} {reason}',
98
+ 'strip.longestCompact': '最久 {time} · {bot} · {reason}',
102
99
  'strip.handle': '立即处理',
103
100
  'overview.openSessions': '活跃会话',
104
101
  'overview.workingSessions': '工作中',
102
+ 'overview.idleSessions': '空闲中',
105
103
  'overview.onlineBots': '在线 Bot',
106
104
  'overview.schedules': '定时任务',
107
105
  'overview.groups': '群聊覆盖',
@@ -111,13 +109,13 @@ const zh = {
111
109
  'overview.daemonRegistry': 'daemon 注册表',
112
110
  'overview.chatMatrix': '群聊矩阵',
113
111
  'overview.recentSessions': '最近会话',
114
- 'overview.nextSchedules': '即将执行',
112
+ 'overview.nextSchedules': '定时任务',
115
113
  'overview.noSessions': '暂无会话。',
116
114
  'overview.noSchedules': '暂无定时任务。',
117
115
  'monitoring.eyebrow': '运行资源',
118
- 'monitoring.title': '资源监控',
116
+ 'monitoring.title': '监控看板',
119
117
  'monitoring.subtitle': '实时查看宿主机、botmux、机器人和会话的 CPU 与内存压力。',
120
- 'monitoring.runtimeTitle': '运行监控',
118
+ 'monitoring.runtimeTitle': '监控看板',
121
119
  'monitoring.runtimeSubtitle': '实时查看 botmux 的运行健康、资源压力和会话压力。',
122
120
  'monitoring.runtimeHealth': '运行健康',
123
121
  'monitoring.runtimeHealthHint': '确认数据是否新鲜、daemon 是否在线、会话是否堆积。',
@@ -184,6 +182,7 @@ const zh = {
184
182
  'monitoring.sessionsHint': '所有 live 会话都有当前值,只有 Top 会话保留历史曲线。',
185
183
  'monitoring.trackedSessionTrends': 'Top 会话趋势',
186
184
  'monitoring.trackedSessionHint': '这是历史保留集合,不代表全量会话范围。',
185
+ 'monitoring.modalClose': '关闭',
187
186
  'monitoring.noTrackedHistory': '暂无 Top 会话历史。',
188
187
  'monitoring.noHotSession': '暂无热点会话',
189
188
  'monitoring.hottest': '热点',
@@ -203,15 +202,17 @@ const zh = {
203
202
  'monitoring.confidence': '归因',
204
203
  'monitoring.rank': '入选原因',
205
204
  'sessions.title': '会话控制',
206
- 'sessions.subtitle': '定位飞书话题、打开 Web Terminal、关闭或恢复 CLI 会话。',
207
205
  'sessions.search': '搜索群聊 / 工作目录 / 标题 / ID',
208
206
  'sessions.anyStatus': '全部状态',
209
- 'sessions.adoptAny': 'adopt: 全部',
210
- 'sessions.adoptYes': 'adopt: 是',
211
- 'sessions.adoptNo': 'adopt: 否',
212
- 'sessions.chatAny': '所在聊天: 全部',
207
+ 'sessions.adoptAny': '接入:全部',
208
+ 'sessions.adoptYes': '接入:是',
209
+ 'sessions.adoptNo': '接入:否',
210
+ 'sessions.chatAny': '所在聊天:全部',
213
211
  'sessions.showUnknownChats': '显示未知聊天',
214
212
  'sessions.activeOnly': '仅活跃',
213
+ 'sessions.runtime.logical': '可继续会话',
214
+ 'sessions.runtime.resident': '常驻会话',
215
+ 'sessions.runtime.dormant': '休眠会话',
215
216
  'sessions.monitorRoom': '监控室',
216
217
  'sessions.addToMonitorRoom': '添加到监控室',
217
218
  'sessions.monitorRoomAdded': '已添加 {added} 个,总计 {total} 个',
@@ -222,7 +223,8 @@ const zh = {
222
223
  'sessions.idleCleanupThreshold': '空闲清理阈值',
223
224
  'sessions.idleCleanupRun': '清理空闲',
224
225
  'sessions.idleCleanupCount': '可清理 {count} 个',
225
- 'sessions.idleCleanupConfirm': '将关闭 {count} 个空闲超过 {threshold} 的会话,确定继续?',
226
+ 'sessions.idleCleanupCancel': '取消',
227
+ 'sessions.idleCleanupApply': '确定',
226
228
  'sessions.idleCleanupRunning': '清理中…',
227
229
  'sessions.idleCleanupDone': '已关闭 {closed} 个,失败 {failed} 个',
228
230
  'sessions.idleCleanupFailed': '清理失败',
@@ -322,13 +324,14 @@ const zh = {
322
324
  'monitorRoom.terminalUnavailable': '暂无可用终端',
323
325
  'monitorRoom.terminalUnavailableHelp': '会话可能已关闭、还未启动 Web Terminal,或当前访问方式下没有可用代理端口。',
324
326
  'monitorRoom.updated': '更新 {time}',
325
- 'nav.insights': '洞察',
326
- 'insights.title': '工作流洞察',
327
- 'insights.subtitle': '只读分析本机 Claude Code / Codex 会话的动作轨迹、失败与摩擦,给出规则型优化建议。',
327
+ 'nav.insights': '数据洞察',
328
+ 'insights.title': '数据洞察',
328
329
  'insights.refresh': '刷新',
329
330
  'insights.search': '搜索会话 / bot / 目录…',
330
331
  'insights.filter': '筛选',
331
332
  'insights.filterAll': '全部',
333
+ 'insights.filterAllSessions': '全部会话',
334
+ 'insights.filterAllCli': '全部 CLI',
332
335
  'insights.filterReview': '值得复盘',
333
336
  'insights.filterFailed': '有失败',
334
337
  'insights.filterSlow': '有慢 span',
@@ -359,7 +362,7 @@ const zh = {
359
362
  'insights.distTrendSub': '每日会话数',
360
363
  'insights.distMedian': '中位 {v}',
361
364
  'insights.distEmpty': '当前筛选下没有可分析的会话。',
362
- 'insights.disclosure': '口径:耗时只算工具执行时间,已剔除等用户回复(问答/计划确认)的挂机时长,故不反映墙钟时长;Codex 会话的「读」多走 shell(exec_command),不计入「读」相,故其读改比会偏低甚至为 0;代码改动按 patch 解析,仅取每会话最活跃的若干文件,与 Claude 的结构化统计口径不同。跨工具的分布与比值仅供参考,不宜直接对比。',
365
+ 'insights.disclosure': '口径:耗时只算工具执行时间,已剔除等用户回复(问答/计划确认)的挂机时长,故不反映墙钟时长;\nCodex 会话的「读」多走 shell(exec_command),不计入「读」相,故其读改比会偏低甚至为 0;\n代码改动按 patch 解析,仅取每会话最活跃的若干文件,与 Claude 的结构化统计口径不同。跨工具的分布与比值仅供参考,不宜直接对比。',
363
366
  'insights.rwNote': 'Codex 读多走 shell,未计入读相',
364
367
  'insights.viewSessions': '按会话查看',
365
368
  'insights.hotHint': '跨会话复发信号——最该收敛的地方。',
@@ -610,8 +613,8 @@ const zh = {
610
613
  'insights.evidence.readWriteRatio': '读改比 {ratio}',
611
614
  'insights.evidence.compactions': '上下文压缩 {count} 次',
612
615
  'insights.evidence.spansAnalyzed': '已分析 {count} 个 span',
613
- 'connectors.lede': '让外部系统(监控告警、CI、工单…)通过一个 webhook 触发机器人在群里说话或跑工作流。',
614
616
  'connectors.createTitle': '新建 Webhook',
617
+ 'connectors.editTitle': '编辑 Webhook',
615
618
  'connectors.fName': '名称',
616
619
  'connectors.fNamePh': '如:线上告警',
617
620
  'connectors.fBot': '触发的机器人',
@@ -628,21 +631,35 @@ const zh = {
628
631
  'connectors.chatManualLink': '找不到群?手动填 ID →',
629
632
  'connectors.chatListLink': '从群列表选择 ←',
630
633
  'connectors.fAllow': '允许的群',
634
+ 'connectors.allowAll': '全部群',
635
+ 'connectors.allowAllHint': '不限制请求可投递的群',
636
+ 'connectors.groupPickerPlaceholder': '搜索并选择群',
637
+ 'connectors.groupSearchPlaceholder': '搜索群名称或群 ID',
638
+ 'connectors.groupNoMatches': '没有找到匹配的群',
639
+ 'connectors.groupSelectedCount': '已选择 {count} 个群',
631
640
  'connectors.optional': '(可选)',
632
- 'connectors.allowHint': '按住 Ctrl/⌘ 多选;留空 = 不限。只用于校验请求传入的群是否被允许。',
641
+ 'connectors.allowHint': '限制动态请求可投递的群;选择「全部群」表示不限制。',
633
642
  'connectors.dynamicHint': '<b>动态模式</b>:群 ID 随每次请求传入,三选一 —— 查询参数 <code>?chatId=&lt;群ID&gt;</code> · 请求头 <code>x-botmux-chat-id: &lt;群ID&gt;</code> · 请求体 <code>{"chatId":"&lt;群ID&gt;"}</code>。<br>想"一个 URL 直接触发、不带参数",请改选「固定群」。',
634
643
  'connectors.fDedup': '去重字段',
635
644
  'connectors.fDedupPh': '如 alert.id(从事件 body 取值)',
636
- 'connectors.dedupHint': '填了:命中相同值的事件都投到<b>同一个群</b>。留空:每个事件<b>新建一个群</b>。',
645
+ 'connectors.dedupHint': '从请求 JSON 中读取业务唯一键,支持 alert.id 或 $.alert.id。',
646
+ 'connectors.newGroupStrategy': '建群策略',
647
+ 'connectors.newGroupFresh': '每次调用都新建群',
648
+ 'connectors.newGroupFreshHint': '适合彼此独立、无需持续跟进的事件。',
649
+ 'connectors.newGroupReuse': '相同事件复用一个群',
650
+ 'connectors.newGroupReuseHint': '按业务唯一键聚合后续调用,便于持续跟进。',
651
+ 'connectors.newGroupNotice': '此模式会自动创建新群并邀请所选机器人,无需选择现有群。',
637
652
  'connectors.fInstruction': '处理指令',
638
- 'connectors.fInstructionPh': '事件触发时让机器人做什么。如:总结这条告警的严重程度,@相关 oncall,给出排查建议。留空 = 只把事件原样交给模型自由发挥。',
653
+ 'connectors.fInstructionPh': '事件触发后的处理目标。留空时仅把原始事件交给模型。',
639
654
  'connectors.fVerify': '校验方式',
640
655
  'connectors.verifyToken': '令牌(简单:密钥放进 URL,一条 curl 就能触发)',
641
656
  'connectors.verifyHmac': 'HMAC 签名(高级:更安全,需自行对请求签名)',
642
657
  'connectors.fSecret': '密钥 / 令牌',
643
658
  'connectors.fSecretPh': '留空自动生成(只显示一次)',
659
+ 'connectors.fSecretEditPh': '留空保持当前密钥;填写后立即替换',
660
+ 'connectors.cancel': '取消',
661
+ 'connectors.close': '关闭',
644
662
  'connectors.btnCreate': '创建',
645
- 'connectors.listTitle': '已有 Webhook',
646
663
  'connectors.loading': '加载中…',
647
664
  'connectors.noBotGroups': '(该机器人暂无可见群,点右侧手动填 ID)',
648
665
  'connectors.modeLabelFixed': '固定群',
@@ -650,8 +667,7 @@ const zh = {
650
667
  'connectors.modeLabelDynamic': '请求指定群',
651
668
  'connectors.kindLabelWorkflow': '工作流',
652
669
  'connectors.kindLabelTurn': '单轮',
653
- 'connectors.count': '· {count} 个',
654
- 'connectors.empty': '还没有 Webhook。用上面的表单创建一个。',
670
+ 'connectors.empty': '还没有 Webhook,点击右上角新建一个',
655
671
  'connectors.enabled': '已启用',
656
672
  'connectors.disabled': '已停用',
657
673
  'connectors.badgeToken': '令牌',
@@ -674,8 +690,13 @@ const zh = {
674
690
  'connectors.errBot': '请选机器人',
675
691
  'connectors.errWf': '请填工作流 ID',
676
692
  'connectors.errChat': '请选择(或手动填)投递的群',
693
+ 'connectors.errDedup': '请填写用于复用群的业务唯一键',
677
694
  'connectors.creating': '创建中…',
678
695
  'connectors.saving': '保存中…',
696
+ 'connectors.updated': '已保存全部配置',
697
+ 'connectors.enabling': '启用中…',
698
+ 'connectors.disabling': '停用中…',
699
+ 'connectors.deleting': '删除中…',
679
700
  'connectors.usageDynamicLede': '动态模式:URL 已含令牌,调用时再带上目标群 ID{gn}:',
680
701
  'connectors.usageDynamicNote': '群也可放请求头 <code>x-botmux-chat-id</code> 或 body <code>{"chatId":"…"}</code>。⚠️ URL 即凭证,勿泄漏。',
681
702
  'connectors.usageTokenLede': '此 URL 已含令牌、且固定投递到所选群,直接 POST 即可触发:',
@@ -689,13 +710,78 @@ const zh = {
689
710
  'connectors.secretOnce': '(只显示这一次,请保存):',
690
711
  'connectors.createFailed': '创建失败:{error}',
691
712
  'connectors.saveFailed': '保存失败:{error}',
713
+ 'connectors.toggleFailed': '状态更新失败:{error}',
714
+ 'connectors.deleteFailed': '删除失败:{error}',
692
715
  'connectors.noOnlineBots': '(没有在线机器人)',
716
+ 'connectors.storePayload': '记录请求参数',
717
+ 'connectors.storePayloadHint': '保存脱敏后的 JSON 请求体和请求头,默认保留 14 天;可随时在列表关闭。',
718
+ 'connectors.payloadLogged': '参数留存 {days} 天',
719
+ 'connectors.metadataOnly': '仅记录调用元数据',
720
+ 'connectors.btnDisablePayloadLog': '停止留存参数',
721
+ 'connectors.btnEnablePayloadLog': '留存请求参数',
722
+ 'connectors.tabWebhooks': 'Webhook 列表',
723
+ 'connectors.tabLogs': '调用日志',
724
+ 'webhookLogs.subtitle': '集中审阅每次调用的结果、耗时、请求参数与实际投递目标。',
725
+ 'webhookLogs.autoRefresh': '15 秒自动刷新',
726
+ 'webhookLogs.manage': '管理 Webhook',
727
+ 'webhookLogs.summary': '调用概览',
728
+ 'webhookLogs.total': '调用总数',
729
+ 'webhookLogs.filteredRange': '当前筛选范围',
730
+ 'webhookLogs.successRate': '成功率',
731
+ 'webhookLogs.calls': '次成功调用',
732
+ 'webhookLogs.failures': '失败调用',
733
+ 'webhookLogs.needsReview': '需要优先审阅',
734
+ 'webhookLogs.noFailures': '当前范围无失败',
735
+ 'webhookLogs.p95': 'P95 耗时',
736
+ 'webhookLogs.average': '平均',
737
+ 'webhookLogs.allConnectors': '全部 Webhook',
738
+ 'webhookLogs.allStatuses': '全部结果',
739
+ 'webhookLogs.success': '成功',
740
+ 'webhookLogs.failed': '失败',
741
+ 'webhookLogs.last24h': '最近 24 小时',
742
+ 'webhookLogs.last7d': '最近 7 天',
743
+ 'webhookLogs.last30d': '最近 30 天',
744
+ 'webhookLogs.allTime': '全部时间',
745
+ 'webhookLogs.search': '搜索调用记录',
746
+ 'webhookLogs.searchPlaceholder': '搜索 Trigger ID、群 ID、错误或参数…',
747
+ 'webhookLogs.connector': 'Webhook',
748
+ 'webhookLogs.status': '调用结果',
749
+ 'webhookLogs.timeRange': '时间范围',
750
+ 'webhookLogs.refresh': '刷新',
751
+ 'webhookLogs.loadFailed': '调用日志加载失败',
752
+ 'webhookLogs.records': '调用记录',
753
+ 'webhookLogs.matching': '{count} 条匹配',
754
+ 'webhookLogs.loading': '正在加载调用日志…',
755
+ 'webhookLogs.empty': '暂无调用记录',
756
+ 'webhookLogs.emptyHint': '调用任意 Webhook 后,记录会自动出现在这里。',
757
+ 'webhookLogs.unknownConnector': '未知 Webhook',
758
+ 'webhookLogs.loadMore': '加载更多',
759
+ 'webhookLogs.selectRecord': '选择一条记录查看请求详情',
760
+ 'webhookLogs.copyJson': '复制完整 JSON',
761
+ 'webhookLogs.copied': '已复制',
762
+ 'webhookLogs.failureReason': '失败原因',
763
+ 'webhookLogs.overview': '调用概况',
764
+ 'webhookLogs.httpStatus': 'HTTP 状态',
765
+ 'webhookLogs.duration': '处理耗时',
766
+ 'webhookLogs.action': '处理结果',
767
+ 'webhookLogs.bodySize': '请求体大小',
768
+ 'webhookLogs.remoteAddress': '来源地址',
769
+ 'webhookLogs.target': '投递目标',
770
+ 'webhookLogs.queryParams': '查询参数',
771
+ 'webhookLogs.headers': '请求头',
772
+ 'webhookLogs.redacted': '敏感值已脱敏',
773
+ 'webhookLogs.headersNotStored': '此 Webhook 未开启请求头留存。',
774
+ 'webhookLogs.payload': '请求体',
775
+ 'webhookLogs.payloadDisabled': '此 Webhook 未开启请求体留存;调用元数据仍已完整记录。',
776
+ 'webhookLogs.payloadTooLarge': '请求体超过 128 KB,为避免日志膨胀未留存内容。',
777
+ 'webhookLogs.payloadUnavailable': '本次调用没有可留存的 JSON 请求体。',
778
+ 'webhookLogs.routeTarget': '路由参数',
779
+ 'webhookLogs.none': '无',
693
780
  'team.navHome': '我的团队',
694
781
  'team.navManage': '团队管理',
695
- 'team.eyebrow': '团队',
696
- 'team.homeTitle': '团队协作(跨部署)',
697
- 'team.homeLede': '把别的部署(同事自己跑的 botmux)邀请进同一个团队,互相发现机器人、协作拉群。',
698
- 'team.localDeployTitle': '本部署',
782
+ 'team.eyebrow': '团队协作',
783
+ 'team.homeTitle': '团队协作',
784
+ 'team.localDeployTitle': '当前部署',
699
785
  'team.myIdentity': '我的飞书身份:',
700
786
  'team.unbound': '未绑定',
701
787
  'team.bindBtn': '绑定',
@@ -710,17 +796,20 @@ const zh = {
710
796
  'team.roleModalTitle': '默认角色',
711
797
  'team.roleModalHint': '该机器人的默认人设(跨群生效),此处只读。如需修改,请到「Bot 配置」页。',
712
798
  'team.close': '关闭',
713
- 'team.tagLocal': '本部署',
799
+ 'team.tagLocal': '当前部署',
714
800
  'team.tagRemoteStale': '远端·离线?',
715
801
  'team.tagRemote': '远端',
716
802
  'team.removeMember': '移除',
717
803
  'team.depTag': '({tag})',
718
804
  'team.depCount': '{count} 个',
719
805
  'team.depSelected': ',已选 {n}',
806
+ 'team.capLabel': '能力标签',
720
807
  'team.capPh': '能力标签…',
721
808
  'team.viewRole': '查看',
722
809
  'team.hasRoleShort': '有角色',
723
810
  'team.noMatch': '没有符合条件的机器人。',
811
+ 'team.gnameLabel': '群名',
812
+ 'team.gnamePlaceholder': '如:跨团队排障',
724
813
  'team.gnamePh': '群名(如:跨团队排障)',
725
814
  'team.pullGroupBtn': '把勾选的机器人拉一个群',
726
815
  'team.pullGroupHint': '勾选机器人 → 拉到一个飞书群(自动含 owner)',
@@ -739,7 +828,7 @@ const zh = {
739
828
  'team.invalidOwners': '{n} 个 owner 未能拉进',
740
829
  'team.missingIdentity': '你未绑定飞书身份,没把你自己拉进群(去「我的团队」绑定)',
741
830
  'team.skippedNoOwner': '{n} 个机器人因负责人未绑定身份被跳过(未加入群)',
742
- 'team.errNoLocalBot': '请至少勾选一个你自己(本部署)的在线机器人——群要由它创建并把你(发起人)拉进群。',
831
+ 'team.errNoLocalBot': '请至少勾选一个你自己(当前部署)的在线机器人——群要由它创建并把你(发起人)拉进群。',
743
832
  'team.errAllSkipped': '所选机器人的负责人都没绑定身份,无法拉群(机器人不能进一个 owner 不在的群)。请让对应部署先绑定身份。',
744
833
  'team.errNoCreator': '没有可用的建群发起方(相关部署都没有在线机器人,或不可达)',
745
834
  'team.errDelegationTimeout': '委托对方部署建群超时(可能已建,去飞书确认,勿重复点)',
@@ -749,7 +838,6 @@ const zh = {
749
838
  'team.myHostedTeam': '我托管的团队',
750
839
  'team.remoteTeamLabel': '{name} 的团队',
751
840
  'team.manageTitle': '团队管理',
752
- 'team.manageLede': '创建多个团队、给每个团队生成邀请码、或加入别人的团队。一个团队 = 你本部署的机器人 + 加入该团队的其它部署。',
753
841
  'team.hostedTitle': '我托管的团队',
754
842
  'team.newTeamPh': '新团队名称',
755
843
  'team.createTeamBtn': '创建团队',
@@ -841,6 +929,7 @@ const zh = {
841
929
  'sessions.create.columnBacklog': '待办池',
842
930
  'sessions.create.columnHelp': '直接进行中:建完群立刻开跑。待办池:先建群+拉机器人但不起 CLI,之后拖到「进行中」或点「开始」再发给机器人。',
843
931
  'sessions.create.advanced': '更多选项',
932
+ 'sessions.create.optionalConfig': '可选配置',
844
933
  'sessions.create.groupName': '群名称',
845
934
  'sessions.create.groupNamePlaceholder': '留空则取内容首行',
846
935
  'sessions.create.workingDir': '工作目录',
@@ -875,25 +964,39 @@ const zh = {
875
964
  'sessions.kanban.teamScope': '{chats} 个协作群 · {sessions} 个会话',
876
965
  'sessions.kanban.remoteHint': '来自 {name} 部署的会话(快照,终端/历史在对方机器上)',
877
966
  'sessions.kanban.clusterDragHint': '拖动标题整组移动',
967
+ 'sessions.kanban.clusterExpand': '展开群组会话',
968
+ 'sessions.kanban.clusterCollapse': '折叠群组会话',
878
969
  'sessions.history.title': '会话历史',
879
970
  'sessions.history.loading': '正在拉取飞书消息…',
880
971
  'sessions.history.fail': '历史拉取失败',
881
972
  'sessions.history.empty': '没有消息',
882
973
  'sessions.history.user': '用户',
974
+ 'sessions.history.bot': '机器人',
975
+ 'sessions.history.system': '系统消息',
883
976
  'sessions.history.owner': '创建者',
884
977
  'sessions.history.staleHint': 'dashboard 或 daemon 进程可能还在跑旧版本,botmux restart 后重试',
885
- 'groups.title': '群组与 Bot',
886
- 'groups.subtitle': '查看 chat x bot 覆盖矩阵,管理拉群、oncall、退群和解散。',
978
+ 'groups.title': '群组管理',
979
+ 'groups.matrixTitle': '群组矩阵',
887
980
  'groups.search': '搜索群名 / ID / owner',
888
981
  'groups.missingOnly': '仅缺 bot',
889
982
  'groups.refresh': '刷新',
890
- 'groups.create': '新建群',
983
+ 'groups.create': '新建群聊',
891
984
  'groups.chat': '群聊',
892
985
  'groups.actions': '操作',
893
986
  'groups.addBots': '添加 bot',
894
- 'groups.saveAsProfile': '保存为 Profile',
987
+ 'groups.saveAsProfile': '保存Profile',
895
988
  'groups.manage': '管理',
896
989
  'groups.empty': '没有符合条件的群聊。',
990
+ 'groups.paginationLabel': '群组列表分页',
991
+ 'groups.pageStatus': '显示 {from}-{to}/{total} · 第 {page}/{pages} 页',
992
+ 'groups.prevPage': '上一页',
993
+ 'groups.nextPage': '下一页',
994
+ 'groups.botCoverage': '机器人覆盖',
995
+ 'groups.memberSummary': '已入群 {count}/{total}',
996
+ 'groups.botStatusIn': '已入群',
997
+ 'groups.botStatusOut': '缺失',
998
+ 'groups.botStatusError': '异常',
999
+ 'groups.botStatusUnknown': '未知',
897
1000
  'groups.profileStatusFull': '完整匹配 {name}({matched}/{total})',
898
1001
  'groups.profileStatusFullChat': '本群 Role 完整匹配 {name}({matched}/{total})',
899
1002
  'groups.profileStatusPartial': '部分匹配 {name}({matched}/{total})',
@@ -925,6 +1028,7 @@ const zh = {
925
1028
  'groups.saveProfileOverwriteSubmit': '覆盖保存',
926
1029
  'groups.saveProfileInvalid': 'Profile id 只能包含字母、数字、点、下划线、短横线,最长 64,且不能是 . 或 ..',
927
1030
  'groups.saveProfileNoRoles': '这个群里没有可保存的 bot 配置。',
1031
+ 'groups.saveProfilePreparing': '读取配置…',
928
1032
  'groups.saveProfileSaving': '保存中…',
929
1033
  'groups.saveProfileDone': '已保存 {count} 个 entry 到 {name}',
930
1034
  'groups.saveProfileFailed': '只保存了 {saved}/{total} 个 entry,请检查离线 bot 或权限。',
@@ -941,7 +1045,8 @@ const zh = {
941
1045
  'groups.roleProfileBootstrapDone': 'Profile:{name};bootstrap 已完成,无需发送 peer bootstrap 消息。',
942
1046
  'groups.roleProfileBootstrapFailed': 'Profile:{name};bootstrap 失败:{reason}',
943
1047
  'groups.botPicker': 'Bot',
944
- 'groups.createSubmit': '创建',
1048
+ 'groups.createSubmit': '创建群聊',
1049
+ 'groups.createSubmitting': '创建中…',
945
1050
  'groups.cancel': '取消',
946
1051
  'groups.successTitle': '群创建成功',
947
1052
  'groups.openGroup': '打开新群',
@@ -957,7 +1062,6 @@ const zh = {
957
1062
  'groups.needWorkingDir': '请填工作目录',
958
1063
  'groups.noBotsOnline': '没有在线 bot。请先重启 daemon。',
959
1064
  'schedules.title': '定时任务',
960
- 'schedules.subtitle': '跨 daemon 查看、暂停、恢复和立即触发定时任务。',
961
1065
  'schedules.search': '搜索名称 / prompt / 工作目录',
962
1066
  'schedules.anyKind': '全部类型',
963
1067
  'schedules.enabledOnly': '仅启用',
@@ -968,8 +1072,14 @@ const zh = {
968
1072
  'schedules.last': '上次',
969
1073
  'schedules.repeat': '重复',
970
1074
  'schedules.enabled': '启用',
1075
+ 'schedules.paused': '暂停',
971
1076
  'schedules.actions': '操作',
972
1077
  'schedules.runNow': '立即运行',
1078
+ 'schedules.running': '运行中',
1079
+ 'schedules.runDone': '已运行',
1080
+ 'schedules.saving': '保存中',
1081
+ 'schedules.saved': '已保存',
1082
+ 'schedules.failed': '失败',
973
1083
  'schedules.pause': '暂停',
974
1084
  'schedules.resume': '恢复',
975
1085
  'schedules.delivery': '投递',
@@ -980,49 +1090,56 @@ const zh = {
980
1090
  'schedules.useOrigin': '改为原话题',
981
1091
  'schedules.empty': '暂无定时任务。',
982
1092
  'settings.title': '全局设置',
983
- 'settings.subtitle': '管理本机 botmux dashboard 与所有 bot 共享的全局行为。',
984
1093
  'settings.loading': '正在加载设置…',
985
1094
  'settings.loadFailed': '设置加载失败',
986
1095
  'settings.readOnlyVisitor': '当前是只读访问,修改设置需要授权链接(运行 botmux dashboard 获取)',
987
1096
  'settings.sectionAccess': '访问权限',
988
1097
  'settings.publicReadOnly': '允许无 token 只读访问 dashboard',
989
- 'settings.publicReadOnlyHelp': '开启后,没有 token 的访问者可以查看 dashboard、会话、定时任务和 SSE;关闭、暂停、审批等写操作仍必须通过 token 鉴权。敏感终端原始日志始终需要 token。',
1098
+ 'settings.publicReadOnlyHelp': '允许无 token 查看只读数据;关闭、审批、暂停等写操作仍需 token。终端原始日志始终需要 token。',
990
1099
  'settings.remoteAccess': '远程访问终端',
991
- 'settings.remoteAccessHelp': '开启后会话 Web 终端 /飞书卡片「打开 Web 终端」/「获取可操作链接」及 webhook 都走中心化平台链接;关闭则用本地链接。默认关闭。',
1100
+ 'settings.remoteAccessHelp': '默认关闭。会话终端、飞书卡片终端入口和 webhook 使用中心化平台链接;关闭则使用本地链接。',
992
1101
  'settings.sectionCards': '飞书卡片',
993
1102
  'settings.openTerminalInFeishu': '流式卡片 Web 终端按钮在飞书侧栏打开',
994
- 'settings.openTerminalInFeishuHelp': '默认关闭:终端按钮直接打开 Web Terminal URL。开启后使用飞书 web_url/open 包装,在飞书 PC 侧栏里打开;写权限仍由终端 token 控制。',
1103
+ 'settings.openTerminalInFeishuHelp': '默认关闭。将 Web Terminal 链接包装为飞书侧栏打开;写权限仍由终端 token 控制。',
995
1104
  'settings.sectionExperimental': '实验性配置',
996
1105
  'settings.chatBotDiscovery': '群内机器人发现(飞书 /members/bots)',
997
- 'settings.chatBotDiscoveryHelp': '开启后用飞书 /members/bots 接口实时读取当前群里的机器人成员,让多个机器人之间能可靠地互相 @(首条消息就能识别,无需等历史 @ 记录积累),多机器人协作更稳。该接口是飞书未公开 API:默认开启,调用失败会自动回退到旧的发现方式(按配置的 bot 逐个探测 + 历史 @ 记录)。仅在以下情况需要关闭它(强制走旧逻辑):你的租户/网关不支持该接口、或它返回的群成员不准导致 @ 错人/@ 不到、或飞书改动该接口后行为异常。',
1106
+ 'settings.chatBotDiscoveryHelp': '默认开启。实时读取群内机器人成员,提高多 bot 互相 @ 的准确性。接口不可用时会回退旧逻辑;仅在成员识别异常时关闭。',
998
1107
  'settings.sectionVcMeetingAgent': '会议监听',
999
1108
  'settings.vcMeetingAgent': '允许本机使用会议监听能力',
1000
- 'settings.vcMeetingAgentHelp': '默认开启。关闭后,本机所有 bot 不再响应新的会议邀请/会中事件,也不会从运行态恢复会议监听;已在进行中的会议不会被主动拆除,通常会自然收尾。要立即硬停可重启 daemon。',
1109
+ 'settings.vcMeetingAgentHelp': '默认开启。控制本机 bot 是否接收新的会议监听事件。关闭后不再恢复监听;已进行中的会议通常自然结束。',
1001
1110
  'settings.vcMeetingListenerBot': '会议监听 bot 身份',
1002
1111
  'settings.vcMeetingListenerBotAuto': '按 bot 自身配置',
1003
- 'settings.vcMeetingListenerBotHelp': '指定后,只有这个 bot app 会接新的会议监听事件;保存前会校验该 bot 已配置 lark-cli profile 且具备 VC 会议权限,校验通过后自动启用会议监听。事件订阅是否已发布无法通过 API 自动检测。',
1112
+ 'settings.vcMeetingListenerBotHelp': '指定接收会议事件的 bot。保存时校验 lark-cli profile 与会议权限,校验通过后启用监听。',
1004
1113
  'settings.vcMeetingListenerBotDisabled': '保存后自动启用',
1005
1114
  'settings.vcMeetingListenerBotNoProfile': '需先配置 profile',
1115
+ 'settings.larkCliReady': 'lark-cli {version} · 版本符合要求',
1116
+ 'settings.larkCliOutdated': 'lark-cli {version} 版本过低,VC bot 入会需要 ≥ {minimum}',
1117
+ 'settings.larkCliMissing': '未检测到 lark-cli,VC bot 入会前需安装',
1118
+ 'settings.feishuLoginRequired': '需要飞书开放平台登录才能自动配置 VC 权限,请扫码。',
1119
+ 'settings.feishuLoginQrAlt': '飞书开放平台登录二维码',
1120
+ 'settings.feishuLoginClose': '关闭登录二维码',
1006
1121
  'settings.sectionRepoPicker': '仓库选择',
1007
1122
  'settings.repoPickerMode': '仓库选择卡模式',
1008
1123
  'settings.repoPickerModeAll': '仓库 + worktree',
1009
1124
  'settings.repoPickerModeRepos': '仅主仓库',
1010
- 'settings.repoPickerModeHelp': '默认显示仓库和 linked worktree。选择「仅主仓库」后,初始化和裸 /repo 的选择卡只列主仓库;显式 /repo /abs/path/to/worktree 仍可直达 worktree。',
1125
+ 'settings.repoPickerModeHelp': '控制仓库选择卡是否展示 linked worktree;显式 /repo 路径仍可直达 worktree。',
1011
1126
  'settings.sectionWhiteboard': '本地白板',
1012
1127
  'settings.whiteboardEnable': '启用项目白板',
1013
- 'settings.whiteboardEnableHelp': '默认关闭。开启只启用能力,不会立即创建白板;首次需要时才按群+项目 ensure。',
1128
+ 'settings.whiteboardEnableHelp': '默认关闭。开启白板能力;不会立即创建白板,首次按群和项目使用时再初始化。',
1014
1129
  'settings.saving': '保存中…',
1015
1130
  'settings.saved': '已保存',
1016
1131
  'settings.saveFailed': '保存失败',
1017
1132
  'settings.sectionSchedule': '定时任务',
1018
1133
  'settings.scheduleTimeZone': '时区',
1019
- 'settings.scheduleTimeZoneHelp': '定时任务的触发与显示所用时区(IANA 名,如 Asia/Shanghai)。留空=跟随主机时区(当前主机:{host})。当前生效:{effective}。',
1134
+ 'settings.scheduleTimeZoneHost': '跟随主机({host}',
1135
+ 'settings.scheduleTimeZoneHelp': '定时任务触发和显示所用时区。留空跟随主机({host});当前生效:{effective}。',
1020
1136
  'settings.sectionMaintenance': '自动维护',
1021
1137
  'settings.autoUpdate': '自动更新',
1022
- 'settings.autoUpdateHelp': '默认关闭。到点执行 npm install -g botmux@latest 安装最新版本(只下载安装、本身不重启)。仅 npm 全局安装可用。',
1138
+ 'settings.autoUpdateHelp': '默认关闭。按当前安装方式(npm / pnpm)更新全局版本;只更新安装包,不自动重启。',
1023
1139
  'settings.autoRestart': '自动重启',
1024
- 'settings.autoRestartHelp': '默认关闭,需先开启自动更新。自动更新装到新版本后,若没有进行中的会话则自动重启以生效(撞上忙碌会话则跳到次日)。',
1140
+ 'settings.autoRestartHelp': '默认关闭,需先开启自动更新。自动更新后在空闲时重启以生效;有进行中会话则延后到下次窗口。',
1025
1141
  'settings.autoUpdateLocalDev': '当前为本地开发安装(从源码运行),自动更新不可用。',
1142
+ 'settings.autoUpdateUnsupportedInstall': '当前安装方式暂不支持自动更新(目前支持 npm / pnpm 全局安装)。',
1026
1143
  'settings.maintenanceTime': '时间',
1027
1144
  'update.section': '版本与更新',
1028
1145
  'update.loginRequired': '登录后可检查版本、执行更新或重启。',
@@ -1034,8 +1151,11 @@ const zh = {
1034
1151
  'update.checkUnavailable': '无法获取最新版本(离线或受网络限制)',
1035
1152
  'update.nodeWarn': '当前 Node 版本 {version} 过低,更新要求 ≥ {required},请先升级 Node。',
1036
1153
  'update.localDev': '当前为本地开发安装(从源码运行),「更新到最新版」不可用;请用 git pull + 构建后重启。',
1037
- 'update.multiInstallWarn': '检测到多个 botmux 安装,npm 更新只会更新 npm 全局那个,可能不是当前生效的版本:',
1154
+ 'update.multiInstallWarn': '检测到多个 botmux 安装;本次只更新当前运行安装所属的包管理器位置:',
1038
1155
  'update.kindNpm': 'npm 全局',
1156
+ 'update.kindPnpm': 'pnpm 全局',
1157
+ 'update.kindYarn': 'Yarn 全局(暂不支持更新)',
1158
+ 'update.kindBun': 'Bun 全局(暂不支持更新)',
1039
1159
  'update.kindSource': '源码 checkout',
1040
1160
  'update.kindUnknown': '未知',
1041
1161
  'update.btnCheck': '检查更新',
@@ -1049,11 +1169,12 @@ const zh = {
1049
1169
  'update.changelogRateLimited': 'GitHub 接口请求超限(未登录每小时每 IP 60 次,共享网络易触发),暂时拿不到更新内容。',
1050
1170
  'update.changelogViewOnGitHub': '前往 GitHub Releases 查看',
1051
1171
  'update.navBadgeTitle': '有新版本 {version}',
1052
- 'update.confirmMultiInstall': '检测到多个 botmux 安装:\n{paths}\n\nnpm 更新只会更新 npm 全局那个,可能不是当前生效的版本。仍要继续?',
1053
- 'update.confirmUpdate': '将运行 npm install -g botmux@latest,更新到 {version}。确认继续?',
1054
- 'update.confirmUpdateNoVer': '将运行 npm install -g botmux@latest 更新到最新版。确认继续?',
1172
+ 'update.confirmMultiInstall': '检测到多个 botmux 安装:\n{paths}\n\n只会更新当前运行的安装位置。仍要继续?',
1173
+ 'update.confirmUpdate': '将运行 {command},更新到 {version}。确认继续?',
1174
+ 'update.confirmUpdateNoVer': '将运行 {command} 更新到最新版。确认继续?',
1055
1175
  'update.nodeTooOldAlert': '当前 Node 版本 {version} 过低(要求 ≥ {required}),请先升级 Node 再更新。',
1056
- 'update.updating': '正在更新(npm install -g botmux@latest),请稍候…',
1176
+ 'update.updating': '正在更新({command}),请稍候…',
1177
+ 'update.unsupportedInstall': '当前安装方式无法安全自动更新;目前仅支持 npm / pnpm 全局安装。请使用原包管理器手动更新。',
1057
1178
  'update.updatedChanged': '已更新 {old} → {new}。',
1058
1179
  'update.confirmRestart': '需要重启 botmux 以应用新版本。现在重启?(所有会话会冷恢复,仪表盘会短暂断开并自动重连)',
1059
1180
  'update.alreadyLatestRun': '已是最新版本({version}),无需更新。',
@@ -1064,27 +1185,32 @@ const zh = {
1064
1185
  'update.restartSlow': '重启耗时较长,请稍后手动刷新页面。',
1065
1186
  'update.restartFailed': '重启失败:{detail}',
1066
1187
  'skills.title': 'Skill 管理',
1067
- 'skills.subtitle': '管理 botmux 的 CLI 无关 Skill 资产,并按 bot 选择优先披露。',
1068
1188
  'skills.installed': '已安装 Skills',
1069
- 'skills.installedHelp': '本机 registry 中可被 bot 优先披露的 Skill 资产。',
1070
- 'skills.overviewTitle': '按 Bot 组织 Skill 资产',
1071
- 'skills.overviewBody': '全局 Skill 注入配置控制会话注入策略;每个 bot 只维护自己的优先披露列表。',
1189
+ 'skills.installedHelp': '本机 registry 中可供 bot 优先披露的 Skill',
1072
1190
  'skills.metricInstalled': '已安装 Skills',
1073
1191
  'skills.metricBots': '已配置 Bot',
1074
1192
  'skills.metricAttached': '优先引用',
1075
1193
  'skills.install': '安装 Skill',
1076
1194
  'skills.installInfoLabel': '安装位置说明',
1077
- 'skills.installInfo': '注册: ~/.botmux/skills/registry.json\n安装: ~/.botmux/skills/store/技能名;Git 缓存: ~/.botmux/skills/sources\n隔离: 不写入 Codex/Claude 全局目录;本机 CLI Skill 直接引用原地址',
1195
+ 'skills.installInfo': '注册信息写入 ~/.botmux/skills/registry.json;安装内容存放在 ~/.botmux/skills/store。本机 CLI Skill 以原路径引用,不写入 CLI 全局目录。',
1078
1196
  'skills.source': '导入地址',
1079
- 'skills.sourcePlaceholder': '粘贴 GitHub 仓库 / Git URL / 本机 Skill 目录',
1197
+ 'skills.sourcePlaceholder': '粘贴 GitHub 仓库 / Git URL / agentbuddy 安装命令 / 本机 Skill 目录',
1080
1198
  'skills.sourceHelpRemoteLabel': 'GitHub / Git: ',
1081
1199
  'skills.sourceHelpRemote': '可粘贴仓库根地址;多 Skill 仓库点击安装后选择。',
1082
1200
  'skills.sourceHelpLocalLabel': '本机 CLI Skill 目录: ',
1083
1201
  'skills.sourceHelpLocal': '直接引用原地址,不复制到 botmux store。',
1202
+ 'skills.sourceHelpAgentbuddyLabel': 'AgentBuddy: ',
1203
+ 'skills.sourceHelpAgentbuddy': '直接粘贴 agentbuddy 安装命令,例如 agentbuddy skill collection add <uid> / agentbuddy plugin collection add <uid>;开源 skills 用 skills add owner/repo 也认(走 GitHub 安装)。agentbuddy 命令需部署机已 agentbuddy login。',
1204
+ 'skills.agentbuddyNotFound': '部署机未找到 agentbuddy CLI。请在部署机全局安装,或设置 BOTMUX_AGENTBUDDY_CMD。',
1205
+ 'skills.agentbuddyNeedsLogin': '部署机 agentbuddy 未登录。请在部署机运行 agentbuddy login 后重试。',
1206
+ 'skills.agentbuddyCommandFailed': 'agentbuddy 安装失败,请查看部署机日志。',
1207
+ 'skills.agentbuddyTelemetryFailed': '内嵌 telemetry 清理失败,已中断安装(如需保留可设 BOTMUX_AGENTBUDDY_KEEP_TELEMETRY=1)。',
1208
+ 'skills.agentbuddyNoSkill': 'agentbuddy 未产出任何 Skill,请检查 identifier 是否正确。',
1209
+ 'skills.agentbuddyInvalid': 'agentbuddy identifier 格式不合法。',
1084
1210
  'skills.discover': '发现 Skill',
1085
1211
  'skills.localDiscover': '浏览本机 Skill',
1086
1212
  'skills.localDiscoverTitle': '本机 CLI Skill',
1087
- 'skills.localDiscoverHelp': ' Codex / Claude 等本机 CLI 已安装的 Skill 目录中选择注册。',
1213
+ 'skills.localDiscoverHelp': '扫描本机 CLI 已安装的 Skill,并注册为本地引用。',
1088
1214
  'skills.scan': '扫描',
1089
1215
  'skills.scanning': '正在扫描',
1090
1216
  'skills.scanFound': '发现 {count} 个 Skill',
@@ -1092,7 +1218,7 @@ const zh = {
1092
1218
  'skills.sourceRequired': '请先填写导入地址。',
1093
1219
  'skills.advanced': '高级选项',
1094
1220
  'skills.discoverTitle': '发现本机 CLI Skill',
1095
- 'skills.discoverHelp': '扫描当前部署中已配置 bot 对应的 CLI Skill 目录;选中后注册为本地引用,不复制文件。',
1221
+ 'skills.discoverHelp': '扫描已配置 bot CLI Skill 目录;选中后注册为本地引用,不复制文件。',
1096
1222
  'skills.discoverEmpty': '没有在本机 CLI skill 目录中发现可注册的 Skill。',
1097
1223
  'skills.discoverGroupEmpty': '这个 CLI 目录下没有可注册的 Skill。',
1098
1224
  'skills.discoverRegistered': '已注册',
@@ -1118,7 +1244,7 @@ const zh = {
1118
1244
  'skills.installSubmit': '安装',
1119
1245
  'skills.installSelected': '安装选中',
1120
1246
  'skills.installSelectionTitle': '选择要安装的 Skill',
1121
- 'skills.installSelectionHelp': '这个来源中发现 {count} 个 Skill,默认全选;取消不需要的项后再安装。',
1247
+ 'skills.installSelectionHelp': '发现 {count} 个 Skill;取消不需要的项后再安装。',
1122
1248
  'skills.installSelectionCancel': '取消',
1123
1249
  'skills.update': '更新',
1124
1250
  'skills.remove': '删除',
@@ -1135,10 +1261,8 @@ const zh = {
1135
1261
  'skills.globalProjectAllHelp': '读取 .agents/skills 与\n.botmux/skills',
1136
1262
  'skills.globalDelivery': 'Skill 注入方式',
1137
1263
  'skills.bots': 'Bot Skill 配置',
1138
- 'skills.botsHelp': '为每个 bot 选择最需要优先披露的 Skill。',
1264
+ 'skills.botsHelp': '为每个 bot 设置优先披露的 Skill。',
1139
1265
  'skills.botCount': '{count} 个 Bot',
1140
- 'skills.scrollBotsPrev': '向左查看 Bot',
1141
- 'skills.scrollBotsNext': '向右查看 Bot',
1142
1266
  'skills.skillCount': '{count} 个 Skill',
1143
1267
  'skills.attach': '加入优先披露',
1144
1268
  'skills.detach': '移除',
@@ -1159,20 +1283,31 @@ const zh = {
1159
1283
  'skills.projectAllHelp': '这个 bot 加入工作区 skill 候选',
1160
1284
  'skills.priority': '优先 skills',
1161
1285
  'skills.noPriority': '未配置,保持 CLI 默认行为',
1286
+ 'skills.pickerPlaceholder': '选择优先 Skill',
1287
+ 'skills.pickerSelectedCount': '已选择 {count} 个 Skill',
1288
+ 'skills.pickerTriggerHint': '点击搜索或调整多选',
1289
+ 'skills.pickerSearchPlaceholder': '搜索 Skill 名称或描述',
1290
+ 'skills.pickerSelectionMeta': '已选 {selected} / 共 {total}',
1291
+ 'skills.pickerClear': '清空',
1292
+ 'skills.pickerNoResults': '没有匹配的 Skill',
1293
+ 'skills.saveSelection': '保存选择',
1294
+ 'skills.cancel': '取消',
1295
+ 'skills.saving': '保存中…',
1296
+ 'skills.policySaved': '优先 Skill 已保存',
1162
1297
  'skills.dangling': '未安装',
1163
1298
  'skills.removeInUse': 'Skill "{skill}" 仍被以下配置引用:{refs}。删除只会移除 registry 文件,不会自动清理引用。继续删除?',
1164
1299
  'skills.saved': '已保存',
1165
1300
  'skills.failed': '失败',
1166
1301
  'skills.jobRunning': '处理中...',
1167
1302
  'skills.refresh': '刷新',
1168
- 'botDefaults.title': '数字员工档案',
1169
- 'botDefaults.subtitle': '每位员工的默认行为:oncall、主动开工、人设角色、卡片与授权。',
1303
+ 'botDefaults.title': 'Bot 配置',
1170
1304
  'botDefaults.metaOnline': '在线 · daemon 正常',
1171
1305
  'botDefaults.search': '搜索 bot 名 / app id',
1172
1306
  'botDefaults.refresh': '刷新',
1173
1307
  'botDefaults.sectionOncall': '新群 Oncall',
1174
1308
  'botDefaults.sectionBrand': '卡片签名',
1175
1309
  'botDefaults.renameTitle': '修改机器人名称',
1310
+ 'botDefaults.renameAction': '修改名称',
1176
1311
  'botDefaults.renameSave': '保存',
1177
1312
  'botDefaults.renameCancel': '取消',
1178
1313
  'botDefaults.renameEmpty': '名称不能为空',
@@ -1197,7 +1332,7 @@ const zh = {
1197
1332
  'botDefaults.agentCli': 'CLI',
1198
1333
  'botDefaults.agentModel': '模型',
1199
1334
  'botDefaults.agentModelPlaceholder': '留空使用该 CLI 默认模型',
1200
- 'botDefaults.agentHelp': '改动只影响新创建的会话;已有会话会继续使用创建时的 CLI / 模型。若要让旧对话使用新配置,请关闭后重新开始。',
1335
+ 'botDefaults.agentHelp': '只影响新会话;已有会话继续使用创建时的 CLI / 模型,需关闭后重开才会切换。',
1201
1336
  'botDefaults.agentSave': '保存 CLI / 模型',
1202
1337
  'botDefaults.skillInjection': 'botmux skills 注入方式',
1203
1338
  'botDefaults.skillInjectionDynamic': '动态注入(--plugin-dir,逐会话)',
@@ -1205,8 +1340,8 @@ const zh = {
1205
1340
  'botDefaults.skillInjectionPrompt': 'prompt — 注入会话 prompt,不落全局盘',
1206
1341
  'botDefaults.skillInjectionGlobal': 'global — 装进 CLI 全局 skills 目录',
1207
1342
  'botDefaults.skillInjectionOff': 'off — 只给 botmux --help 引导',
1208
- 'botDefaults.skillInjectionHelpDynamic': '该 CLI(claude 家族)走 --plugin-dir 逐会话动态注入 botmux 技能:仅本会话可见、不写全局盘、随开随走,无需配置。',
1209
- 'botDefaults.skillInjectionHelp': '这个 bot 的 botmux 内置 skills 怎么送进 codex/gemini 等「只有全局 skills 目录」的 CLI。默认 prompt:把 skills 目录注入会话 prompt(只在会话开场注入一次,后续每轮不重复),全文按需 `botmux skill show`,不写 ~/.codex/skills 等全局盘,你手动跑的独立 CLI 看不到;global:装进 CLI 全局目录(原生体验,但独立 CLI 也会看到);off:只留路由提示 + `botmux --help`。改后下个会话生效;切到/离开 global 需重启 daemon 才完全生效。',
1343
+ 'botDefaults.skillInjectionHelpDynamic': '该 CLI 支持 --plugin-dir 动态注入。skills 仅当前会话可见,不写入全局目录,无需额外配置。',
1344
+ 'botDefaults.skillInjectionHelp': '选择 botmux skills 的注入方式:prompt 为默认方式,会在会话开始时写入提示词且不改全局目录;global 安装到 CLI 全局 skills 目录;off 仅保留 botmux --help 引导。改动下个新会话生效,切换 global 需重启 daemon',
1210
1345
  'botDefaults.agentSaved': '已保存(下个新会话生效)',
1211
1346
  'botDefaults.warning': '开启后,没有 oncall binding 的群会在下次开新话题时自动绑定到该目录;手动绑定或手动解绑过的群不会被覆盖。',
1212
1347
  'botDefaults.empty': '没有在线 bot。先 botmux restart 让 daemon 上线。',
@@ -1223,16 +1358,16 @@ const zh = {
1223
1358
  'botDefaults.workingDirModeOff': '关闭(新会话弹「选仓库」卡)',
1224
1359
  'botDefaults.workingDirModeDefault': '仅默认目录(不改权限)',
1225
1360
  'botDefaults.workingDirModeOncall': 'Oncall 模式(群内开放对话)',
1226
- 'botDefaults.workingDirModeHelp': '该 bot 新会话默认在哪个目录启动,三选一(互斥):「关闭」=不钉目录,新会话弹「选仓库」卡;「仅默认目录」=所有新会话(含私聊/话题)直接进该目录、跳过选仓库卡,不改任何权限(私有 bot 用);「Oncall 模式」=在「仅默认目录」基础上,额外把新进的普通群自动绑定为 oncall(群里任何人都能跟 bot 对话;按钮/命令等写操作仍只限 allowedUsers),适合值班/对外支持。改后下个新会话生效,运行中的会话需 /restart。',
1361
+ 'botDefaults.workingDirModeHelp': '设置新会话启动目录:关闭=走仓库选择;仅默认目录=直接进入该目录且不改变权限;Oncall=默认目录 + 新普通群自动开放对话。改动下个新会话生效。',
1227
1362
  'botDefaults.autoWorktree': '每个新会话自动创建 worktree',
1228
- 'botDefaults.autoWorktreeHelp': '仅「仅默认目录」模式可用:新会话启动前,先在默认目录(须是 git 仓库)基于远端默认分支自动创建一个独立 worktree,会话在该 worktree 里运行,多个会话互不干扰。覆盖交互式新话题/私聊、dashboard 建会话、webhook 外部事件(workflow 不适用)。默认目录不是 git 仓库或创建失败时回退到直接用默认目录启动并在群里提示。会话 /close 不会自动删除 worktree。',
1363
+ 'botDefaults.autoWorktreeHelp': '仅用于「仅默认目录」。新会话会在默认 git 仓库中创建独立 worktree,避免并发会话互相影响;失败时回退到默认目录。/close 不会自动删除 worktree。',
1229
1364
  'botDefaults.workingDirSaved': '已保存(下个新会话生效)',
1230
1365
  'botDefaults.brandLabel': '个性签名(卡片页脚)',
1231
- 'botDefaults.brandLabelHelp': ' bot 发出的卡片页脚签名。留空保存=不显示;填写=自定义(支持 markdown,如 [Acme](https://…));恢复默认=显示 botmux。',
1366
+ 'botDefaults.brandLabelHelp': '设置该 bot 卡片页脚签名。留空=不显示;填写=自定义 Markdown;恢复默认=显示 botmux。',
1232
1367
  'botDefaults.brandLabelPlaceholder': '默认:botmux(留空则不显示)',
1233
1368
  'botDefaults.sectionSandbox': '文件沙盒(oncall)',
1234
1369
  'botDefaults.sandboxToggle': '开启文件沙盒',
1235
- 'botDefaults.sandboxHelp': '开启后,该 bot 的每个会话都跑在按会话隔离的沙盒里:只看得到一份项目副本,碰不到你磁盘上的真实文件、密钥、别的会话数据。适合把机器人分享给半受信任的人(oncall)。仅 Linux 生效,下个新会话起效。',
1370
+ 'botDefaults.sandboxHelp': '为该 bot 的新会话启用隔离项目副本,避免直接访问真实文件、密钥和其他会话。仅 Linux 生效,适合 oncall 场景。',
1236
1371
  'botDefaults.sandboxSaved': '已保存(下个新会话生效)',
1237
1372
  'botDefaults.brandSave': '保存签名',
1238
1373
  'botDefaults.brandReset': '恢复默认',
@@ -1241,67 +1376,66 @@ const zh = {
1241
1376
  'botDefaults.brandStateCustom': '当前:自定义',
1242
1377
  'botDefaults.sectionCard': '卡片行为',
1243
1378
  'botDefaults.disableStreaming': '关闭飞书流式卡片',
1244
- 'botDefaults.disableStreamingHelp': '不再发实时刷新的会话状态卡(含「打开 Web 终端」入口);任务最终结果仍通过消息送达。适合嫌流式卡片烦的场景。',
1379
+ 'botDefaults.disableStreamingHelp': '关闭实时会话状态卡和 Web Terminal 入口;最终结果仍会以消息发送。',
1245
1380
  'botDefaults.silentTurnReactions': '关闭无卡片模式下的状态 reaction',
1246
- 'botDefaults.silentTurnReactionsHelp': '关闭流式卡片后,botmux 会用 ✋→✅ 这类轻量 reaction 给触发消息标「已收到 / 已完成」。勾选后连这个也不加,适合低噪音的观察型 bot。仅在「关闭飞书流式卡片」开启时可改。',
1381
+ 'botDefaults.silentTurnReactionsHelp': '关闭流式卡片后,默认用 reaction 标记收到/完成。开启后不再添加这些状态 reaction',
1247
1382
  'botDefaults.writableLink': '卡片上直接给可操作(可写)终端链接',
1248
- 'botDefaults.writableLinkHelp': '⚠️ 在流式卡片正文直接贴出可写终端链接,群内任何人都能点开并操控终端。不勾=保持现状(走「获取操作链接」按钮私聊发给点击者)。',
1383
+ 'botDefaults.writableLinkHelp': '在流式卡片正文中显示可写终端链接。群内成员可直接操作终端,请仅在可信群使用。',
1249
1384
  'botDefaults.writableLinkMoot': '已关闭流式卡片',
1250
1385
  'botDefaults.privateCard': '/card 发私密卡片(仅授权人可见)',
1251
- 'botDefaults.privateCardHelp': '开启后 /card 改用「仅特定人可见」的临时卡片:只发给 ownerallowedUsers),/grant 授权对话的人和群里其他人都看不到。代价:是静态快照、不会实时刷新;且仅普通群可用(话题群 / 单聊会失败,不降级)。只影响 /card 命令,自动流式卡不变。',
1386
+ 'botDefaults.privateCardHelp': '/card 只发送给 owner/allowedUsers。卡片为静态快照,仅普通群可用;不影响自动流式卡片。',
1252
1387
  'botDefaults.sectionCrossBot': '跨 bot 协作',
1253
1388
  'botDefaults.botToBotSameDir': 'bot@bot 同目录拉起',
1254
- 'botDefaults.botToBotSameDirHelp': '开启后,本 bot 被 @ 进一个已有其它 bot 在干活的群/话题时,直接复用对方的工作目录、跳过仓库选择卡片(与 oncall 绑定无关,默认开)。关掉则本 bot 永远走自己的仓库选择卡 / 默认目录。',
1389
+ 'botDefaults.botToBotSameDirHelp': '默认开启。当该 bot 被 @ 到已有其他 bot 工作的群/话题时,复用对方工作目录并跳过仓库选择。关闭后始终使用本 bot 自己的目录规则。',
1255
1390
  'botDefaults.cardPrefSaved': '已保存',
1256
1391
  'botDefaults.sectionSummaryTrigger': '/summary 总结范围',
1257
1392
  'botDefaults.summaryLimit': '最近消息条数',
1258
1393
  'botDefaults.summarySinceHours': '最近小时数',
1259
- 'botDefaults.summaryLimitHelp': '@ 机器人并输入 /summary 时读取该范围内历史消息;默认最近 50 / 24 小时,任一项填 0 表示该项不做限制。话题群始终读取当前话题历史。',
1394
+ 'botDefaults.summaryLimitHelp': '/summary 读取的历史范围。默认最近 50 条或 24 小时;任一项填 0 表示不限制。话题群始终只读当前话题。',
1260
1395
  'botDefaults.summarySave': '保存总结范围',
1261
1396
  'botDefaults.summaryNumberInvalid': '时长和条数必须是 0 或正整数',
1262
1397
  'botDefaults.sectionRole': '默认角色',
1263
- 'botDefaults.roleHelp': '该 bot 的默认人设(跨群生效),会注入到该 bot 在各群的会话里;单个群可在「角色」页单独覆盖。留空保存=删除。',
1398
+ 'botDefaults.roleHelp': '该 bot 的默认角色,会注入到所有会话;单个群可在「角色管理」覆盖。留空保存即删除。',
1264
1399
  'botDefaults.rolePlaceholder': '例如:你是后端排障助手,回答简洁、优先给可执行命令…',
1265
1400
  'botDefaults.roleSave': '保存角色',
1266
- 'botDefaults.roleDelete': '删除',
1267
1401
  'botDefaults.roleSaved': '已保存',
1268
1402
  'botDefaults.roleDeleted': '已删除',
1269
1403
  'botDefaults.roleLoadErr': '角色加载失败',
1270
1404
  'botDefaults.profileRoles': 'Profile 角色',
1271
- 'botDefaults.profileRolesHelp': ' bot 在各个 Profile 中的角色条目;默认折叠,展开后读取详情。',
1405
+ 'botDefaults.profileRolesHelp': '展示该 bot 在各 Profile 中的角色条目;展开后加载详情。',
1272
1406
  'botDefaults.profileRolesEmpty': '这个 bot 暂无 Profile 角色。',
1273
1407
  'botDefaults.profileRolesLoadFailed': 'Profile 角色加载失败:{error}',
1274
1408
  'botDefaults.profileRoleClickToLoad': '展开后加载角色详情。',
1275
1409
  'botDefaults.profileRoleDetailLoadFailed': '角色详情加载失败:{error}',
1276
1410
  'botDefaults.sectionAutoStart': '主动开工',
1277
1411
  'botDefaults.autoStartJoin': '被拉进新群自动开工',
1278
- 'botDefaults.autoStartJoinHelp': '开启后,机器人一被拉进新群(群里有授权用户 allowedUsers 时)就自动开一个会话开始工作,无需 @。在机器人的默认工作目录启动;未配置默认目录时先弹仓库选择卡让你选。前提:需在飞书开放平台为本应用订阅「机器人进群」事件 im.chat.member.bot.added_v1,并开通群成员读取权限。',
1412
+ 'botDefaults.autoStartJoinHelp': '机器人被加入新群且群内有授权用户时,自动启动会话,无需 @。使用默认工作目录;未配置时先弹仓库选择。需要订阅机器人进群事件并具备群成员读取权限。',
1279
1413
  'botDefaults.autoStartJoinPrompt': '入群首轮 prompt(可选)',
1280
1414
  'botDefaults.autoStartJoinPromptPlaceholder': '填了=作为入群后的第一条任务;留空=机器人自己看群里信息决定做什么',
1281
1415
  'botDefaults.autoStartJoinPromptSave': '保存 prompt',
1282
1416
  'botDefaults.autoStartTopic': '话题群新话题自动开工',
1283
- 'botDefaults.autoStartTopicHelp': '开启后,在话题群里每当有人新开一个话题,机器人就会自动接入该话题、把首条消息当作任务开始处理,无需 @。仅对话题群生效,普通群不受影响。',
1417
+ 'botDefaults.autoStartTopicHelp': '话题群中新建话题时,自动接入并处理首条消息,无需 @。仅影响话题群。',
1284
1418
  'botDefaults.sectionSessionMode': '会话模式',
1285
1419
  'botDefaults.p2pMode': '私聊会话模式',
1286
1420
  'botDefaults.p2pThread': 'thread(每条 DM 独立会话)',
1287
1421
  'botDefaults.p2pChat': 'chat(扁平连续单聊会话)',
1288
- 'botDefaults.p2pHelp': '私聊(1:1 DM)的会话方式:thread = 每条顶层消息各自起独立会话(避免把对话堆进同一个 CLI 进程);chat = 整段 DM 共用一个连续会话、共享上下文(类 Hermes)。改后立即生效。',
1422
+ 'botDefaults.p2pHelp': '私聊会话方式:thread=每条顶层消息独立会话;chat=整段私聊共享一个连续会话。改动立即生效。',
1289
1423
  'botDefaults.regularGroupMode': '普通群会话模式',
1290
1424
  'botDefaults.regularGroupModeChat': 'chat(扁平连续单聊会话,默认)',
1291
1425
  'botDefaults.regularGroupModeChatTopic': 'chat-topic(顶层平铺连续会话,原生话题各自独立会话)',
1292
1426
  'botDefaults.regularGroupModeNewTopic': 'new-topic(每条顶层 @ 各开独立话题与会话)',
1293
1427
  'botDefaults.regularGroupModeShared': 'shared(话题模式但复用同一个 session)',
1294
- 'botDefaults.regularGroupModeHelp': '普通群(非话题群)里 @ 该 bot 的新顶层消息怎么开会话:chat = 整群共用一个连续会话(默认,连你在群里手动开的原生话题也并进这个会话);chat-topic = 顶层 @ 仍平铺进群里那一个连续会话,但你手动开的原生话题各自独立会话(话题里开新会话);new-topic = 每条顶层 @ 在原消息下开独立话题、各自独立会话;shared = 话题模式但复用同一个 session(回复落在话题里、但共用本群会话与上下文)。这是 per-bot 默认,具体某个群可用 /reply-mode 单独覆盖。改后立即生效。',
1428
+ 'botDefaults.regularGroupModeHelp': '普通群顶层 @ 的开会话方式:chat=整群连续会话;chat-topic=顶层连续、原生话题独立;new-topic=每次 @ 新建话题与会话;shared=话题展示但共享会话。可被群级 /reply-mode 覆盖。',
1295
1429
  'botDefaults.mentionMode': '群聊 @ 策略',
1296
1430
  'botDefaults.mentionModeAlways': '都需要 @(默认)',
1297
1431
  'botDefaults.mentionModeTopic': '仅话题内不需要 @',
1298
1432
  'botDefaults.mentionModeNever': '所有消息都不需要 @',
1299
1433
  'botDefaults.mentionModeAmbient': '都不需要 @(但你 @ 别人时让位)',
1300
- 'botDefaults.mentionModeHelp': ' bot 全局生效,决定群里要不要 @ 才回:「都需要 @」= 任何消息都得 @(默认,最安全;多人群里话题内也要 @);「仅话题内不需要 @」= 起新对话 / 顶层仍要 @,但在该 bot 已开的任何话题里(new-topic / shared / 话题群)后续消息免 @ 续聊;「所有消息都不需要 @」= 该 bot 有对话权限的群里非 @ 消息也无条件回(含全新消息冷启动,适合专用 / 值班小群);「都不需要 @(但你 @ 别人时让位)」= 同样免 @ 也回,但当这条消息 @ 了别的人或别的 bot(而没 @ 它)时它识趣不回,相当于你把这条交给别人了(@所有人 不算交给别人,仍会回),适合多人 / 多 bot 群里想要一个默认响应者、但你点名别人时它就让位。注:群里只有你和该 bot(1 对 1)时一直免 @,与本设置无关。',
1434
+ 'botDefaults.mentionModeHelp': '控制群聊是否必须 @ 才回复:默认都需要 @;可允许已接管话题内免 @、全群免 @,或在消息 @ 其他人时让位。私聊始终不需要 @。',
1301
1435
  'botDefaults.docSubscribeMode': '文档订阅触发范围(默认)',
1302
1436
  'botDefaults.docSubscribeModeMention': '仅评论 @ 我才触发',
1303
1437
  'botDefaults.docSubscribeModeAll': '所有新评论都触发',
1304
- 'botDefaults.docSubscribeModeHelp': ' /subscribe-lark-doc 订阅飞书文档后,文档评论会喂进会话、bot 回复发回评论。这里设新订阅的默认触发范围:「仅评论 @ 我」最安全(防刷屏);「所有新评论」适合专用文档。',
1438
+ 'botDefaults.docSubscribeModeHelp': '设置新文档订阅的默认触发范围。仅评论 @ 我更安静;所有新评论适合专用文档。',
1305
1439
  'botDefaults.sectionSubstitute': '替身模式',
1306
1440
  'botDefaults.substituteEnabled': '启用替身触发',
1307
1441
  'botDefaults.substituteHelp': '普通群里 @ 到配置的替身对象时,由本 bot 代答;发消息的人仍需具备 canTalk 权限。推荐与「Oncall 模式」一起使用,让群内成员都能自然 @ 替身触发代答。当前群可用 /substitute off 临时关闭。',
@@ -1309,8 +1443,19 @@ const zh = {
1309
1443
  'botDefaults.substituteDisclosurePrefix': '默认说明“我先代 TA 回复”',
1310
1444
  'botDefaults.substituteDisclosureNone': '不额外说明',
1311
1445
  'botDefaults.substituteTargetsPlaceholder': 'zhangsan@bytedance.com\nou_xxxx(也可直接填 open_id / union_id)',
1312
- 'botDefaults.substituteTargetsHelp': '一行一个替身对象:填邮箱最省事(保存时自动解析成 open_id 并显示姓名),也可直接填 ou_ 开头的 open_id 或 on_ 开头的 union_id。邮箱解析受本 bot 的通讯录可见范围限制,解析不到的会标红。',
1313
- 'botDefaults.substituteTargetsInvalid': '这些行无法识别(只能填邮箱 / ou_ / on_,纯姓名无法解析)',
1446
+ 'botDefaults.substituteTargets': '替身对象',
1447
+ 'botDefaults.substituteTargetsHelp': '每项对应一个替身对象。可直接填邮箱(保存时自动解析为 Open ID),也可选择 Open ID、User ID 或 Union ID;解析失败的邮箱会标红。',
1448
+ 'botDefaults.substituteTargetType': '标识类型',
1449
+ 'botDefaults.substituteTargetEmail': '邮箱',
1450
+ 'botDefaults.substituteTargetOpenId': 'Open ID',
1451
+ 'botDefaults.substituteTargetUserId': 'User ID',
1452
+ 'botDefaults.substituteTargetUnionId': 'Union ID',
1453
+ 'botDefaults.substituteTargetIdPlaceholder': '输入飞书用户标识或邮箱',
1454
+ 'botDefaults.substituteTargetName': '显示名称',
1455
+ 'botDefaults.substituteTargetNamePlaceholder': '显示名称(可选)',
1456
+ 'botDefaults.substituteTargetAdd': '添加替身对象',
1457
+ 'botDefaults.substituteTargetRemove': '删除替身对象',
1458
+ 'botDefaults.substituteTargetsInvalid': '启用前至少填写一个有效的替身对象;邮箱需能解析为 Open ID',
1314
1459
  'botDefaults.substituteTargetsRequired': '开启替身触发至少需要一个能解析成 open_id 的对象',
1315
1460
  'botDefaults.substituteResolving': '解析中…',
1316
1461
  'botDefaults.substituteUnresolved': '未解析',
@@ -1318,45 +1463,44 @@ const zh = {
1318
1463
  'botDefaults.substituteOff': '关闭全局替身配置',
1319
1464
  'botDefaults.sectionGrant': '授权与额度',
1320
1465
  'botDefaults.autoGrantCard': '未授权 @ 自动弹授权卡',
1321
- 'botDefaults.autoGrantCardHelp': '开启后,群里有人或外部 bot 明确 @ bot 但被对话权限闸挡住时,会自动给 owner /grant 申请卡;关闭后保持权限拦截但静默丢弃。',
1466
+ 'botDefaults.autoGrantCardHelp': '未授权用户或外部 bot 明确 @ 时,自动向 owner 发送 /grant 申请卡。关闭后仍拦截,但不提示。',
1322
1467
  'botDefaults.restrictGrant': '限制被授权人只能纯对话',
1323
- 'botDefaults.restrictGrantHelp': '开启后,被 /grant 授权的人(owner 自己不受限)只能发普通对话,所有 slash 命令一律拦截:botmux 自带命令、透传命令、/workflow、/template、/introduce、/t 以及 CLI 原生命令(/help 等)。形如 /path/to/file 的内容不会被误判。',
1468
+ 'botDefaults.restrictGrantHelp': '限制 /grant 用户只能普通对话,禁止 botmux 命令、透传命令、CLI 原生命令和工作流相关命令;owner 不受影响。',
1324
1469
  'botDefaults.quotaDefault': '默认消息额度',
1325
1470
  'botDefaults.quotaPlaceholder': '留空=不配置默认额度',
1326
- 'botDefaults.quotaHelp': '不带数字的 /grant @x 默认给的消息条数。留空或点「关闭」只是不再给裸 /grant 套默认额度,不会清掉已有的额度计数,也不影响显式 /grant @x N——它们照常继续 enforce。额度用尽会自动撤销该人授权。',
1471
+ 'botDefaults.quotaHelp': '设置裸 /grant @用户 的默认消息额度。留空保存=不再设置默认额度;已有额度和显式 /grant @用户 N 不受影响。额度用尽后自动撤销授权。',
1327
1472
  'botDefaults.quotaSave': '保存额度',
1328
- 'botDefaults.quotaOff': '关闭',
1329
1473
  'botDefaults.quotaInvalid': '额度必须是正整数',
1330
1474
  'botDefaults.quotaStateOff': '当前:未配置默认额度',
1331
1475
  'botDefaults.quotaStateOn': '当前:每人 {count} 条',
1332
- 'botDefaults.sectionSessionCap': '会话数上限',
1333
- 'botDefaults.maxLiveWorkers': '最大同时活跃会话数',
1476
+ 'botDefaults.sectionSessionCap': '会话常驻上限',
1477
+ 'botDefaults.maxLiveWorkers': '最大常驻会话数',
1334
1478
  'botDefaults.maxLiveWorkersPlaceholder': '留空=默认 30',
1335
- 'botDefaults.maxLiveWorkersHelp': ' Bot 同时保活的会话数上限,用于控制内存。超过后最久未用的会话自动休眠:worker CLI 进程一起杀掉、回收全部内存,下条消息时从磁盘 transcript 冷恢复(--resume 重建上下文,几秒,不再常驻占内存)。留空=用默认 30;填数字=本 Bot 自定义(想要更多就填大数字)。注意:休眠只对可恢复后端(tmux/herdr/zellij)生效,纯 PTY 会话不受影响;正在出答案的会话不会被打断。',
1479
+ 'botDefaults.maxLiveWorkersUsage': '常驻 {resident}/{cap} · 休眠 {dormant} · 总会话 {logical}',
1480
+ 'botDefaults.maxLiveWorkersHelp': '本 Bot 同时常驻内存的会话数上限。超过后最久未用的会话自动休眠:其后台进程和 CLI 一起退出、回收内存,但话题仍可继续;下条消息会从磁盘记录冷恢复上下文(通常几秒)。留空=默认 30;填数字=本 Bot 自定义。注意:正在出答案的会话不会被打断;只有可恢复的会话会自动休眠,接入外部终端或不可恢复的会话不受影响。',
1336
1481
  'botDefaults.maxLiveWorkersSave': '保存上限',
1337
1482
  'botDefaults.maxLiveWorkersOff': '恢复默认',
1338
1483
  'botDefaults.maxLiveWorkersInvalid': '上限必须是正整数',
1339
- 'botDefaults.maxLiveWorkersStateDefault': '当前:默认 30 个活跃会话',
1340
- 'botDefaults.maxLiveWorkersStateOn': '当前:最多 {count} 个活跃会话',
1484
+ 'botDefaults.maxLiveWorkersStateDefault': '当前:默认常驻 30 个会话',
1485
+ 'botDefaults.maxLiveWorkersStateOn': '当前:最多常驻 {count} 个会话',
1486
+ 'botDefaults.sectionRuntimeEnv': '启动环境',
1341
1487
  'botDefaults.sectionStartupCommands': '启动命令',
1342
- 'botDefaults.startupCommandsHelp': '开会话后、首条消息之前,自动按顺序发给 CLI 的命令(每条独立回车),如 /effort ultracode。逗号或换行分隔,每行一条,可带参数;留空=不发。下个新会话起效,且每次新会话(含 resume)都重放——所以 /effort ultracode 这类只对当前会话生效的设置不会因 resume 丢失。仅对原生 CLI 会话生效,adopt 接管的会话不发。',
1488
+ 'botDefaults.startupCommandsHelp': '新会话启动后、首条消息前自动发送的 CLI 命令。支持逗号或换行分隔;每次新会话和恢复都会重放。仅原生 CLI 会话生效。',
1343
1489
  'botDefaults.startupCommandsPlaceholder': '每行一条,如 /effort ultracode',
1344
1490
  'botDefaults.startupCommandsSave': '保存启动命令',
1345
1491
  'botDefaults.sectionLaunchShell': '启动 Shell',
1346
- 'botDefaults.launchShellHelp': '启动 CLI 用的 shell,覆盖 daemon $SHELL:填 shell 名(zsh|bash|sh)或绝对路径(如 /usr/bin/zsh)。用于登录 $SHELL(如 bash)的 rc 文件里有 `exec zsh` 之类跳转、把 CLI 启动命令顶掉、导致会话起不来(裸壳里报 parse error)的场景——指定 launchShell 直接用它启动、绕开被跳过的 rc。注意:PATH/nvm/pnpm 等要放进所选 shell 的 rc(如 .zshrc/.zprofile)。留空=回 $SHELL。下个新会话起效;仅 tmux/zellij 后端(pty 直接 exec CLI,本就不受影响)。',
1492
+ 'botDefaults.launchShellHelp': '指定启动 CLI 的 shell(如 zsh /usr/bin/zsh),覆盖 daemon 的 $SHELL。用于绕过登录 shell rc 中的跳转问题;PATH 等仍需在所选 shell 配置中可用。下个新会话生效。',
1347
1493
  'botDefaults.launchShellPlaceholder': '如 zsh 或 /usr/bin/zsh;留空=用 $SHELL',
1348
1494
  'botDefaults.launchShellSave': '保存启动 Shell',
1349
1495
  'botDefaults.sectionEnv': '环境变量',
1350
- 'botDefaults.envHelp': '注入到本 bot CLI 进程的环境变量(JSON 对象)。典型用途:让某个 bot GLM / 第三方 Anthropic·OpenAI 兼容服务商——填 ANTHROPIC_BASE_URL + ANTHROPIC_AUTH_TOKEN(GLM 国际站 https://api.z.ai/api/anthropic,国内站 https://open.bigmodel.cn/api/anthropic),或设 HTTPS_PROXY、CLI 专属开关。值仅接受字符串/数字/布尔;BOTMUX_ / LARK_APP_ botmux 保留键会被忽略。下个新会话起效,按会话注入到 CLI 进程(不进共享 tmux server 全局,不会串到别的 bot)。留空=清除。注意:值以明文存于 bots.json,不是密钥保险箱。',
1496
+ 'botDefaults.envHelp': ' JSON 为该 bot CLI 进程注入环境变量。支持字符串/数字/布尔;BOTMUX_LARK_APP_ 等保留键会被忽略。下个新会话生效,明文存储在 bots.json',
1351
1497
  'botDefaults.envPlaceholder': '{\n "ANTHROPIC_BASE_URL": "https://api.z.ai/api/anthropic",\n "ANTHROPIC_AUTH_TOKEN": "你的 GLM Coding Plan key"\n}',
1352
1498
  'botDefaults.envSave': '保存环境变量',
1353
1499
  'nav.roles': '角色管理',
1354
1500
  'nav.groupRoles': '群角色',
1355
1501
  'nav.roleProfiles': 'Profiles',
1356
1502
  'roles.title': '角色管理',
1357
- 'roles.subtitle': '管理每个群的 Bot 角色,并维护可复用的 Profiles。',
1358
1503
  'roleProfiles.title': 'Profiles',
1359
- 'roleProfiles.subtitle': '维护可复用的多 Bot Profiles,并快速预览或应用到目标群。',
1360
1504
  'roles.search': '搜索群名/Bot/ID',
1361
1505
  'roles.refresh': '刷新',
1362
1506
  'roles.selectHint': '← 展开群组,选择一个 Bot 来编辑角色',
@@ -1413,6 +1557,8 @@ const zh = {
1413
1557
  'workflow.subnav.runs': '运行',
1414
1558
  'workflow.subnav.catalog': '目录',
1415
1559
  'workflow.subnav.v3': '新版工作流 →',
1560
+ 'workflow.version.legacy': '旧版',
1561
+ 'workflow.version.v3': '新版',
1416
1562
  'workflow.searchPlaceholder': '搜索 runId / workflowId / chatId',
1417
1563
  'workflow.filter.nonTerminal': '非终态',
1418
1564
  'workflow.filter.all': '全部',
@@ -1542,7 +1688,6 @@ const zh = {
1542
1688
  'workflow.dangling.waits': 'Waits',
1543
1689
  'workflow.dangling.cancels': 'Cancels',
1544
1690
  'catalog.title': '工作流目录',
1545
- 'catalog.subtitle': '从已保存的 workflow 定义创建一次运行。',
1546
1691
  'catalog.searchPlaceholder': '搜索 workflowId / 路径',
1547
1692
  'catalog.refresh': '刷新',
1548
1693
  'catalog.loading': '正在加载目录...',
@@ -1592,17 +1737,20 @@ const en = {
1592
1737
  'time.secondsAgo': '{value}s ago',
1593
1738
  'time.minutesAgo': '{value}m ago',
1594
1739
  'time.hoursAgo': '{value}h ago',
1595
- 'nav.overview': 'Overview',
1596
- 'nav.monitoring': 'Monitor',
1597
- 'nav.sessions': 'Sessions',
1598
- 'nav.sidebarCollapse': 'Collapse sidebar',
1599
- 'nav.sidebarExpand': 'Expand sidebar',
1600
- 'nav.groups': 'Groups',
1601
- 'nav.schedules': 'Schedules',
1602
- 'nav.settings': 'Settings',
1603
- 'nav.botDefaults': 'Bot Defaults',
1604
- 'nav.skills': 'Skills',
1605
- 'status.live': 'Live',
1740
+ 'nav.overview': 'Workbench',
1741
+ 'nav.monitoring': 'Monitoring Board',
1742
+ 'nav.sessions': 'Session Control',
1743
+ 'nav.groups': 'Group Management',
1744
+ 'nav.schedules': 'Scheduled Tasks',
1745
+ 'nav.settings': 'Global Settings',
1746
+ 'nav.botDefaults': 'Bot Config',
1747
+ 'nav.skills': 'Skill Management',
1748
+ 'nav.whiteboards': 'Whiteboards',
1749
+ 'nav.team': 'Team Collaboration',
1750
+ 'nav.connectors': 'Webhook',
1751
+ 'nav.webhookLogs': 'Invocation Logs',
1752
+ 'nav.office': 'Office',
1753
+ 'status.live': 'Live link',
1606
1754
  'status.disconnected': 'Disconnected',
1607
1755
  'status.system': 'System',
1608
1756
  'status.light': 'Light',
@@ -1612,13 +1760,7 @@ const en = {
1612
1760
  'theme.base': 'Basic',
1613
1761
  'theme.skins': 'Skins',
1614
1762
  'skin.cyber': '2077',
1615
- 'skin.genshin': 'Genshin',
1616
1763
  'skin.fallout': 'Fallout',
1617
- 'skin.prts': 'PRTS',
1618
- 'skin.bluearchive': 'Blue Archive',
1619
- 'skin.zzz': 'ZZZ',
1620
- 'skin.dragonball': 'Dragon Ball',
1621
- 'skin.ikun': 'ikun',
1622
1764
  'botOnboarding.add': 'Add Bot',
1623
1765
  'botOnboarding.title': 'Add Bot',
1624
1766
  'botOnboarding.intro': 'Pick a CLI and working directory, scan to create a PersonalAgent app — the dashboard writes it to local bots.json and auto-configures Open Platform permissions.',
@@ -1662,16 +1804,16 @@ const en = {
1662
1804
  'botOnboarding.ownerInvalid': 'Owner validation failed. Please check and retry.',
1663
1805
  'botOnboarding.qrAlt': 'Feishu bot onboarding QR code',
1664
1806
  'overview.title': 'Workbench',
1665
- 'overview.subtitle': 'Live status of your AI teammates · synced with Feishu topics',
1666
1807
  'overview.team': 'AI Team',
1667
1808
  'overview.teamHint': 'Live status of every digital teammate',
1668
1809
  'overview.attention': 'Needs You',
1669
- 'overview.attentionHint': 'Blocked tasks — one reply gets them moving again',
1670
1810
  'overview.activeSessions': 'Active Sessions',
1671
- 'overview.activeSessionsHint': 'Sessions currently running',
1672
- 'overview.today': 'Right Now',
1673
- 'overview.todayHint': 'Active session distribution',
1811
+ 'overview.sessionOverview': 'Session Overview',
1674
1812
  'overview.viewAll': 'View all →',
1813
+ 'overview.viewAllPlain': 'View all',
1814
+ 'overview.sort': 'Sort',
1815
+ 'overview.sortByTime': 'By time',
1816
+ 'overview.sortAttentionFirst': 'Needs you first',
1675
1817
  'overview.botIdle': 'Standing by, ready for new tasks',
1676
1818
  'overview.botOffline': 'Offline — daemon not running',
1677
1819
  'overview.botBusy': 'Working · {count} sessions',
@@ -1680,14 +1822,15 @@ const en = {
1680
1822
  'overview.botOff': 'Offline',
1681
1823
  'overview.sessionsCount': '{count} sessions',
1682
1824
  'overview.lastActive': 'active {time} ago',
1683
- 'overview.noAttention': 'Nothing waiting on you',
1684
- 'overview.teamExpand': 'Show all {count} ▾',
1685
- 'overview.teamCollapse': 'Collapse',
1825
+ 'overview.teamCount': '{count} bots',
1826
+ 'overview.teamExpand': 'Show all',
1827
+ 'overview.teamCollapse': 'Collapse',
1686
1828
  'strip.pending': '{count} pending',
1687
- 'strip.longest': 'waiting {time} {bot} {reason}',
1829
+ 'strip.longestCompact': 'longest {time} · {bot} · {reason}',
1688
1830
  'strip.handle': 'Handle now',
1689
1831
  'overview.openSessions': 'Active Sessions',
1690
1832
  'overview.workingSessions': 'Working',
1833
+ 'overview.idleSessions': 'Idle',
1691
1834
  'overview.onlineBots': 'Online Bots',
1692
1835
  'overview.schedules': 'Schedules',
1693
1836
  'overview.groups': 'Groups Seen',
@@ -1697,13 +1840,13 @@ const en = {
1697
1840
  'overview.daemonRegistry': 'daemon registry',
1698
1841
  'overview.chatMatrix': 'chat matrix',
1699
1842
  'overview.recentSessions': 'Recent Sessions',
1700
- 'overview.nextSchedules': 'Next Runs',
1843
+ 'overview.nextSchedules': 'Schedules',
1701
1844
  'overview.noSessions': 'No sessions yet.',
1702
1845
  'overview.noSchedules': 'No schedules yet.',
1703
1846
  'monitoring.eyebrow': 'Runtime resources',
1704
- 'monitoring.title': 'Resource Monitor',
1847
+ 'monitoring.title': 'Monitoring Board',
1705
1848
  'monitoring.subtitle': 'Watch host, botmux, bot, and session CPU and memory pressure in real time.',
1706
- 'monitoring.runtimeTitle': 'Runtime Monitor',
1849
+ 'monitoring.runtimeTitle': 'Monitoring Board',
1707
1850
  'monitoring.runtimeSubtitle': 'Monitor botmux runtime health, resource pressure, and session pressure in real time.',
1708
1851
  'monitoring.runtimeHealth': 'Runtime Health',
1709
1852
  'monitoring.runtimeHealthHint': 'Check sample freshness, daemon availability, and session buildup.',
@@ -1770,6 +1913,7 @@ const en = {
1770
1913
  'monitoring.sessionsHint': 'Every live session has current values; only Top sessions keep trend history.',
1771
1914
  'monitoring.trackedSessionTrends': 'Top Session Trends',
1772
1915
  'monitoring.trackedSessionHint': 'This is the retained history subset, not the full current session set.',
1916
+ 'monitoring.modalClose': 'Close',
1773
1917
  'monitoring.noTrackedHistory': 'No Top session history yet.',
1774
1918
  'monitoring.noHotSession': 'No hot session',
1775
1919
  'monitoring.hottest': 'Hottest',
@@ -1789,7 +1933,6 @@ const en = {
1789
1933
  'monitoring.confidence': 'Confidence',
1790
1934
  'monitoring.rank': 'Rank reason',
1791
1935
  'sessions.title': 'Session Control',
1792
- 'sessions.subtitle': 'Locate Feishu topics, open Web Terminal, close or resume CLI sessions.',
1793
1936
  'sessions.search': 'Search chat / working dir / title / IDs',
1794
1937
  'sessions.anyStatus': 'Any status',
1795
1938
  'sessions.adoptAny': 'adopt: any',
@@ -1798,6 +1941,9 @@ const en = {
1798
1941
  'sessions.chatAny': 'Chat: all',
1799
1942
  'sessions.showUnknownChats': 'Show unknown chats',
1800
1943
  'sessions.activeOnly': 'Active only',
1944
+ 'sessions.runtime.logical': 'Open sessions',
1945
+ 'sessions.runtime.resident': 'Resident sessions',
1946
+ 'sessions.runtime.dormant': 'Dormant sessions',
1801
1947
  'sessions.monitorRoom': 'Monitor Room',
1802
1948
  'sessions.addToMonitorRoom': 'Add to monitor room',
1803
1949
  'sessions.monitorRoomAdded': 'Added {added}; total {total}',
@@ -1808,7 +1954,8 @@ const en = {
1808
1954
  'sessions.idleCleanupThreshold': 'Idle cleanup threshold',
1809
1955
  'sessions.idleCleanupRun': 'Clean idle',
1810
1956
  'sessions.idleCleanupCount': '{count} cleanable',
1811
- 'sessions.idleCleanupConfirm': 'Close {count} sessions idle for more than {threshold}?',
1957
+ 'sessions.idleCleanupCancel': 'Cancel',
1958
+ 'sessions.idleCleanupApply': 'Confirm',
1812
1959
  'sessions.idleCleanupRunning': 'Cleaning…',
1813
1960
  'sessions.idleCleanupDone': 'Closed {closed}, failed {failed}',
1814
1961
  'sessions.idleCleanupFailed': 'Cleanup failed',
@@ -1908,13 +2055,14 @@ const en = {
1908
2055
  'monitorRoom.terminalUnavailable': 'Terminal unavailable',
1909
2056
  'monitorRoom.terminalUnavailableHelp': 'The session may be closed, not started with a Web Terminal yet, or missing a reachable proxy port for this access mode.',
1910
2057
  'monitorRoom.updated': 'Updated {time}',
1911
- 'nav.insights': 'Insight',
1912
- 'insights.title': 'Workflow Insight',
1913
- 'insights.subtitle': 'Read-only analysis of local Claude Code / Codex sessions — action trace, failures, friction, with rule-based optimization tips.',
2058
+ 'nav.insights': 'Data Insights',
2059
+ 'insights.title': 'Data Insights',
1914
2060
  'insights.refresh': 'Refresh',
1915
2061
  'insights.search': 'Search session / bot / dir…',
1916
2062
  'insights.filter': 'Filter',
1917
2063
  'insights.filterAll': 'All',
2064
+ 'insights.filterAllSessions': 'All sessions',
2065
+ 'insights.filterAllCli': 'All CLI',
1918
2066
  'insights.filterReview': 'Worth review',
1919
2067
  'insights.filterFailed': 'Has failures',
1920
2068
  'insights.filterSlow': 'Has slow spans',
@@ -1945,7 +2093,7 @@ const en = {
1945
2093
  'insights.distTrendSub': 'sessions / day',
1946
2094
  'insights.distMedian': 'median {v}',
1947
2095
  'insights.distEmpty': 'No analyzable sessions under the current filter.',
1948
- 'insights.disclosure': 'Measurement note: durations count tool-execution time only and exclude time spent waiting for a user reply (question / plan approval), so they do not reflect wall-clock; Codex reads files mostly via shell (exec_command), not counted as "read", so its read/write ratio runs low or 0; code churn is parsed from patches and covers only each session\'s most active files. Cross-tool distributions and ratios are indicative only, not directly comparable.',
2096
+ 'insights.disclosure': 'Measurement note: durations count tool-execution time only and exclude time spent waiting for a user reply (question / plan approval), so they do not reflect wall-clock;\nCodex reads files mostly via shell (exec_command), not counted as "read", so its read/write ratio runs low or 0;\nCode churn is parsed from patches and covers only each session\'s most active files. Cross-tool distributions and ratios are indicative only, not directly comparable.',
1949
2097
  'insights.rwNote': 'Codex reads mostly via shell, not counted as reads',
1950
2098
  'insights.viewSessions': 'View sessions',
1951
2099
  'insights.hotHint': 'Cross-session recurrence — where it pays to converge.',
@@ -2196,8 +2344,8 @@ const en = {
2196
2344
  'insights.evidence.readWriteRatio': 'read/write ratio {ratio}',
2197
2345
  'insights.evidence.compactions': 'compactions {count}',
2198
2346
  'insights.evidence.spansAnalyzed': '{count} spans analyzed',
2199
- 'connectors.lede': 'Let external systems (alerts, CI, tickets…) trigger a bot to speak in a group or run a workflow via one webhook.',
2200
2347
  'connectors.createTitle': 'New Webhook',
2348
+ 'connectors.editTitle': 'Edit Webhook',
2201
2349
  'connectors.fName': 'Name',
2202
2350
  'connectors.fNamePh': 'e.g. Prod alerts',
2203
2351
  'connectors.fBot': 'Trigger bot',
@@ -2214,21 +2362,35 @@ const en = {
2214
2362
  'connectors.chatManualLink': 'Group not listed? Enter ID manually →',
2215
2363
  'connectors.chatListLink': '← Pick from group list',
2216
2364
  'connectors.fAllow': 'Allowed groups',
2365
+ 'connectors.allowAll': 'All groups',
2366
+ 'connectors.allowAllHint': 'Allow requests to target any group',
2367
+ 'connectors.groupPickerPlaceholder': 'Search and select a group',
2368
+ 'connectors.groupSearchPlaceholder': 'Search by group name or ID',
2369
+ 'connectors.groupNoMatches': 'No matching groups',
2370
+ 'connectors.groupSelectedCount': '{count} groups selected',
2217
2371
  'connectors.optional': ' (optional)',
2218
- 'connectors.allowHint': 'Hold Ctrl/⌘ to multi-select; empty = unrestricted. Only validates the chat passed in the request.',
2372
+ 'connectors.allowHint': 'Restricts which chats dynamic requests may target. All groups means unrestricted.',
2219
2373
  'connectors.dynamicHint': '<b>Dynamic mode</b>: the chat ID is passed per request, one of three ways — query <code>?chatId=&lt;chatId&gt;</code> · header <code>x-botmux-chat-id: &lt;chatId&gt;</code> · body <code>{"chatId":"&lt;chatId&gt;"}</code>.<br>For "one URL triggers directly, no params", choose Fixed group instead.',
2220
2374
  'connectors.fDedup': 'Dedup field',
2221
2375
  'connectors.fDedupPh': 'e.g. alert.id (read from event body)',
2222
- 'connectors.dedupHint': 'Set: events with the same value go to the <b>same group</b>. Empty: each event <b>creates a new group</b>.',
2376
+ 'connectors.dedupHint': 'Reads a business key from request JSON; supports alert.id or $.alert.id.',
2377
+ 'connectors.newGroupStrategy': 'Group creation strategy',
2378
+ 'connectors.newGroupFresh': 'Create a group for every call',
2379
+ 'connectors.newGroupFreshHint': 'Best for independent events that need no ongoing follow-up.',
2380
+ 'connectors.newGroupReuse': 'Reuse a group for the same event',
2381
+ 'connectors.newGroupReuseHint': 'Groups later calls by business key for continued follow-up.',
2382
+ 'connectors.newGroupNotice': 'This mode creates a group and invites the selected bot automatically. No existing group is required.',
2223
2383
  'connectors.fInstruction': 'Instruction',
2224
- 'connectors.fInstructionPh': 'What the bot should do on the event. e.g. Summarize the severity, @ the oncall, suggest next steps. Empty = hand the raw event to the model.',
2384
+ 'connectors.fInstructionPh': 'What the bot should do after the event. Empty passes the raw event to the model.',
2225
2385
  'connectors.fVerify': 'Verification',
2226
2386
  'connectors.verifyToken': 'Token (simple: secret in the URL, one curl triggers it)',
2227
2387
  'connectors.verifyHmac': 'HMAC signature (advanced: more secure, sign the request yourself)',
2228
2388
  'connectors.fSecret': 'Secret / token',
2229
2389
  'connectors.fSecretPh': 'Leave empty to auto-generate (shown once)',
2390
+ 'connectors.fSecretEditPh': 'Leave empty to keep the current secret; enter one to replace it',
2391
+ 'connectors.cancel': 'Cancel',
2392
+ 'connectors.close': 'Close',
2230
2393
  'connectors.btnCreate': 'Create',
2231
- 'connectors.listTitle': 'Existing Webhooks',
2232
2394
  'connectors.loading': 'Loading…',
2233
2395
  'connectors.noBotGroups': '(This bot has no visible groups; enter an ID manually on the right)',
2234
2396
  'connectors.modeLabelFixed': 'Fixed group',
@@ -2236,8 +2398,7 @@ const en = {
2236
2398
  'connectors.modeLabelDynamic': 'Per-request group',
2237
2399
  'connectors.kindLabelWorkflow': 'Workflow',
2238
2400
  'connectors.kindLabelTurn': 'Single turn',
2239
- 'connectors.count': '· {count}',
2240
- 'connectors.empty': 'No webhooks yet. Create one with the form above.',
2401
+ 'connectors.empty': 'No webhooks yet, create one from the upper-right button',
2241
2402
  'connectors.enabled': 'Enabled',
2242
2403
  'connectors.disabled': 'Disabled',
2243
2404
  'connectors.badgeToken': 'Token',
@@ -2260,8 +2421,13 @@ const en = {
2260
2421
  'connectors.errBot': 'Pick a bot',
2261
2422
  'connectors.errWf': 'Enter a workflow ID',
2262
2423
  'connectors.errChat': 'Pick (or enter) a target group',
2424
+ 'connectors.errDedup': 'Enter the business key used to reuse a group',
2263
2425
  'connectors.creating': 'Creating…',
2264
2426
  'connectors.saving': 'Saving…',
2427
+ 'connectors.updated': 'All settings saved',
2428
+ 'connectors.enabling': 'Enabling…',
2429
+ 'connectors.disabling': 'Disabling…',
2430
+ 'connectors.deleting': 'Deleting…',
2265
2431
  'connectors.usageDynamicLede': 'Dynamic mode: the URL already has the token; pass the target chat ID when calling{gn}:',
2266
2432
  'connectors.usageDynamicNote': 'The chat can also go in header <code>x-botmux-chat-id</code> or body <code>{"chatId":"…"}</code>. ⚠️ The URL is the credential — keep it secret.',
2267
2433
  'connectors.usageTokenLede': 'This URL already has the token and a fixed target group; just POST to trigger:',
@@ -2275,13 +2441,78 @@ const en = {
2275
2441
  'connectors.secretOnce': ' (shown once — save it): ',
2276
2442
  'connectors.createFailed': 'Create failed: {error}',
2277
2443
  'connectors.saveFailed': 'Save failed: {error}',
2444
+ 'connectors.toggleFailed': 'Status update failed: {error}',
2445
+ 'connectors.deleteFailed': 'Delete failed: {error}',
2278
2446
  'connectors.noOnlineBots': '(No online bots)',
2447
+ 'connectors.storePayload': 'Retain request parameters',
2448
+ 'connectors.storePayloadHint': 'Stores redacted JSON bodies and headers for 14 days by default. You can turn this off from the list.',
2449
+ 'connectors.payloadLogged': 'Parameters kept {days} days',
2450
+ 'connectors.metadataOnly': 'Invocation metadata only',
2451
+ 'connectors.btnDisablePayloadLog': 'Stop retaining parameters',
2452
+ 'connectors.btnEnablePayloadLog': 'Retain request parameters',
2453
+ 'connectors.tabWebhooks': 'Webhooks',
2454
+ 'connectors.tabLogs': 'Invocation logs',
2455
+ 'webhookLogs.subtitle': 'Review every invocation result, latency, request parameter, and resolved delivery target in one place.',
2456
+ 'webhookLogs.autoRefresh': 'Auto-refreshes every 15s',
2457
+ 'webhookLogs.manage': 'Manage webhooks',
2458
+ 'webhookLogs.summary': 'Invocation summary',
2459
+ 'webhookLogs.total': 'Total calls',
2460
+ 'webhookLogs.filteredRange': 'Current filter range',
2461
+ 'webhookLogs.successRate': 'Success rate',
2462
+ 'webhookLogs.calls': 'successful calls',
2463
+ 'webhookLogs.failures': 'Failed calls',
2464
+ 'webhookLogs.needsReview': 'Needs review',
2465
+ 'webhookLogs.noFailures': 'No failures in range',
2466
+ 'webhookLogs.p95': 'P95 latency',
2467
+ 'webhookLogs.average': 'Average',
2468
+ 'webhookLogs.allConnectors': 'All webhooks',
2469
+ 'webhookLogs.allStatuses': 'All results',
2470
+ 'webhookLogs.success': 'Success',
2471
+ 'webhookLogs.failed': 'Failed',
2472
+ 'webhookLogs.last24h': 'Last 24 hours',
2473
+ 'webhookLogs.last7d': 'Last 7 days',
2474
+ 'webhookLogs.last30d': 'Last 30 days',
2475
+ 'webhookLogs.allTime': 'All time',
2476
+ 'webhookLogs.search': 'Search invocation logs',
2477
+ 'webhookLogs.searchPlaceholder': 'Search Trigger ID, chat ID, errors, or parameters…',
2478
+ 'webhookLogs.connector': 'Webhook',
2479
+ 'webhookLogs.status': 'Result',
2480
+ 'webhookLogs.timeRange': 'Time range',
2481
+ 'webhookLogs.refresh': 'Refresh',
2482
+ 'webhookLogs.loadFailed': 'Failed to load invocation logs',
2483
+ 'webhookLogs.records': 'Invocation records',
2484
+ 'webhookLogs.matching': '{count} matches',
2485
+ 'webhookLogs.loading': 'Loading invocation logs…',
2486
+ 'webhookLogs.empty': 'No invocation records yet',
2487
+ 'webhookLogs.emptyHint': 'Records appear here automatically after any webhook call.',
2488
+ 'webhookLogs.unknownConnector': 'Unknown webhook',
2489
+ 'webhookLogs.loadMore': 'Load more',
2490
+ 'webhookLogs.selectRecord': 'Select a record to inspect its request',
2491
+ 'webhookLogs.copyJson': 'Copy full JSON',
2492
+ 'webhookLogs.copied': 'Copied',
2493
+ 'webhookLogs.failureReason': 'Failure reason',
2494
+ 'webhookLogs.overview': 'Invocation overview',
2495
+ 'webhookLogs.httpStatus': 'HTTP status',
2496
+ 'webhookLogs.duration': 'Duration',
2497
+ 'webhookLogs.action': 'Action',
2498
+ 'webhookLogs.bodySize': 'Body size',
2499
+ 'webhookLogs.remoteAddress': 'Remote address',
2500
+ 'webhookLogs.target': 'Delivery target',
2501
+ 'webhookLogs.queryParams': 'Query parameters',
2502
+ 'webhookLogs.headers': 'Request headers',
2503
+ 'webhookLogs.redacted': 'Sensitive values redacted',
2504
+ 'webhookLogs.headersNotStored': 'Request header retention is disabled for this webhook.',
2505
+ 'webhookLogs.payload': 'Request body',
2506
+ 'webhookLogs.payloadDisabled': 'Request body retention is disabled for this webhook; invocation metadata is still recorded.',
2507
+ 'webhookLogs.payloadTooLarge': 'The request body exceeded 128 KB and was omitted to keep logs bounded.',
2508
+ 'webhookLogs.payloadUnavailable': 'This invocation has no storable JSON request body.',
2509
+ 'webhookLogs.routeTarget': 'Routing parameters',
2510
+ 'webhookLogs.none': 'None',
2279
2511
  'team.navHome': 'My team',
2280
2512
  'team.navManage': 'Team management',
2281
- 'team.eyebrow': 'Team',
2282
- 'team.homeTitle': 'Team collaboration (cross-deployment)',
2283
- 'team.homeLede': 'Invite other deployments (botmux instances teammates run) into one team to discover bots across deployments and pull collaborative groups.',
2284
- 'team.localDeployTitle': 'This deployment',
2513
+ 'team.eyebrow': 'Team Collaboration',
2514
+ 'team.homeTitle': 'Team Collaboration',
2515
+ 'team.localDeployTitle': 'Current deployment',
2285
2516
  'team.myIdentity': 'My Lark identity: ',
2286
2517
  'team.unbound': 'Not bound',
2287
2518
  'team.bindBtn': 'Bind',
@@ -2296,17 +2527,20 @@ const en = {
2296
2527
  'team.roleModalTitle': 'Default role',
2297
2528
  'team.roleModalHint': 'The bot default persona (applies across groups), read-only here. To edit, go to the Bot Defaults page.',
2298
2529
  'team.close': 'Close',
2299
- 'team.tagLocal': 'This deployment',
2530
+ 'team.tagLocal': 'Current deployment',
2300
2531
  'team.tagRemoteStale': 'Remote · offline?',
2301
2532
  'team.tagRemote': 'Remote',
2302
2533
  'team.removeMember': 'Remove',
2303
2534
  'team.depTag': '({tag})',
2304
2535
  'team.depCount': '{count}',
2305
2536
  'team.depSelected': ', {n} selected',
2537
+ 'team.capLabel': 'Capability',
2306
2538
  'team.capPh': 'Capability tag…',
2307
2539
  'team.viewRole': 'View',
2308
2540
  'team.hasRoleShort': 'Has role',
2309
2541
  'team.noMatch': 'No bots match the filters.',
2542
+ 'team.gnameLabel': 'Group',
2543
+ 'team.gnamePlaceholder': 'e.g. cross-team triage',
2310
2544
  'team.gnamePh': 'Group name (e.g. cross-team triage)',
2311
2545
  'team.pullGroupBtn': 'Pull ticked bots into a group',
2312
2546
  'team.pullGroupHint': 'Tick bots → pull into a Lark group (owner included automatically)',
@@ -2325,7 +2559,7 @@ const en = {
2325
2559
  'team.invalidOwners': '{n} owner(s) could not be added',
2326
2560
  'team.missingIdentity': 'You have not bound a Lark identity, so you were not added to the group (bind it in My team)',
2327
2561
  'team.skippedNoOwner': '{n} bot(s) skipped because their owner has no bound identity (not added)',
2328
- 'team.errNoLocalBot': 'Tick at least one of your own (this deployment) online bots — the group is created by it and adds you (the initiator).',
2562
+ 'team.errNoLocalBot': 'Tick at least one of your own (current deployment) online bots — the group is created by it and adds you (the initiator).',
2329
2563
  'team.errAllSkipped': 'None of the selected bot owners have a bound identity, so the group cannot be pulled (a bot cannot join a group without its owner). Have those deployments bind an identity first.',
2330
2564
  'team.errNoCreator': 'No available group creator (the relevant deployments have no online bot, or are unreachable)',
2331
2565
  'team.errDelegationTimeout': 'Timed out delegating group creation to the other deployment (it may have succeeded — check Lark, do not retry)',
@@ -2335,7 +2569,6 @@ const en = {
2335
2569
  'team.myHostedTeam': 'My hosted team',
2336
2570
  'team.remoteTeamLabel': '{name} team',
2337
2571
  'team.manageTitle': 'Team management',
2338
- 'team.manageLede': 'Create multiple teams, generate an invite code per team, or join another team. A team = this deployment bots + the other deployments that joined it.',
2339
2572
  'team.hostedTitle': 'Teams I host',
2340
2573
  'team.newTeamPh': 'New team name',
2341
2574
  'team.createTeamBtn': 'Create team',
@@ -2427,6 +2660,7 @@ const en = {
2427
2660
  'sessions.create.columnBacklog': 'Backlog',
2428
2661
  'sessions.create.columnHelp': 'In progress: start immediately after the group is created. Backlog: create the group and add bots but do not start the CLI; drag to “In Progress” or hit “Start” later to send the content.',
2429
2662
  'sessions.create.advanced': 'More options',
2663
+ 'sessions.create.optionalConfig': 'Optional config',
2430
2664
  'sessions.create.groupName': 'Group name',
2431
2665
  'sessions.create.groupNamePlaceholder': 'Defaults to the first line of the content',
2432
2666
  'sessions.create.workingDir': 'Working directory',
@@ -2461,25 +2695,39 @@ const en = {
2461
2695
  'sessions.kanban.teamScope': '{chats} collab chats · {sessions} sessions',
2462
2696
  'sessions.kanban.remoteHint': 'Session from the {name} deployment (snapshot; terminal/history live on their machine)',
2463
2697
  'sessions.kanban.clusterDragHint': 'Drag header to move the whole group',
2698
+ 'sessions.kanban.clusterExpand': 'Expand grouped sessions',
2699
+ 'sessions.kanban.clusterCollapse': 'Collapse grouped sessions',
2464
2700
  'sessions.history.title': 'History',
2465
2701
  'sessions.history.loading': 'Fetching Feishu messages…',
2466
2702
  'sessions.history.fail': 'Failed to load history',
2467
2703
  'sessions.history.empty': 'No messages',
2468
2704
  'sessions.history.user': 'User',
2705
+ 'sessions.history.bot': 'Bot',
2706
+ 'sessions.history.system': 'System',
2469
2707
  'sessions.history.owner': 'Owner',
2470
2708
  'sessions.history.staleHint': 'The dashboard or daemon process may still run an old build — botmux restart and retry',
2471
- 'groups.title': 'Groups & Bots',
2472
- 'groups.subtitle': 'Inspect the chat x bot matrix and manage group creation, oncall, leave, and disband flows.',
2709
+ 'groups.title': 'Group Management',
2710
+ 'groups.matrixTitle': 'Group Matrix',
2473
2711
  'groups.search': 'Search chat name / ID / owner',
2474
2712
  'groups.missingOnly': 'Missing bot only',
2475
2713
  'groups.refresh': 'Refresh',
2476
- 'groups.create': 'New Group',
2714
+ 'groups.create': 'New Chat',
2477
2715
  'groups.chat': 'Chat',
2478
2716
  'groups.actions': 'Actions',
2479
2717
  'groups.addBots': 'Add Bots',
2480
- 'groups.saveAsProfile': 'Save as Profile',
2718
+ 'groups.saveAsProfile': 'Save Profile',
2481
2719
  'groups.manage': 'Manage',
2482
2720
  'groups.empty': 'No chats match the filters.',
2721
+ 'groups.paginationLabel': 'Group list pagination',
2722
+ 'groups.pageStatus': 'Showing {from}-{to}/{total} · Page {page}/{pages}',
2723
+ 'groups.prevPage': 'Previous',
2724
+ 'groups.nextPage': 'Next',
2725
+ 'groups.botCoverage': 'Bot coverage',
2726
+ 'groups.memberSummary': 'In chat {count}/{total}',
2727
+ 'groups.botStatusIn': 'In chat',
2728
+ 'groups.botStatusOut': 'Missing',
2729
+ 'groups.botStatusError': 'Error',
2730
+ 'groups.botStatusUnknown': 'Unknown',
2483
2731
  'groups.profileStatusFull': 'Fully matches {name} ({matched}/{total})',
2484
2732
  'groups.profileStatusFullChat': 'Group roles fully match {name} ({matched}/{total})',
2485
2733
  'groups.profileStatusPartial': 'Partially matches {name} ({matched}/{total})',
@@ -2511,6 +2759,7 @@ const en = {
2511
2759
  'groups.saveProfileOverwriteSubmit': 'Overwrite Save',
2512
2760
  'groups.saveProfileInvalid': 'Profile id may contain letters, numbers, dots, underscores, and hyphens only; max 64; cannot be . or ..',
2513
2761
  'groups.saveProfileNoRoles': 'This chat has no bot configs to save.',
2762
+ 'groups.saveProfilePreparing': 'Loading config…',
2514
2763
  'groups.saveProfileSaving': 'Saving…',
2515
2764
  'groups.saveProfileDone': 'Saved {count} entries into {name}',
2516
2765
  'groups.saveProfileFailed': 'Saved only {saved}/{total} entries. Check offline bots or permissions.',
@@ -2527,7 +2776,8 @@ const en = {
2527
2776
  'groups.roleProfileBootstrapDone': 'Profile: {name}; bootstrap completed with no peer bootstrap message needed.',
2528
2777
  'groups.roleProfileBootstrapFailed': 'Profile: {name}; bootstrap failed: {reason}',
2529
2778
  'groups.botPicker': 'Bots',
2530
- 'groups.createSubmit': 'Create',
2779
+ 'groups.createSubmit': 'Create Chat',
2780
+ 'groups.createSubmitting': 'Creating…',
2531
2781
  'groups.cancel': 'Cancel',
2532
2782
  'groups.successTitle': 'Group Created',
2533
2783
  'groups.openGroup': 'Open Group',
@@ -2542,8 +2792,7 @@ const en = {
2542
2792
  'groups.save': 'Save',
2543
2793
  'groups.needWorkingDir': 'Working directory is required',
2544
2794
  'groups.noBotsOnline': 'No bots online. Restart the daemon first.',
2545
- 'schedules.title': 'Schedules',
2546
- 'schedules.subtitle': 'View, pause, resume, and run scheduled tasks across daemons.',
2795
+ 'schedules.title': 'Scheduled Tasks',
2547
2796
  'schedules.search': 'Search name / prompt / working dir',
2548
2797
  'schedules.anyKind': 'Any kind',
2549
2798
  'schedules.enabledOnly': 'Enabled only',
@@ -2554,8 +2803,14 @@ const en = {
2554
2803
  'schedules.last': 'Last',
2555
2804
  'schedules.repeat': 'Repeat',
2556
2805
  'schedules.enabled': 'Enabled',
2806
+ 'schedules.paused': 'Paused',
2557
2807
  'schedules.actions': 'Actions',
2558
2808
  'schedules.runNow': 'Run Now',
2809
+ 'schedules.running': 'Running',
2810
+ 'schedules.runDone': 'Done',
2811
+ 'schedules.saving': 'Saving',
2812
+ 'schedules.saved': 'Saved',
2813
+ 'schedules.failed': 'Failed',
2559
2814
  'schedules.pause': 'Pause',
2560
2815
  'schedules.resume': 'Resume',
2561
2816
  'schedules.delivery': 'Delivery',
@@ -2566,49 +2821,56 @@ const en = {
2566
2821
  'schedules.useOrigin': 'Switch to original',
2567
2822
  'schedules.empty': 'No schedules.',
2568
2823
  'settings.title': 'Global Settings',
2569
- 'settings.subtitle': 'Manage machine-wide botmux dashboard behavior shared by every bot.',
2570
2824
  'settings.loading': 'Loading settings…',
2571
2825
  'settings.loadFailed': 'Failed to load settings',
2572
2826
  'settings.readOnlyVisitor': 'Read-only access — changing settings requires an authorized link (run botmux dashboard).',
2573
2827
  'settings.sectionAccess': 'Access',
2574
2828
  'settings.publicReadOnly': 'Allow tokenless read-only dashboard access',
2575
- 'settings.publicReadOnlyHelp': 'When enabled, visitors without a token can view the dashboard, sessions, schedules, and SSE. Writes such as close, pause, and approvals still require token auth. Sensitive raw terminal logs always require a token.',
2829
+ 'settings.publicReadOnlyHelp': 'Allows tokenless read-only dashboard access. Writes such as close, approve, or pause still require a token; raw terminal logs always require one.',
2576
2830
  'settings.remoteAccess': 'Remote terminal access',
2577
- 'settings.remoteAccessHelp': 'When enabled, session web terminals, Feishu card "Open Web Terminal" / "Get writable link" buttons, and webhooks all use central-platform links; when off, local links are used. Off by default.',
2831
+ 'settings.remoteAccessHelp': 'Off by default. Uses central-platform links for terminals, Feishu terminal entries, and webhooks. Off uses local links.',
2578
2832
  'settings.sectionCards': 'Feishu Cards',
2579
2833
  'settings.openTerminalInFeishu': 'Open streaming-card Web terminals in the Feishu sidebar',
2580
- 'settings.openTerminalInFeishuHelp': 'Off by default: terminal buttons open the Web Terminal URL directly. When enabled, botmux wraps the URL with Feishu web_url/open so Feishu PC opens it in a sidebar. Terminal write access is still controlled by its token.',
2834
+ 'settings.openTerminalInFeishuHelp': 'Off by default. Wraps Web Terminal links so Feishu opens them in the sidebar. Write access is still controlled by the terminal token.',
2581
2835
  'settings.sectionExperimental': 'Experimental',
2582
2836
  'settings.chatBotDiscovery': 'In-chat bot discovery (Feishu /members/bots)',
2583
- 'settings.chatBotDiscoveryHelp': 'When enabled, botmux reads the current chat\'s bot members in real time via Feishu /members/bots so multiple bots can reliably @-mention each other — it works from the very first message, with no need to accumulate past @ history, making multi-bot collaboration more robust. This is a non-public Feishu endpoint: it is on by default and automatically falls back to legacy discovery (per-bot probing + observed @ history) on failure. Turn it off (forcing the legacy path) only if your tenant/gateway does not support the endpoint, if it returns inaccurate membership that causes wrong or missing @-mentions, or if a Feishu change breaks its behaviour.',
2837
+ 'settings.chatBotDiscoveryHelp': 'On by default. Reads bot members in the current chat to improve multi-bot @ accuracy. Falls back to legacy discovery on failure; disable only if membership detection is wrong.',
2584
2838
  'settings.sectionVcMeetingAgent': 'Meeting Listener',
2585
2839
  'settings.vcMeetingAgent': 'Allow meeting listener features on this machine',
2586
- 'settings.vcMeetingAgentHelp': 'On by default. When off, bots on this host ignore new meeting invites/events and skip restoring meeting listeners from runtime state. Meetings already running are not force-closed and usually finish naturally; restart daemons to hard-stop them.',
2840
+ 'settings.vcMeetingAgentHelp': 'On by default. Controls whether bots on this host accept new meeting listener events. Off also skips listener restore; running meetings usually finish naturally.',
2587
2841
  'settings.vcMeetingListenerBot': 'Meeting listener bot identity',
2588
2842
  'settings.vcMeetingListenerBotAuto': 'Follow each bot config',
2589
- 'settings.vcMeetingListenerBotHelp': 'When set, only this bot app accepts new meeting listener events. Saving first validates that the bot has a lark-cli profile and required VC meeting scopes, then enables meeting listener config. Event subscription publication cannot be checked by API.',
2843
+ 'settings.vcMeetingListenerBotHelp': 'Chooses the bot that receives meeting events. Saving validates its lark-cli profile and meeting scopes, then enables the listener.',
2590
2844
  'settings.vcMeetingListenerBotDisabled': 'auto-enable on save',
2591
2845
  'settings.vcMeetingListenerBotNoProfile': 'profile required first',
2846
+ 'settings.larkCliReady': 'lark-cli {version} · version requirement met',
2847
+ 'settings.larkCliOutdated': 'lark-cli {version} is too old; VC bot joining requires ≥ {minimum}',
2848
+ 'settings.larkCliMissing': 'lark-cli was not detected; install it before using VC bot joining',
2849
+ 'settings.feishuLoginRequired': 'Log in to the Feishu Open Platform to configure VC permissions automatically, then scan this QR code.',
2850
+ 'settings.feishuLoginQrAlt': 'Feishu Open Platform login QR code',
2851
+ 'settings.feishuLoginClose': 'Close login QR code',
2592
2852
  'settings.sectionRepoPicker': 'Repo Picker',
2593
2853
  'settings.repoPickerMode': 'Repo picker card mode',
2594
2854
  'settings.repoPickerModeAll': 'Repos + worktrees',
2595
2855
  'settings.repoPickerModeRepos': 'Main repos only',
2596
- 'settings.repoPickerModeHelp': 'Default shows repositories and linked worktrees. Main repos only hides linked worktrees from initialization and bare /repo cards; explicit /repo /abs/path/to/worktree still works.',
2856
+ 'settings.repoPickerModeHelp': 'Controls whether repo picker cards show linked worktrees. Explicit /repo paths can still open a worktree.',
2597
2857
  'settings.sectionWhiteboard': 'Local Whiteboard',
2598
2858
  'settings.whiteboardEnable': 'Enable project whiteboards',
2599
- 'settings.whiteboardEnableHelp': 'Off by default. Enabling only turns the capability on — nothing is created immediately; whiteboards are ensured lazily per chat + project on first use.',
2859
+ 'settings.whiteboardEnableHelp': 'Off by default. Enables whiteboard support. Nothing is created until a chat and project first need it.',
2600
2860
  'settings.saving': 'Saving…',
2601
2861
  'settings.saved': 'Saved',
2602
2862
  'settings.saveFailed': 'Save failed',
2603
2863
  'settings.sectionSchedule': 'Scheduled tasks',
2604
2864
  'settings.scheduleTimeZone': 'Timezone',
2605
- 'settings.scheduleTimeZoneHelp': 'Timezone used to fire and display scheduled tasks (IANA name, e.g. Asia/Shanghai). Leave empty to follow the host zone (current host: {host}). Effective: {effective}.',
2865
+ 'settings.scheduleTimeZoneHost': 'Follow host ({host})',
2866
+ 'settings.scheduleTimeZoneHelp': 'Timezone for scheduled-task firing and display. Empty follows host zone ({host}); effective: {effective}.',
2606
2867
  'settings.sectionMaintenance': 'Auto Maintenance',
2607
2868
  'settings.autoUpdate': 'Auto update',
2608
- 'settings.autoUpdateHelp': 'Off by default. At the set time, runs npm install -g botmux@latest to install the latest version (download/install only no restart). npm-global installs only.',
2869
+ 'settings.autoUpdateHelp': 'Off by default. Updates the global install with its owning package manager (npm/pnpm). It updates the package only; no restart.',
2609
2870
  'settings.autoRestart': 'Auto restart',
2610
- 'settings.autoRestartHelp': 'Off by default; requires auto-update. After auto-update installs a newer version, restart to apply it if no session is in progress (busy slips to the next day).',
2871
+ 'settings.autoRestartHelp': 'Off by default and requires auto-update. After update, restarts during an idle window; busy sessions defer to the next window.',
2611
2872
  'settings.autoUpdateLocalDev': 'This is a local-dev install (running from source); auto-update is unavailable.',
2873
+ 'settings.autoUpdateUnsupportedInstall': 'This install method cannot be auto-updated yet (npm/pnpm global installs are supported).',
2612
2874
  'settings.maintenanceTime': 'Time',
2613
2875
  'update.section': 'Version & Update',
2614
2876
  'update.loginRequired': 'Sign in to check the version, update, or restart.',
@@ -2620,8 +2882,11 @@ const en = {
2620
2882
  'update.checkUnavailable': "Couldn't fetch the latest version (offline or network-restricted)",
2621
2883
  'update.nodeWarn': 'Node {version} is too old; update requires ≥ {required}. Please upgrade Node first.',
2622
2884
  'update.localDev': 'This is a local-dev install (running from source); "Update to latest" is unavailable — use git pull + build, then restart.',
2623
- 'update.multiInstallWarn': 'Multiple botmux installs detected. npm only updates the npm-global one, which may not be the active version:',
2885
+ 'update.multiInstallWarn': 'Multiple botmux installs detected. This update only changes the package-manager location that owns the running install:',
2624
2886
  'update.kindNpm': 'npm-global',
2887
+ 'update.kindPnpm': 'pnpm-global',
2888
+ 'update.kindYarn': 'Yarn global (update unsupported)',
2889
+ 'update.kindBun': 'Bun global (update unsupported)',
2625
2890
  'update.kindSource': 'source checkout',
2626
2891
  'update.kindUnknown': 'unknown',
2627
2892
  'update.btnCheck': 'Check for updates',
@@ -2635,11 +2900,12 @@ const en = {
2635
2900
  'update.changelogRateLimited': 'GitHub API rate limit hit (60 req/h per IP unauthenticated, easily tripped on shared networks). Try again later.',
2636
2901
  'update.changelogViewOnGitHub': 'View on GitHub Releases',
2637
2902
  'update.navBadgeTitle': 'New version {version} available',
2638
- 'update.confirmMultiInstall': 'Multiple botmux installs detected:\n{paths}\n\nnpm only updates the npm-global one, which may not be the active version. Continue anyway?',
2639
- 'update.confirmUpdate': 'This will run npm install -g botmux@latest to update to {version}. Continue?',
2640
- 'update.confirmUpdateNoVer': 'This will run npm install -g botmux@latest to update to the latest version. Continue?',
2903
+ 'update.confirmMultiInstall': 'Multiple botmux installs detected:\n{paths}\n\nOnly the running install location will be updated. Continue anyway?',
2904
+ 'update.confirmUpdate': 'This will run {command} to update to {version}. Continue?',
2905
+ 'update.confirmUpdateNoVer': 'This will run {command} to update to the latest version. Continue?',
2641
2906
  'update.nodeTooOldAlert': 'Node {version} is too old (requires ≥ {required}). Please upgrade Node before updating.',
2642
- 'update.updating': 'Updating (npm install -g botmux@latest)…',
2907
+ 'update.updating': 'Updating ({command})…',
2908
+ 'update.unsupportedInstall': 'This install cannot be auto-updated safely. Only npm/pnpm global installs are supported; update manually with the owning package manager.',
2643
2909
  'update.updatedChanged': 'Updated {old} → {new}.',
2644
2910
  'update.confirmRestart': 'A restart is required to apply the new version. Restart now? (Sessions cold-resume; the dashboard briefly disconnects and reconnects.)',
2645
2911
  'update.alreadyLatestRun': 'Already on the latest version ({version}); nothing to update.',
@@ -2650,27 +2916,32 @@ const en = {
2650
2916
  'update.restartSlow': 'Restart is taking a while; please refresh the page manually.',
2651
2917
  'update.restartFailed': 'Restart failed: {detail}',
2652
2918
  'skills.title': 'Skill Management',
2653
- 'skills.subtitle': 'Manage CLI-neutral botmux Skill assets and choose priority disclosure per bot.',
2654
2919
  'skills.installed': 'Installed Skills',
2655
- 'skills.installedHelp': 'Skill assets in the local registry that bots can disclose first.',
2656
- 'skills.overviewTitle': 'Organize Skill assets by bot',
2657
- 'skills.overviewBody': 'Global Skill delivery settings control session injection; each bot only manages its priority disclosure list.',
2920
+ 'skills.installedHelp': 'Skills in the local registry that bots can disclose first.',
2658
2921
  'skills.metricInstalled': 'Installed Skills',
2659
2922
  'skills.metricBots': 'Configured Bots',
2660
2923
  'skills.metricAttached': 'Priority refs',
2661
2924
  'skills.install': 'Install Skill',
2662
2925
  'skills.installInfoLabel': 'Install location details',
2663
- 'skills.installInfo': 'Registry: ~/.botmux/skills/registry.json\nInstall: ~/.botmux/skills/store/skill-name; Git cache: ~/.botmux/skills/sources\nIsolation: Codex/Claude global directories are not modified; local CLI Skills are referenced in place',
2926
+ 'skills.installInfo': 'Registry metadata is stored in ~/.botmux/skills/registry.json; installed content lives under ~/.botmux/skills/store. Local CLI Skills are referenced in place and do not modify CLI global directories.',
2664
2927
  'skills.source': 'Import Address',
2665
- 'skills.sourcePlaceholder': 'Paste a GitHub repo, Git URL, or local Skill directory',
2928
+ 'skills.sourcePlaceholder': 'Paste a GitHub repo, Git URL, agentbuddy install command, or local Skill directory',
2666
2929
  'skills.sourceHelpRemoteLabel': 'GitHub / Git: ',
2667
2930
  'skills.sourceHelpRemote': 'Paste a repository root URL. Repositories with multiple Skills can be selected after clicking Install.',
2668
2931
  'skills.sourceHelpLocalLabel': 'Local CLI Skill directory: ',
2669
2932
  'skills.sourceHelpLocal': 'Referenced in place without copying into the botmux store.',
2933
+ 'skills.sourceHelpAgentbuddyLabel': 'AgentBuddy: ',
2934
+ 'skills.sourceHelpAgentbuddy': 'Paste an agentbuddy install command, e.g. agentbuddy skill collection add <uid> / agentbuddy plugin collection add <uid>; the open-source skills CLI form skills add owner/repo also works (via GitHub install). agentbuddy commands need the deploy host logged in via agentbuddy login.',
2935
+ 'skills.agentbuddyNotFound': 'agentbuddy CLI not found on the deploy host. Install it globally there, or set BOTMUX_AGENTBUDDY_CMD.',
2936
+ 'skills.agentbuddyNeedsLogin': 'agentbuddy on the deploy host is not logged in. Run agentbuddy login there and retry.',
2937
+ 'skills.agentbuddyCommandFailed': 'agentbuddy install failed — check the deploy-host logs.',
2938
+ 'skills.agentbuddyTelemetryFailed': 'Embedded-telemetry removal failed; install aborted (set BOTMUX_AGENTBUDDY_KEEP_TELEMETRY=1 to keep it).',
2939
+ 'skills.agentbuddyNoSkill': 'agentbuddy produced no Skill — check the identifier.',
2940
+ 'skills.agentbuddyInvalid': 'Invalid agentbuddy identifier format.',
2670
2941
  'skills.discover': 'Discover Skills',
2671
2942
  'skills.localDiscover': 'Browse Local Skills',
2672
2943
  'skills.localDiscoverTitle': 'Local CLI Skills',
2673
- 'skills.localDiscoverHelp': 'Register Skills already installed in local CLI directories such as Codex or Claude.',
2944
+ 'skills.localDiscoverHelp': 'Scans locally installed CLI Skills and registers them as local references.',
2674
2945
  'skills.scan': 'Scan',
2675
2946
  'skills.scanning': 'Scanning',
2676
2947
  'skills.scanFound': 'Found {count} Skills',
@@ -2678,7 +2949,7 @@ const en = {
2678
2949
  'skills.sourceRequired': 'Enter an import address first.',
2679
2950
  'skills.advanced': 'Advanced Options',
2680
2951
  'skills.discoverTitle': 'Discover Local CLI Skills',
2681
- 'skills.discoverHelp': 'Scan CLI Skill directories used by bots configured in this deployment. Selected Skills are registered as local links without copying files.',
2952
+ 'skills.discoverHelp': 'Scans Skill directories used by configured bots. Selected Skills are registered as local links without copying files.',
2682
2953
  'skills.discoverEmpty': 'No registerable Skills were found in local CLI skill directories.',
2683
2954
  'skills.discoverGroupEmpty': 'No registerable Skills were found in this CLI directory.',
2684
2955
  'skills.discoverRegistered': 'Registered',
@@ -2704,7 +2975,7 @@ const en = {
2704
2975
  'skills.installSubmit': 'Install',
2705
2976
  'skills.installSelected': 'Install Selected',
2706
2977
  'skills.installSelectionTitle': 'Select Skills to Install',
2707
- 'skills.installSelectionHelp': 'Found {count} Skills in this source. All are selected by default; clear anything you do not need before installing.',
2978
+ 'skills.installSelectionHelp': 'Found {count} Skills. Clear items you do not need before installing.',
2708
2979
  'skills.installSelectionCancel': 'Cancel',
2709
2980
  'skills.update': 'Update',
2710
2981
  'skills.remove': 'Remove',
@@ -2721,10 +2992,8 @@ const en = {
2721
2992
  'skills.globalProjectAllHelp': 'Read .agents/skills and\n.botmux/skills',
2722
2993
  'skills.globalDelivery': 'Skill Delivery',
2723
2994
  'skills.bots': 'Bot Skill Settings',
2724
- 'skills.botsHelp': 'Choose the Skills each bot should disclose first.',
2995
+ 'skills.botsHelp': 'Choose priority Skills for each bot to disclose first.',
2725
2996
  'skills.botCount': '{count} Bots',
2726
- 'skills.scrollBotsPrev': 'Scroll bots left',
2727
- 'skills.scrollBotsNext': 'Scroll bots right',
2728
2997
  'skills.skillCount': '{count} Skills',
2729
2998
  'skills.attach': 'Add to priority',
2730
2999
  'skills.detach': 'Remove',
@@ -2745,20 +3014,31 @@ const en = {
2745
3014
  'skills.projectAllHelp': 'This bot includes workspace skill candidates',
2746
3015
  'skills.priority': 'Priority skills',
2747
3016
  'skills.noPriority': 'Not configured, keeping CLI default behavior',
3017
+ 'skills.pickerPlaceholder': 'Select priority Skills',
3018
+ 'skills.pickerSelectedCount': '{count} Skills selected',
3019
+ 'skills.pickerTriggerHint': 'Click to search or edit the selection',
3020
+ 'skills.pickerSearchPlaceholder': 'Search Skill names or descriptions',
3021
+ 'skills.pickerSelectionMeta': '{selected} selected · {total} total',
3022
+ 'skills.pickerClear': 'Clear',
3023
+ 'skills.pickerNoResults': 'No matching Skills',
3024
+ 'skills.saveSelection': 'Save selection',
3025
+ 'skills.cancel': 'Cancel',
3026
+ 'skills.saving': 'Saving…',
3027
+ 'skills.policySaved': 'Priority Skills saved',
2748
3028
  'skills.dangling': 'Not installed',
2749
3029
  'skills.removeInUse': 'Skill "{skill}" is still referenced by: {refs}. Removing it deletes the registry package but does not automatically clean references. Continue?',
2750
3030
  'skills.saved': 'Saved',
2751
3031
  'skills.failed': 'Failed',
2752
3032
  'skills.jobRunning': 'Working...',
2753
3033
  'skills.refresh': 'Refresh',
2754
- 'botDefaults.title': 'Bot Profiles',
2755
- 'botDefaults.subtitle': 'Per-bot defaults: oncall, proactive start, persona role, cards and grants.',
3034
+ 'botDefaults.title': 'Bot Config',
2756
3035
  'botDefaults.metaOnline': 'Online · daemon healthy',
2757
3036
  'botDefaults.search': 'Search bot name / app id',
2758
3037
  'botDefaults.refresh': 'Refresh',
2759
3038
  'botDefaults.sectionOncall': 'New-chat Oncall',
2760
3039
  'botDefaults.sectionBrand': 'Card Signature',
2761
3040
  'botDefaults.renameTitle': 'Rename bot',
3041
+ 'botDefaults.renameAction': 'Rename',
2762
3042
  'botDefaults.renameSave': 'Save',
2763
3043
  'botDefaults.renameCancel': 'Cancel',
2764
3044
  'botDefaults.renameEmpty': 'Name cannot be empty',
@@ -2783,7 +3063,7 @@ const en = {
2783
3063
  'botDefaults.agentCli': 'CLI',
2784
3064
  'botDefaults.agentModel': 'Model',
2785
3065
  'botDefaults.agentModelPlaceholder': 'Leave empty for the CLI default model',
2786
- 'botDefaults.agentHelp': 'Changes affect only newly created sessions. Existing sessions keep the CLI / model they were created with; close and start again to use the new configuration.',
3066
+ 'botDefaults.agentHelp': 'Affects new sessions only. Existing sessions keep their original CLI / model until closed and started again.',
2787
3067
  'botDefaults.agentSave': 'Save CLI / Model',
2788
3068
  'botDefaults.skillInjection': 'botmux skills injection',
2789
3069
  'botDefaults.skillInjectionDynamic': 'Dynamic (--plugin-dir, per session)',
@@ -2791,8 +3071,8 @@ const en = {
2791
3071
  'botDefaults.skillInjectionPrompt': 'prompt — into session prompt, no global dir',
2792
3072
  'botDefaults.skillInjectionGlobal': 'global — install into CLI global skills dir',
2793
3073
  'botDefaults.skillInjectionOff': 'off — only a botmux --help pointer',
2794
- 'botDefaults.skillInjectionHelpDynamic': 'This CLI (claude-family) injects botmux skills per session via --plugin-dir: session-scoped, nothing written to a global dir, set up and torn down each session — nothing to configure.',
2795
- 'botDefaults.skillInjectionHelp': 'How this bot\'s botmux built-in skills reach CLIs with a global skills dir (codex/gemini/…). Default prompt: inject the skill catalog into the session prompt (once at session start, not repeated each turn), full text on demand via `botmux skill show`, nothing written to ~/.codex/skills etc., so your own standalone CLI never sees them; global: install into the CLI global dir (native, but standalone CLI sees them too); off: routing hints + `botmux --help` only. Applies to the next session; switching to/from global needs a daemon restart to fully apply.',
3074
+ 'botDefaults.skillInjectionHelpDynamic': 'This CLI supports --plugin-dir injection. Skills are session-scoped, not written to global directories, and need no extra setup.',
3075
+ 'botDefaults.skillInjectionHelp': 'Choose how botmux skills are delivered: prompt is the default and injects them at session start without touching global dirs; global installs into the CLI global skills dir; off keeps only the botmux --help pointer. Applies next session; switching global requires a daemon restart.',
2796
3076
  'botDefaults.agentSaved': 'Saved (takes effect next session)',
2797
3077
  'botDefaults.warning': 'When enabled, chats without an oncall binding auto-bind to this directory on their next new topic. Manually bound or unbound chats are preserved.',
2798
3078
  'botDefaults.empty': 'No bots online. Run botmux restart first.',
@@ -2809,16 +3089,16 @@ const en = {
2809
3089
  'botDefaults.workingDirModeOff': 'Off (new sessions show the repo picker)',
2810
3090
  'botDefaults.workingDirModeDefault': 'Default directory only (no permission change)',
2811
3091
  'botDefaults.workingDirModeOncall': 'Oncall mode (open chat to the whole group)',
2812
- 'botDefaults.workingDirModeHelp': 'Where this bot starts new sessions, pick one (mutually exclusive): "Off" = no pinned dir, new sessions show the repo picker; "Default directory only" = every new session (incl. DMs / topics) starts in this dir and skips the picker, with no permission change (private bots); "Oncall mode" = same dir for all sessions PLUS newly-seen group chats auto-bind to oncall (anyone in the group can talk to the bot; write actions like buttons/commands still require allowedUsers), for on-call / support. Takes effect next session; running sessions need /restart.',
3092
+ 'botDefaults.workingDirModeHelp': 'Sets where new sessions start: Off shows the repo picker; Default directory starts there without permission changes; Oncall adds automatic group chat access on top. Applies next session.',
2813
3093
  'botDefaults.autoWorktree': 'Auto-create a worktree per new session',
2814
- 'botDefaults.autoWorktreeHelp': 'Only for "Default directory only" mode: before a new session starts, auto-create an isolated git worktree in the default directory (must be a git repo) off the remote default branch, and run the session inside it so concurrent sessions don\'t collide. Covers interactive new topics/DMs, dashboard-created sessions and webhook events (not workflows). If the default dir isn\'t a git repo or creation fails, it falls back to starting directly in the default dir and posts a notice. Worktrees are NOT auto-removed on /close.',
3094
+ 'botDefaults.autoWorktreeHelp': 'Only for Default directory mode. Creates an isolated git worktree per new session to avoid collisions; falls back to the default dir on failure. /close does not remove worktrees.',
2815
3095
  'botDefaults.workingDirSaved': 'Saved (takes effect next session)',
2816
3096
  'botDefaults.brandLabel': 'Signature (card footer)',
2817
- 'botDefaults.brandLabelHelp': 'Footer signature on cards this bot sends. Save empty = hide; fill in = custom (markdown ok, e.g. [Acme](https://…)); Reset = show botmux.',
3097
+ 'botDefaults.brandLabelHelp': 'Footer signature for cards sent by this bot. Empty hides it; custom text supports Markdown; reset shows botmux.',
2818
3098
  'botDefaults.brandLabelPlaceholder': 'Default: botmux (empty = hidden)',
2819
3099
  'botDefaults.sectionSandbox': 'File sandbox (oncall)',
2820
3100
  'botDefaults.sandboxToggle': 'Enable file sandbox',
2821
- 'botDefaults.sandboxHelp': "When on, every session of this bot runs in a per-session sandbox: only a project copy is visible — your real files, secrets, and other sessions are not. For sharing the bot with semi-trusted users (oncall). Linux only; applies to the next new session.",
3101
+ 'botDefaults.sandboxHelp': "Runs new sessions in an isolated project copy so real files, secrets, and other sessions are not directly visible. Linux only; intended for oncall sharing.",
2822
3102
  'botDefaults.sandboxSaved': 'Saved (applies to the next new session)',
2823
3103
  'botDefaults.brandSave': 'Save Signature',
2824
3104
  'botDefaults.brandReset': 'Reset to default',
@@ -2827,67 +3107,66 @@ const en = {
2827
3107
  'botDefaults.brandStateCustom': 'Current: custom',
2828
3108
  'botDefaults.sectionCard': 'Card Behavior',
2829
3109
  'botDefaults.disableStreaming': 'Disable streaming card',
2830
- 'botDefaults.disableStreamingHelp': 'Stop posting the live session status card (and its Open Web Terminal entry). The task\'s final result still arrives as a message. For those who find the live card noisy.',
3110
+ 'botDefaults.disableStreamingHelp': 'Disables the live session card and Web Terminal entry. Final results are still sent as messages.',
2831
3111
  'botDefaults.silentTurnReactions': 'Disable status reactions in card-off mode',
2832
- 'botDefaults.silentTurnReactionsHelp': 'With the streaming card off, botmux marks the triggering message with lightweight ✋→✅ reactions ("received / done"). Check this to drop those too — handy for low-noise observer bots. Editable only while "Disable streaming card" is on.',
3112
+ 'botDefaults.silentTurnReactionsHelp': 'When streaming cards are off, botmux can mark received/done with reactions. Enable this to suppress those reactions too.',
2833
3113
  'botDefaults.writableLink': 'Put a writable terminal link on the card',
2834
- 'botDefaults.writableLinkHelp': '⚠️ Embeds a writable terminal link in the streaming card body — anyone in the chat can open and drive the terminal. Off = current behavior (private DM via the "Get Write Link" button).',
3114
+ 'botDefaults.writableLinkHelp': 'Shows a writable terminal link in the streaming card. Anyone in the chat can operate it, so use only in trusted groups.',
2835
3115
  'botDefaults.writableLinkMoot': 'Streaming card disabled — this has no effect',
2836
3116
  'botDefaults.privateCard': '/card sends a private card (authorized users only)',
2837
- 'botDefaults.privateCardHelp': 'Makes /card send an ephemeral "visible-to-specific-people" card: delivered only to the owner (allowedUsers); /grant-authorized talk users and everyone else in the chat cannot see it. Trade-off: it is a static snapshot (no live updates) and only works in regular group chats (topic groups / DMs fail, with no fallback). Affects only the /card command; the auto streaming card is unchanged.',
3117
+ 'botDefaults.privateCardHelp': '/card is visible only to owner/allowedUsers. It is a static snapshot, works only in regular groups, and does not affect automatic streaming cards.',
2838
3118
  'botDefaults.sectionCrossBot': 'Cross-bot',
2839
3119
  'botDefaults.botToBotSameDir': 'bot@bot same-directory launch',
2840
- 'botDefaults.botToBotSameDirHelp': 'When ON, if this bot is @-ed into a chat/thread where another bot is already working, it reuses that bot\'s working directory and skips the repo-selection card (independent of oncall; default ON). When OFF, this bot always falls through to its own repo card / default dir.',
3120
+ 'botDefaults.botToBotSameDirHelp': 'On by default. When this bot is @-ed into a chat where another bot is already working, reuse that bot\'s directory and skip repo selection. Off uses this bot\'s own directory rules.',
2841
3121
  'botDefaults.cardPrefSaved': 'Saved',
2842
3122
  'botDefaults.sectionSummaryTrigger': '/summary Range',
2843
3123
  'botDefaults.summaryLimit': 'Recent message count',
2844
3124
  'botDefaults.summarySinceHours': 'Recent hours',
2845
- 'botDefaults.summaryLimitHelp': 'When the user mentions the bot and sends /summary, this range is read. Defaults to latest 50 messages / 24 hours. Set either value to 0 to remove that limit. Topic groups always read the current topic history.',
3125
+ 'botDefaults.summaryLimitHelp': 'History range read by /summary. Default is latest 50 messages or 24 hours; set either value to 0 to remove that limit. Topic groups read only the current topic.',
2846
3126
  'botDefaults.summarySave': 'Save summary range',
2847
3127
  'botDefaults.summaryNumberInvalid': 'Hours and message count must be 0 or a positive integer',
2848
3128
  'botDefaults.sectionRole': 'Default Role',
2849
- 'botDefaults.roleHelp': 'This bot\'s default persona (applies across all chats), injected into the bot\'s sessions in every chat; a single group can override it on the Roles page. Save empty = delete.',
3129
+ 'botDefaults.roleHelp': 'Default role injected into this bot\'s sessions. Individual chats can override it in Role Management. Saving empty deletes it.',
2850
3130
  'botDefaults.rolePlaceholder': 'e.g. You are a backend triage assistant; answer concisely, prefer runnable commands…',
2851
3131
  'botDefaults.roleSave': 'Save role',
2852
- 'botDefaults.roleDelete': 'Delete',
2853
3132
  'botDefaults.roleSaved': 'Saved',
2854
3133
  'botDefaults.roleDeleted': 'Deleted',
2855
3134
  'botDefaults.roleLoadErr': 'Failed to load role',
2856
3135
  'botDefaults.profileRoles': 'Profile Roles',
2857
- 'botDefaults.profileRolesHelp': 'Role entries this bot has in Profiles. Collapsed by default; expand a profile to load details.',
3136
+ 'botDefaults.profileRolesHelp': 'Role entries for this bot in Profiles. Expand a profile to load details.',
2858
3137
  'botDefaults.profileRolesEmpty': 'This bot has no profile roles.',
2859
3138
  'botDefaults.profileRolesLoadFailed': 'Failed to load profile roles: {error}',
2860
3139
  'botDefaults.profileRoleClickToLoad': 'Expand to load role details.',
2861
3140
  'botDefaults.profileRoleDetailLoadFailed': 'Failed to load role detail: {error}',
2862
3141
  'botDefaults.sectionAutoStart': 'Proactive Start',
2863
3142
  'botDefaults.autoStartJoin': 'Auto-start when added to a new chat',
2864
- 'botDefaults.autoStartJoinHelp': 'When enabled, the bot auto-starts a session and gets to work the moment it is added to a new chat (when an authorized user / allowedUsers is a member), no @ needed. It launches in the bot default working dir; if none is configured it shows a repo-select card first. Prerequisite: subscribe the "bot joined chat" event im.chat.member.bot.added_v1 for this app and grant the member-read scope in the Feishu console.',
3143
+ 'botDefaults.autoStartJoinHelp': 'Starts a session when the bot joins a new chat that contains an authorized user, without requiring @. Uses the default directory or shows repo selection. Requires the bot-joined event and member-read scope.',
2865
3144
  'botDefaults.autoStartJoinPrompt': 'First-turn prompt on join (optional)',
2866
3145
  'botDefaults.autoStartJoinPromptPlaceholder': 'Filled = used as the first task after joining; blank = the bot reads the chat and decides what to do',
2867
3146
  'botDefaults.autoStartJoinPromptSave': 'Save prompt',
2868
3147
  'botDefaults.autoStartTopic': 'Auto-start on new topics in topic groups',
2869
- 'botDefaults.autoStartTopicHelp': 'When enabled, in a topic group the bot automatically joins each newly opened topic and starts working on its first message, no @ needed. Topic groups only — regular groups are unaffected.',
3148
+ 'botDefaults.autoStartTopicHelp': 'In topic groups, automatically joins each new topic and handles its first message without @. Regular groups are unaffected.',
2870
3149
  'botDefaults.sectionSessionMode': 'Session mode',
2871
3150
  'botDefaults.p2pMode': 'Private chat session mode',
2872
3151
  'botDefaults.p2pThread': 'thread (separate session per DM)',
2873
3152
  'botDefaults.p2pChat': 'chat (flat continuous session)',
2874
- 'botDefaults.p2pHelp': 'How 1:1 DMs are sessioned: thread = each top-level message starts its own session (keeps chatter out of one CLI process); chat = the whole DM shares one continuous session and context (Hermes-like). Takes effect immediately.',
3153
+ 'botDefaults.p2pHelp': 'Private chat session mode: thread creates one session per top-level message; chat shares one continuous session. Applies immediately.',
2875
3154
  'botDefaults.regularGroupMode': 'Regular group session mode',
2876
3155
  'botDefaults.regularGroupModeChat': 'chat (flat continuous session, default)',
2877
3156
  'botDefaults.regularGroupModeChatTopic': 'chat-topic (flat continuous at top level, native topics each get their own session)',
2878
3157
  'botDefaults.regularGroupModeNewTopic': 'new-topic (each top-level @ opens its own topic & session)',
2879
3158
  'botDefaults.regularGroupModeShared': 'shared (topic display, reusing one session)',
2880
- 'botDefaults.regularGroupModeHelp': 'How new top-level @mentions in regular (non-topic) groups are sessioned: chat = the whole group shares one continuous session (default, even a native Lark topic you open folds into it); chat-topic = top-level @ still stays flat in the one group session, but each native Lark topic you open runs its own independent session (a new session per topic); new-topic = each top-level @ opens its own topic with a separate session; shared = topic display but reuse the same session (replies fold into a topic yet share the group session & context). This is the per-bot default; a specific group can override it via /reply-mode. Takes effect immediately.',
3159
+ 'botDefaults.regularGroupModeHelp': 'Regular group mode for top-level @mentions: chat = one continuous group session; chat-topic = native topics get separate sessions; new-topic = each @ opens a topic and session; shared = topic UI with shared session. Chat-level /reply-mode can override it.',
2881
3160
  'botDefaults.mentionMode': 'Group @ policy',
2882
3161
  'botDefaults.mentionModeAlways': 'Always require @ (default)',
2883
3162
  'botDefaults.mentionModeTopic': 'No @ needed inside topics',
2884
3163
  'botDefaults.mentionModeNever': 'Never require @',
2885
3164
  'botDefaults.mentionModeAmbient': 'No @ needed, but yields when you @ someone else',
2886
- 'botDefaults.mentionModeHelp': 'Bot-global: controls when an @ is required to get a reply in groups. "Always require @" = every message needs an @ (default, safest; inside topics too, in multi-person groups); "No @ needed inside topics" = starting a new conversation / top-level still needs @, but follow-ups inside ANY topic this bot already drives (new-topic / shared / topic-group) continue without @; "Never require @" = non-@ messages are always answered wherever the bot has talk access (including cold-starting on a brand-new message) — for dedicated / on-call small groups; "No @ needed, but yields when you @ someone else" = same no-@ answering, EXCEPT when your message @mentions another person or bot (and not this one), in which case it backs off, treating it as handed to someone else (@all does not count, so it still replies) — best for multi-bot / multi-person groups that want a default responder which yields the moment you address someone else. Note: when you are alone with this bot (1:1) replies never need an @, independent of this setting.',
3165
+ 'botDefaults.mentionModeHelp': 'Controls whether group messages must @ the bot. Options allow @ only, topic follow-ups without @, all messages without @, or yielding when the message @mentions someone else. Private chats never require @.',
2887
3166
  'botDefaults.docSubscribeMode': 'Doc subscription trigger (default)',
2888
3167
  'botDefaults.docSubscribeModeMention': 'Only when a comment @s me',
2889
3168
  'botDefaults.docSubscribeModeAll': 'Every new comment',
2890
- 'botDefaults.docSubscribeModeHelp': 'After subscribing to a Feishu doc with /subscribe-lark-doc, its comments feed into the session and the bot replies back into the comment. This sets the default trigger range for new subscriptions: "only when a comment @s me" is safest (avoids noise); "every new comment" suits dedicated docs.',
3169
+ 'botDefaults.docSubscribeModeHelp': 'Default trigger range for new document subscriptions. @mentions only is quieter; every comment is suitable for dedicated docs.',
2891
3170
  'botDefaults.sectionSubstitute': 'Substitute mode',
2892
3171
  'botDefaults.substituteEnabled': 'Enable substitute trigger',
2893
3172
  'botDefaults.substituteHelp': 'In regular groups, when a configured substitute target is @mentioned, this bot answers on their behalf. The sender still needs canTalk. Recommended with Oncall mode so group members can naturally @ the substitute target. Use /substitute off to disable it for a specific group.',
@@ -2895,8 +3174,19 @@ const en = {
2895
3174
  'botDefaults.substituteDisclosurePrefix': 'Default: say I am answering for them',
2896
3175
  'botDefaults.substituteDisclosureNone': 'No extra disclosure',
2897
3176
  'botDefaults.substituteTargetsPlaceholder': 'alice@example.com\nou_xxxx (open_id / union_id also accepted)',
2898
- 'botDefaults.substituteTargetsHelp': 'One substitute target per line. Email is easiest (resolved to an open_id with the person\'s name on save); you may also paste an ou_ open_id or on_ union_id. Email resolution is bounded by this bot\'s contact visibility — anything that can\'t resolve is flagged in red.',
2899
- 'botDefaults.substituteTargetsInvalid': 'These lines are not recognized (use an email / ou_ / on_; a bare name can\'t resolve)',
3177
+ 'botDefaults.substituteTargets': 'Substitute targets',
3178
+ 'botDefaults.substituteTargetsHelp': 'Each row is one substitute target. Enter an email to resolve it to an Open ID on save, or select Open ID, User ID, or Union ID. Emails that cannot be resolved are flagged.',
3179
+ 'botDefaults.substituteTargetType': 'Identifier type',
3180
+ 'botDefaults.substituteTargetEmail': 'Email',
3181
+ 'botDefaults.substituteTargetOpenId': 'Open ID',
3182
+ 'botDefaults.substituteTargetUserId': 'User ID',
3183
+ 'botDefaults.substituteTargetUnionId': 'Union ID',
3184
+ 'botDefaults.substituteTargetIdPlaceholder': 'Enter a Lark user identifier or email',
3185
+ 'botDefaults.substituteTargetName': 'Display name',
3186
+ 'botDefaults.substituteTargetNamePlaceholder': 'Display name (optional)',
3187
+ 'botDefaults.substituteTargetAdd': 'Add substitute target',
3188
+ 'botDefaults.substituteTargetRemove': 'Remove substitute target',
3189
+ 'botDefaults.substituteTargetsInvalid': 'Add at least one valid substitute target before enabling; emails must resolve to an Open ID',
2900
3190
  'botDefaults.substituteTargetsRequired': 'Enabling the substitute trigger needs at least one target that resolves to an open_id',
2901
3191
  'botDefaults.substituteResolving': 'Resolving…',
2902
3192
  'botDefaults.substituteUnresolved': 'unresolved',
@@ -2904,45 +3194,44 @@ const en = {
2904
3194
  'botDefaults.substituteOff': 'Turn off global substitute config',
2905
3195
  'botDefaults.sectionGrant': 'Authorization & Quota',
2906
3196
  'botDefaults.autoGrantCard': 'Auto grant card for blocked @mentions',
2907
- 'botDefaults.autoGrantCardHelp': 'When enabled, if a person or external bot explicitly @mentions this bot in a group but the talk gate blocks it, BotMux sends a /grant request card to the owner. When disabled, the gate still blocks but stays silent.',
3197
+ 'botDefaults.autoGrantCardHelp': 'When an unauthorized user or external bot @mentions this bot, send a /grant request card to the owner. Off still blocks, but silently.',
2908
3198
  'botDefaults.restrictGrant': 'Restrict grantees to plain conversation',
2909
- 'botDefaults.restrictGrantHelp': 'When enabled, /grant-authorized users (the owner is exempt) can only send plain messages; every slash command is blocked: botmux built-in commands, passthrough commands, /workflow, /template, /introduce, /t, and CLI-native commands (/help, etc.). Text like /path/to/file is not misclassified.',
3199
+ 'botDefaults.restrictGrantHelp': 'Restricts /grant users to plain conversation. Botmux commands, passthrough commands, CLI-native commands, and workflow commands are blocked; the owner is exempt.',
2910
3200
  'botDefaults.quotaDefault': 'Default message quota',
2911
3201
  'botDefaults.quotaPlaceholder': 'Empty = no default quota',
2912
- 'botDefaults.quotaHelp': 'Message count a bare /grant @x (no number) hands out. Empty or "Turn off" merely stops applying a default to bare /grant — it does NOT clear existing quota counters, nor affect an explicit /grant @x N; those keep being enforced. Authorization is auto-revoked once a quota runs out.',
3202
+ 'botDefaults.quotaHelp': 'Default quota for bare /grant @user. Saving empty stops assigning a default; existing quotas and explicit /grant @user N are unchanged. Authorization is revoked when quota runs out.',
2913
3203
  'botDefaults.quotaSave': 'Save quota',
2914
- 'botDefaults.quotaOff': 'Turn off',
2915
3204
  'botDefaults.quotaInvalid': 'Quota must be a positive integer',
2916
3205
  'botDefaults.quotaStateOff': 'Current: no default quota',
2917
3206
  'botDefaults.quotaStateOn': 'Current: {count} per grantee',
2918
- 'botDefaults.sectionSessionCap': 'Session limit',
2919
- 'botDefaults.maxLiveWorkers': 'Max live sessions',
3207
+ 'botDefaults.sectionSessionCap': 'Resident session limit',
3208
+ 'botDefaults.maxLiveWorkers': 'Max resident sessions',
2920
3209
  'botDefaults.maxLiveWorkersPlaceholder': 'Empty = default 30',
2921
- 'botDefaults.maxLiveWorkersHelp': 'Cap on this bot\'s simultaneously-live sessions, to bound memory. Beyond it, the least-recently-used sessions are suspended: both the worker AND the CLI process are killed to reclaim all their memory, and the session cold-resumes from its on-disk transcript on the next message (--resume rebuilds context in a few seconds — nothing stays resident). Empty = use the default of 30; a number = a per-bot override (set a larger number if you want more). Note: suspension only applies to resumable backends (tmux/herdr/zellij), never plain PTY; a session that is mid-reply is never interrupted.',
3210
+ 'botDefaults.maxLiveWorkersUsage': 'Resident {resident}/{cap} · dormant {dormant} · total {logical}',
3211
+ 'botDefaults.maxLiveWorkersHelp': 'Maximum sessions this bot keeps resident in memory. Beyond it, the least-recently-used session is suspended: its background process and CLI exit to reclaim memory, while the conversation remains resumable. The next message cold-restores context from disk, usually within a few seconds. Empty = default 30; enter a number for a per-bot override. A session producing an answer is never interrupted; adopted external terminals and non-resumable sessions are exempt.',
2922
3212
  'botDefaults.maxLiveWorkersSave': 'Save limit',
2923
3213
  'botDefaults.maxLiveWorkersOff': 'Reset to default',
2924
3214
  'botDefaults.maxLiveWorkersInvalid': 'Limit must be a positive integer',
2925
- 'botDefaults.maxLiveWorkersStateDefault': 'Current: default 30 live sessions',
2926
- 'botDefaults.maxLiveWorkersStateOn': 'Current: up to {count} live sessions',
3215
+ 'botDefaults.maxLiveWorkersStateDefault': 'Current: 30 resident sessions by default',
3216
+ 'botDefaults.maxLiveWorkersStateOn': 'Current: up to {count} resident sessions',
3217
+ 'botDefaults.sectionRuntimeEnv': 'Startup environment',
2927
3218
  'botDefaults.sectionStartupCommands': 'Startup commands',
2928
- 'botDefaults.startupCommandsHelp': 'Commands auto-sent to the CLI in order after launch, before the first message (each its own Enter), e.g. /effort ultracode. Comma- or newline-separated, one per line, arguments allowed; empty = none. Takes effect from the next session, and replays on every new session (incl. resume) — so session-only settings like /effort ultracode survive a resume. Native CLI sessions only; adopted sessions are not driven.',
3219
+ 'botDefaults.startupCommandsHelp': 'CLI commands sent automatically after launch and before the first message. Use commas or new lines; replayed on every new or resumed session. Native CLI sessions only.',
2929
3220
  'botDefaults.startupCommandsPlaceholder': 'One per line, e.g. /effort ultracode',
2930
3221
  'botDefaults.startupCommandsSave': 'Save startup commands',
2931
3222
  'botDefaults.sectionLaunchShell': 'Launch shell',
2932
- 'botDefaults.launchShellHelp': 'Shell used to launch the CLI, overriding the daemon $SHELL: a shell name (zsh|bash|sh) or an absolute path (e.g. /usr/bin/zsh). For when the login $SHELL (e.g. bash) has an rcfile that `exec`-trampolines into another shell (`exec zsh`), pre-empting the CLI launch so the session never starts (bare-shell `parse error`) pinning launchShell launches under it directly, bypassing the skipped rcfile. Note: PATH/nvm/pnpm must then live in the chosen shell’s rcfiles (e.g. .zshrc/.zprofile). Empty = use $SHELL. Takes effect next session; tmux/zellij backends only (pty execs the CLI directly and is unaffected).',
3223
+ 'botDefaults.launchShellHelp': 'Shell used to launch the CLI, such as zsh or /usr/bin/zsh, overriding the daemon $SHELL. Use it to avoid login-shell rc redirection issues; PATH must still be available in that shell. Applies next session.',
2933
3224
  'botDefaults.launchShellPlaceholder': 'e.g. zsh or /usr/bin/zsh; empty = $SHELL',
2934
3225
  'botDefaults.launchShellSave': 'Save launch shell',
2935
3226
  'botDefaults.sectionEnv': 'Environment variables',
2936
- 'botDefaults.envHelp': 'Environment variables injected into THIS bot\'s CLI process (a JSON object). Typical use: run a bot on GLM / a third-party Anthropic·OpenAI-compatible provider — set ANTHROPIC_BASE_URL + ANTHROPIC_AUTH_TOKEN (GLM: https://api.z.ai/api/anthropic, or https://open.bigmodel.cn/api/anthropic in China), or set HTTPS_PROXY / a CLI feature flag. Values accept string/number/boolean only; botmux-reserved keys (BOTMUX_, LARK_APP_, …) are ignored. Takes effect from the next session, injected per-session into the CLI process (never into the shared tmux server env, so it can\'t leak across bots). Empty = clear. Note: values live in bots.json in plaintext — not a secret vault.',
3227
+ 'botDefaults.envHelp': 'JSON environment variables injected into this bot\'s CLI process. Values may be string, number, or boolean; reserved BOTMUX_ / LARK_APP_ keys are ignored. Applies next session and is stored in plaintext in bots.json.',
2937
3228
  'botDefaults.envPlaceholder': '{\n "ANTHROPIC_BASE_URL": "https://api.z.ai/api/anthropic",\n "ANTHROPIC_AUTH_TOKEN": "your GLM Coding Plan key"\n}',
2938
3229
  'botDefaults.envSave': 'Save environment variables',
2939
3230
  'nav.roles': 'Role Management',
2940
3231
  'nav.groupRoles': 'Group Roles',
2941
3232
  'nav.roleProfiles': 'Profiles',
2942
3233
  'roles.title': 'Role Management',
2943
- 'roles.subtitle': 'Manage per-group bot roles and reusable Profiles.',
2944
3234
  'roleProfiles.title': 'Profiles',
2945
- 'roleProfiles.subtitle': 'Maintain reusable multi-bot Profiles, then preview or apply them to target groups.',
2946
3235
  'roles.search': 'Search group / bot / ID',
2947
3236
  'roles.refresh': 'Refresh',
2948
3237
  'roles.selectHint': '← Expand a group and select a bot to edit its role',
@@ -2999,6 +3288,8 @@ const en = {
2999
3288
  'workflow.subnav.runs': 'Runs',
3000
3289
  'workflow.subnav.catalog': 'Catalog',
3001
3290
  'workflow.subnav.v3': 'New workflow →',
3291
+ 'workflow.version.legacy': 'Legacy',
3292
+ 'workflow.version.v3': 'New',
3002
3293
  'workflow.searchPlaceholder': 'search runId / workflowId / chatId',
3003
3294
  'workflow.filter.nonTerminal': 'non-terminal',
3004
3295
  'workflow.filter.all': 'all',
@@ -3128,7 +3419,6 @@ const en = {
3128
3419
  'workflow.dangling.waits': 'waits',
3129
3420
  'workflow.dangling.cancels': 'cancels',
3130
3421
  'catalog.title': 'Workflow catalog',
3131
- 'catalog.subtitle': 'Create a workflow run from a saved workflow definition.',
3132
3422
  'catalog.searchPlaceholder': 'search workflowId / path',
3133
3423
  'catalog.refresh': 'Refresh',
3134
3424
  'catalog.loading': 'Loading catalog...',