@poolzin/pool-bot 2026.2.24 → 2026.2.26

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 (646) hide show
  1. package/CHANGELOG.md +21 -0
  2. package/dist/acp/client.js +207 -18
  3. package/dist/acp/event-mapper.js +87 -22
  4. package/dist/acp/meta.js +12 -6
  5. package/dist/acp/secret-file.js +22 -0
  6. package/dist/agents/agent-paths.js +8 -9
  7. package/dist/agents/agent-scope.js +17 -5
  8. package/dist/agents/auth-profiles/oauth.js +148 -64
  9. package/dist/agents/auth-profiles/session-override.js +13 -7
  10. package/dist/agents/bash-process-registry.test-helpers.js +29 -0
  11. package/dist/agents/bash-tools.exec-approval-request.js +20 -0
  12. package/dist/agents/bash-tools.exec-host-gateway.js +240 -0
  13. package/dist/agents/bash-tools.exec-host-node.js +235 -0
  14. package/dist/agents/bash-tools.exec-runtime.js +2 -25
  15. package/dist/agents/bash-tools.exec-types.js +1 -0
  16. package/dist/agents/bash-tools.process.js +224 -218
  17. package/dist/agents/bedrock-discovery.js +3 -1
  18. package/dist/agents/byteplus-models.js +97 -0
  19. package/dist/agents/chutes-oauth.js +1 -0
  20. package/dist/agents/cli-runner/helpers.js +4 -0
  21. package/dist/agents/compaction.js +41 -14
  22. package/dist/agents/content-blocks.js +16 -0
  23. package/dist/agents/doubao-models.js +121 -0
  24. package/dist/agents/failover-error.js +2 -0
  25. package/dist/agents/huggingface-models.js +5 -3
  26. package/dist/agents/live-model-filter.js +5 -0
  27. package/dist/agents/minimax-vlm.js +10 -8
  28. package/dist/agents/model-auth.js +6 -0
  29. package/dist/agents/model-catalog.js +3 -1
  30. package/dist/agents/model-fallback.js +96 -101
  31. package/dist/agents/model-selection.js +7 -1
  32. package/dist/agents/models-config.providers.js +364 -165
  33. package/dist/agents/ollama-stream.js +117 -4
  34. package/dist/agents/opencode-zen-models.js +22 -11
  35. package/dist/agents/pi-embedded-helpers/errors.js +55 -33
  36. package/dist/agents/pi-embedded-helpers/messaging-dedupe.js +10 -5
  37. package/dist/agents/pi-embedded-helpers/thinking.js +10 -5
  38. package/dist/agents/pi-embedded-helpers.js +1 -1
  39. package/dist/agents/pi-embedded-payloads.js +1 -0
  40. package/dist/agents/pi-embedded-runner/compact.js +29 -7
  41. package/dist/agents/pi-embedded-runner/extensions.js +28 -26
  42. package/dist/agents/pi-embedded-runner/google.js +20 -8
  43. package/dist/agents/pi-embedded-runner/run/attempt.js +95 -36
  44. package/dist/agents/pi-embedded-runner/run.js +71 -12
  45. package/dist/agents/pi-embedded-runner/run.overflow-compaction.fixture.js +34 -0
  46. package/dist/agents/pi-embedded-runner/run.overflow-compaction.mocks.shared.js +11 -2
  47. package/dist/agents/pi-embedded-runner/session-manager-cache.js +11 -7
  48. package/dist/agents/pi-embedded-runner/system-prompt.js +2 -0
  49. package/dist/agents/pi-embedded-runner/thinking.js +42 -0
  50. package/dist/agents/pi-embedded-runner/tool-name-allowlist.js +19 -0
  51. package/dist/agents/pi-embedded-runner/utils.js +7 -10
  52. package/dist/agents/pi-embedded-subscribe.handlers.lifecycle.js +45 -56
  53. package/dist/agents/pi-embedded-subscribe.handlers.tools.js +2 -2
  54. package/dist/agents/pi-embedded-subscribe.js +9 -4
  55. package/dist/agents/pi-embedded-subscribe.tools.js +68 -14
  56. package/dist/agents/pi-embedded-utils.js +3 -0
  57. package/dist/agents/pi-extensions/compaction-safeguard-runtime.js +4 -20
  58. package/dist/agents/pi-extensions/compaction-safeguard.js +75 -33
  59. package/dist/agents/pi-settings.js +40 -0
  60. package/dist/agents/pi-tools.policy.js +2 -1
  61. package/dist/agents/provider/config-loader.js +1 -1
  62. package/dist/agents/sandbox/browser.js +170 -33
  63. package/dist/agents/sandbox/config-hash.js +14 -27
  64. package/dist/agents/sandbox/config.js +21 -2
  65. package/dist/agents/sandbox/constants.js +2 -0
  66. package/dist/agents/sandbox/docker.js +16 -2
  67. package/dist/agents/sandbox/novnc-auth.js +62 -0
  68. package/dist/agents/sandbox/sanitize-env-vars.js +1 -1
  69. package/dist/agents/sandbox/shared.js +10 -6
  70. package/dist/agents/sandbox-paths.js +24 -11
  71. package/dist/agents/schema/clean-for-gemini.js +132 -85
  72. package/dist/agents/session-slug.js +10 -5
  73. package/dist/agents/session-tool-result-guard-wrapper.js +1 -0
  74. package/dist/agents/session-tool-result-guard.js +3 -1
  75. package/dist/agents/session-transcript-repair.js +40 -6
  76. package/dist/agents/skills/bundled-dir.js +19 -5
  77. package/dist/agents/skills/env-overrides.js +124 -43
  78. package/dist/agents/skills/frontmatter.js +6 -6
  79. package/dist/agents/skills/plugin-skills.js +14 -7
  80. package/dist/agents/skills/workspace.js +1 -0
  81. package/dist/agents/skills.test-helpers.js +13 -0
  82. package/dist/agents/stable-stringify.js +12 -0
  83. package/dist/agents/subagent-announce.js +251 -49
  84. package/dist/agents/subagent-lifecycle-events.js +19 -0
  85. package/dist/agents/subagent-registry-cleanup.js +31 -0
  86. package/dist/agents/subagent-registry-completion.js +68 -0
  87. package/dist/agents/subagent-registry-queries.js +117 -0
  88. package/dist/agents/subagent-registry-state.js +46 -0
  89. package/dist/agents/subagent-registry.js +252 -221
  90. package/dist/agents/subagent-registry.mocks.shared.js +12 -0
  91. package/dist/agents/subagent-registry.store.js +1 -0
  92. package/dist/agents/subagent-registry.types.js +1 -0
  93. package/dist/agents/subagent-spawn.js +195 -7
  94. package/dist/agents/system-prompt.js +22 -6
  95. package/dist/agents/test-helpers/assistant-message-fixtures.js +29 -0
  96. package/dist/agents/test-helpers/fast-coding-tools.js +1 -18
  97. package/dist/agents/test-helpers/fast-core-tools.js +1 -17
  98. package/dist/agents/test-helpers/pi-tools-sandbox-context.js +27 -0
  99. package/dist/agents/timeout.js +18 -6
  100. package/dist/agents/tool-call-id.js +1 -1
  101. package/dist/agents/tool-display-common.js +162 -29
  102. package/dist/agents/tool-images.js +82 -9
  103. package/dist/agents/tool-policy-shared.js +108 -0
  104. package/dist/agents/tool-policy.js +51 -26
  105. package/dist/agents/tools/browser-tool.js +160 -54
  106. package/dist/agents/tools/canvas-tool.js +27 -1
  107. package/dist/agents/tools/common.js +45 -0
  108. package/dist/agents/tools/cron-tool.test-helpers.js +12 -0
  109. package/dist/agents/tools/discord-actions-guild.js +4 -1
  110. package/dist/agents/tools/discord-actions-moderation-shared.js +27 -0
  111. package/dist/agents/tools/gateway-tool.js +3 -1
  112. package/dist/agents/tools/image-tool.js +214 -99
  113. package/dist/agents/tools/nodes-utils.js +1 -10
  114. package/dist/agents/tools/sessions-history-tool.js +140 -108
  115. package/dist/agents/tools/sessions-send-helpers.js +12 -6
  116. package/dist/agents/tools/sessions-spawn-tool.js +8 -2
  117. package/dist/agents/tools/subagents-tool.js +2 -1
  118. package/dist/agents/tools/whatsapp-actions.js +10 -2
  119. package/dist/agents/tools/whatsapp-target-auth.js +18 -0
  120. package/dist/agents/transcript-policy.js +22 -8
  121. package/dist/agents/venice-models.js +11 -3
  122. package/dist/agents/workspace.js +222 -46
  123. package/dist/auto-reply/commands-registry.data.js +51 -0
  124. package/dist/auto-reply/commands-registry.js +19 -21
  125. package/dist/auto-reply/fallback-state.js +114 -0
  126. package/dist/auto-reply/group-activation.js +10 -5
  127. package/dist/auto-reply/inbound-debounce.js +10 -5
  128. package/dist/auto-reply/model-runtime.js +68 -0
  129. package/dist/auto-reply/reply/abort.js +1 -1
  130. package/dist/auto-reply/reply/agent-runner-execution.js +40 -5
  131. package/dist/auto-reply/reply/agent-runner.js +165 -39
  132. package/dist/auto-reply/reply/bash-command.js +41 -39
  133. package/dist/auto-reply/reply/command-gates.js +25 -0
  134. package/dist/auto-reply/reply/commands-allowlist.js +111 -72
  135. package/dist/auto-reply/reply/commands-bash.js +6 -5
  136. package/dist/auto-reply/reply/commands-config.js +30 -28
  137. package/dist/auto-reply/reply/commands-core.js +2 -1
  138. package/dist/auto-reply/reply/commands-info.js +1 -0
  139. package/dist/auto-reply/reply/commands-models.js +65 -14
  140. package/dist/auto-reply/reply/commands-session.js +237 -82
  141. package/dist/auto-reply/reply/commands-setunset-standard.js +13 -0
  142. package/dist/auto-reply/reply/commands-setunset.js +45 -0
  143. package/dist/auto-reply/reply/commands-subagents/action-agents.js +44 -0
  144. package/dist/auto-reply/reply/commands-subagents/action-focus.js +64 -0
  145. package/dist/auto-reply/reply/commands-subagents/action-help.js +4 -0
  146. package/dist/auto-reply/reply/commands-subagents/action-info.js +45 -0
  147. package/dist/auto-reply/reply/commands-subagents/action-kill.js +60 -0
  148. package/dist/auto-reply/reply/commands-subagents/action-list.js +44 -0
  149. package/dist/auto-reply/reply/commands-subagents/action-log.js +29 -0
  150. package/dist/auto-reply/reply/commands-subagents/action-send.js +119 -0
  151. package/dist/auto-reply/reply/commands-subagents/action-spawn.js +52 -0
  152. package/dist/auto-reply/reply/commands-subagents/action-unfocus.js +30 -0
  153. package/dist/auto-reply/reply/commands-subagents/shared.js +303 -0
  154. package/dist/auto-reply/reply/commands-subagents.js +51 -587
  155. package/dist/auto-reply/reply/commands-tts.js +10 -5
  156. package/dist/auto-reply/reply/config-value.js +10 -5
  157. package/dist/auto-reply/reply/directive-handling.model-picker.js +12 -6
  158. package/dist/auto-reply/reply/directive-handling.persist.js +9 -21
  159. package/dist/auto-reply/reply/directive-handling.shared.js +24 -4
  160. package/dist/auto-reply/reply/followup-runner.js +1 -0
  161. package/dist/auto-reply/reply/get-reply-directives-utils.js +23 -14
  162. package/dist/auto-reply/reply/get-reply-directives.js +17 -28
  163. package/dist/auto-reply/reply/get-reply-inline-actions.js +1 -0
  164. package/dist/auto-reply/reply/get-reply.js +71 -12
  165. package/dist/auto-reply/reply/model-selection.js +80 -39
  166. package/dist/auto-reply/reply/queue/enqueue.js +10 -5
  167. package/dist/auto-reply/reply/queue/state.js +13 -12
  168. package/dist/auto-reply/reply/reply-payloads.js +67 -36
  169. package/dist/auto-reply/reply/reply-reference.js +9 -8
  170. package/dist/auto-reply/reply/route-reply.js +15 -8
  171. package/dist/auto-reply/reply/session-reset-prompt.js +1 -1
  172. package/dist/auto-reply/reply/session.js +22 -6
  173. package/dist/auto-reply/reply/strip-inbound-meta.js +147 -0
  174. package/dist/auto-reply/reply/subagents-utils.js +56 -30
  175. package/dist/auto-reply/reply/typing.js +46 -21
  176. package/dist/auto-reply/send-policy.js +14 -7
  177. package/dist/auto-reply/status.js +140 -16
  178. package/dist/auto-reply/templating.js +10 -5
  179. package/dist/auto-reply/thinking.js +7 -16
  180. package/dist/auto-reply/tokens.js +21 -5
  181. package/dist/browser/bridge-server.js +36 -20
  182. package/dist/browser/cdp.helpers.js +7 -14
  183. package/dist/browser/cdp.js +35 -15
  184. package/dist/browser/chrome.profile-decoration.js +7 -4
  185. package/dist/browser/config.js +30 -0
  186. package/dist/browser/extension-relay-auth.js +55 -0
  187. package/dist/browser/extension-relay.js +74 -29
  188. package/dist/browser/navigation-guard.js +39 -0
  189. package/dist/browser/paths.js +77 -0
  190. package/dist/browser/profiles.js +13 -8
  191. package/dist/browser/pw-ai-module.js +10 -5
  192. package/dist/browser/pw-session.js +76 -39
  193. package/dist/browser/pw-tools-core.interactions.js +14 -7
  194. package/dist/browser/pw-tools-core.state.js +12 -6
  195. package/dist/browser/routes/agent.act.js +431 -424
  196. package/dist/browser/routes/agent.shared.js +47 -3
  197. package/dist/browser/routes/agent.snapshot.js +122 -116
  198. package/dist/browser/routes/agent.storage.js +303 -297
  199. package/dist/browser/routes/tabs.js +154 -100
  200. package/dist/browser/server-context.js +7 -0
  201. package/dist/browser/server-lifecycle.js +37 -0
  202. package/dist/build-info.json +3 -3
  203. package/dist/channels/allow-from.js +26 -0
  204. package/dist/channels/allowlists/resolve-utils.js +43 -19
  205. package/dist/channels/channel-config.js +14 -7
  206. package/dist/channels/draft-stream-loop.js +7 -0
  207. package/dist/channels/model-overrides.js +82 -0
  208. package/dist/channels/plugins/account-action-gate.js +13 -0
  209. package/dist/channels/plugins/message-actions.js +10 -0
  210. package/dist/channels/plugins/normalize/imessage.js +14 -7
  211. package/dist/channels/plugins/normalize/slack.js +10 -5
  212. package/dist/channels/plugins/normalize/telegram.js +14 -7
  213. package/dist/channels/plugins/outbound/discord.js +80 -8
  214. package/dist/channels/plugins/outbound/signal.js +11 -11
  215. package/dist/channels/plugins/setup-helpers.js +10 -5
  216. package/dist/channels/sender-label.js +14 -7
  217. package/dist/channels/session.js +4 -2
  218. package/dist/channels/status-reactions.js +297 -0
  219. package/dist/channels/telegram/api.js +18 -0
  220. package/dist/cli/argv.js +84 -21
  221. package/dist/cli/banner.js +3 -2
  222. package/dist/cli/browser-cli-actions-input/register.files-downloads.js +65 -56
  223. package/dist/cli/cli-name.js +11 -11
  224. package/dist/cli/cli-utils.js +13 -3
  225. package/dist/cli/command-format.js +1 -1
  226. package/dist/cli/config-cli.js +1 -1
  227. package/dist/cli/daemon-cli/lifecycle-core.js +31 -19
  228. package/dist/cli/daemon-cli/lifecycle.js +64 -2
  229. package/dist/cli/daemon-cli/restart-health.js +126 -0
  230. package/dist/cli/daemon-cli/status.gather.js +9 -13
  231. package/dist/cli/daemon-cli/status.print.js +2 -10
  232. package/dist/cli/deps.js +27 -22
  233. package/dist/cli/exec-approvals-cli.js +92 -124
  234. package/dist/cli/gateway-cli/run-loop.js +23 -5
  235. package/dist/cli/memory-cli.js +158 -61
  236. package/dist/cli/node-cli/register.js +14 -5
  237. package/dist/cli/nodes-cli/register.push.js +63 -0
  238. package/dist/cli/nodes-media-utils.js +26 -0
  239. package/dist/cli/outbound-send-deps.js +2 -9
  240. package/dist/cli/outbound-send-mapping.js +11 -0
  241. package/dist/cli/pairing-cli.js +40 -14
  242. package/dist/cli/plugins-cli.js +250 -73
  243. package/dist/cli/ports.js +11 -10
  244. package/dist/cli/program/build-program.js +3 -1
  245. package/dist/cli/program/command-registry.js +214 -136
  246. package/dist/cli/program/command-tree.js +16 -0
  247. package/dist/cli/program/help.js +43 -12
  248. package/dist/cli/program/preaction.js +13 -9
  249. package/dist/cli/program/register.configure.js +3 -18
  250. package/dist/cli/program/register.maintenance.js +2 -2
  251. package/dist/cli/program/register.onboard.js +2 -0
  252. package/dist/cli/program/register.status-health-sessions.js +16 -17
  253. package/dist/cli/program/register.subclis.js +93 -52
  254. package/dist/cli/route.js +12 -8
  255. package/dist/cli/system-cli.js +36 -46
  256. package/dist/cli/test-runtime-capture.js +24 -0
  257. package/dist/cli/update-cli/shared.js +22 -9
  258. package/dist/cli/update-cli/update-command.js +89 -14
  259. package/dist/cli/update-cli/wizard.js +6 -12
  260. package/dist/commands/agent/run-context.js +18 -5
  261. package/dist/commands/agent/session-store.js +17 -4
  262. package/dist/commands/agent.js +185 -89
  263. package/dist/commands/agents.bindings.js +14 -7
  264. package/dist/commands/agents.commands.add.js +13 -9
  265. package/dist/commands/agents.commands.identity.js +12 -6
  266. package/dist/commands/agents.commands.list.js +11 -6
  267. package/dist/commands/agents.config.js +8 -10
  268. package/dist/commands/agents.providers.js +12 -6
  269. package/dist/commands/auth-choice-options.js +103 -75
  270. package/dist/commands/auth-choice.apply.byteplus.js +55 -0
  271. package/dist/commands/auth-choice.apply.js +4 -0
  272. package/dist/commands/auth-choice.apply.minimax.js +61 -13
  273. package/dist/commands/auth-choice.apply.openai.js +3 -1
  274. package/dist/commands/auth-choice.apply.volcengine.js +55 -0
  275. package/dist/commands/auth-choice.preferred-provider.js +2 -0
  276. package/dist/commands/channels/remove.js +13 -6
  277. package/dist/commands/channels/shared.js +4 -14
  278. package/dist/commands/channels.mock-harness.js +23 -0
  279. package/dist/commands/configure.commands.js +14 -0
  280. package/dist/commands/configure.gateway.js +2 -4
  281. package/dist/commands/configure.js +1 -1
  282. package/dist/commands/configure.shared.js +11 -0
  283. package/dist/commands/daemon-install-helpers.js +2 -2
  284. package/dist/commands/daemon-install-runtime-warning.js +11 -0
  285. package/dist/commands/dashboard.js +12 -10
  286. package/dist/commands/docs.js +14 -8
  287. package/dist/commands/doctor-config-flow.js +11 -9
  288. package/dist/commands/doctor-legacy-config.js +281 -0
  289. package/dist/commands/doctor-state-integrity.js +99 -23
  290. package/dist/commands/doctor-update.js +12 -9
  291. package/dist/commands/models/list.list-command.js +7 -5
  292. package/dist/commands/models/set-image.js +2 -21
  293. package/dist/commands/node-daemon-install-helpers.js +10 -8
  294. package/dist/commands/onboard-auth.config-minimax.js +54 -80
  295. package/dist/commands/onboard-auth.config-opencode.js +2 -18
  296. package/dist/commands/onboard-auth.credentials.js +90 -13
  297. package/dist/commands/onboard-auth.js +1 -1
  298. package/dist/commands/onboard-auth.models.js +6 -5
  299. package/dist/commands/onboard-hooks.js +1 -1
  300. package/dist/commands/onboard-non-interactive/api-keys.js +14 -7
  301. package/dist/commands/onboard-non-interactive/local/auth-choice.js +64 -49
  302. package/dist/commands/onboard-provider-auth-flags.js +14 -0
  303. package/dist/commands/onboard-remote.js +14 -7
  304. package/dist/commands/onboard.js +11 -13
  305. package/dist/commands/sandbox-display.js +6 -5
  306. package/dist/commands/sessions.test-helpers.js +61 -0
  307. package/dist/commands/status-all/diagnosis.js +14 -10
  308. package/dist/commands/status-all/format.js +1 -0
  309. package/dist/commands/status.gateway-probe.js +1 -16
  310. package/dist/commands/systemd-linger.js +12 -6
  311. package/dist/config/agent-limits.js +2 -0
  312. package/dist/config/commands.js +32 -15
  313. package/dist/config/config-paths.js +9 -11
  314. package/dist/config/config.js +1 -1
  315. package/dist/config/defaults.js +22 -2
  316. package/dist/config/discord-preview-streaming.js +104 -0
  317. package/dist/config/env-substitution.js +62 -34
  318. package/dist/config/env-vars.js +45 -7
  319. package/dist/config/includes.js +4 -0
  320. package/dist/config/io.js +656 -171
  321. package/dist/config/legacy.migrations.part-1.js +189 -78
  322. package/dist/config/legacy.shared.js +3 -1
  323. package/dist/config/merge-patch.js +54 -4
  324. package/dist/config/prototype-keys.js +4 -0
  325. package/dist/config/redact-snapshot.js +404 -76
  326. package/dist/config/schema.help.js +44 -7
  327. package/dist/config/schema.js +58 -570
  328. package/dist/config/schema.labels.js +38 -6
  329. package/dist/config/sessions/delivery-info.js +10 -3
  330. package/dist/config/sessions/main-session.js +10 -5
  331. package/dist/config/sessions/session-file.js +33 -0
  332. package/dist/config/sessions/session-key.js +10 -5
  333. package/dist/config/sessions/store.js +1 -1
  334. package/dist/config/sessions.js +1 -0
  335. package/dist/config/validation.js +140 -85
  336. package/dist/config/zod-schema.agent-runtime.js +11 -0
  337. package/dist/config/zod-schema.hooks.js +40 -11
  338. package/dist/config/zod-schema.installs.js +20 -0
  339. package/dist/config/zod-schema.js +156 -20
  340. package/dist/config/zod-schema.providers-core.js +78 -4
  341. package/dist/config/zod-schema.providers.js +6 -1
  342. package/dist/config/zod-schema.session.js +41 -2
  343. package/dist/cron/run-log.js +3 -0
  344. package/dist/cron/schedule.js +21 -10
  345. package/dist/cron/service/ops.js +35 -21
  346. package/dist/cron/service/timer.js +116 -16
  347. package/dist/cron/stagger.js +3 -1
  348. package/dist/daemon/cmd-argv.js +21 -0
  349. package/dist/daemon/cmd-set.js +58 -0
  350. package/dist/daemon/service-types.js +1 -0
  351. package/dist/discord/api.js +12 -6
  352. package/dist/discord/draft-chunking.js +22 -0
  353. package/dist/discord/draft-stream.js +124 -0
  354. package/dist/discord/monitor/agent-components.js +1 -1
  355. package/dist/discord/monitor/commands.js +5 -0
  356. package/dist/discord/monitor/exec-approvals.js +357 -162
  357. package/dist/discord/monitor/gateway-plugin.js +2 -1
  358. package/dist/discord/monitor/listeners.js +37 -27
  359. package/dist/discord/monitor/message-handler.js +4 -1
  360. package/dist/discord/monitor/message-handler.preflight.js +65 -8
  361. package/dist/discord/monitor/message-handler.process.js +246 -217
  362. package/dist/discord/monitor/message-utils.js +143 -6
  363. package/dist/discord/monitor/model-picker-preferences.js +143 -0
  364. package/dist/discord/monitor/model-picker.js +651 -0
  365. package/dist/discord/monitor/native-command.js +573 -16
  366. package/dist/discord/monitor/provider.allowlist.js +223 -0
  367. package/dist/discord/monitor/provider.js +275 -347
  368. package/dist/discord/monitor/provider.lifecycle.js +100 -0
  369. package/dist/discord/monitor/reply-delivery.js +123 -16
  370. package/dist/discord/monitor/thread-bindings.discord-api.js +215 -0
  371. package/dist/discord/monitor/thread-bindings.js +4 -0
  372. package/dist/discord/monitor/thread-bindings.lifecycle.js +177 -0
  373. package/dist/discord/monitor/thread-bindings.manager.js +423 -0
  374. package/dist/discord/monitor/thread-bindings.messages.js +55 -0
  375. package/dist/discord/monitor/thread-bindings.state.js +358 -0
  376. package/dist/discord/monitor/thread-bindings.types.js +6 -0
  377. package/dist/discord/resolve-users.js +33 -21
  378. package/dist/discord/send.channels.js +15 -0
  379. package/dist/discord/send.js +3 -2
  380. package/dist/discord/send.outbound.js +82 -26
  381. package/dist/discord/send.permissions.js +83 -30
  382. package/dist/discord/send.reactions.js +8 -4
  383. package/dist/discord/token.js +10 -5
  384. package/dist/discord/voice/command.js +263 -0
  385. package/dist/discord/voice/manager.js +531 -0
  386. package/dist/gateway/auth.js +72 -13
  387. package/dist/gateway/call.js +152 -83
  388. package/dist/gateway/canvas-capability.js +75 -0
  389. package/dist/gateway/client.js +28 -4
  390. package/dist/gateway/config-reload.js +3 -4
  391. package/dist/gateway/control-plane-audit.js +28 -0
  392. package/dist/gateway/control-plane-rate-limit.js +53 -0
  393. package/dist/gateway/control-ui.js +219 -96
  394. package/dist/gateway/events.js +1 -0
  395. package/dist/gateway/hooks-mapping.js +88 -38
  396. package/dist/gateway/hooks.js +109 -54
  397. package/dist/gateway/http-auth-helpers.js +3 -2
  398. package/dist/gateway/http-common.js +22 -0
  399. package/dist/gateway/http-endpoint-helpers.js +1 -0
  400. package/dist/gateway/method-scopes.js +169 -0
  401. package/dist/gateway/net.js +74 -9
  402. package/dist/gateway/node-invoke-system-run-approval.js +14 -35
  403. package/dist/gateway/node-registry.js +10 -5
  404. package/dist/gateway/openai-http.js +1 -0
  405. package/dist/gateway/openresponses-http.js +121 -110
  406. package/dist/gateway/origin-check.js +1 -18
  407. package/dist/gateway/probe-auth.js +2 -0
  408. package/dist/gateway/protocol/index.js +4 -2
  409. package/dist/gateway/protocol/schema/cron.js +1 -0
  410. package/dist/gateway/protocol/schema/devices.js +1 -0
  411. package/dist/gateway/protocol/schema/protocol-schemas.js +4 -1
  412. package/dist/gateway/protocol/schema/push.js +18 -0
  413. package/dist/gateway/protocol/schema/sessions.js +6 -0
  414. package/dist/gateway/protocol/schema.js +1 -0
  415. package/dist/gateway/role-policy.js +17 -0
  416. package/dist/gateway/server/ws-connection/connect-policy.js +37 -0
  417. package/dist/gateway/server/ws-connection/message-handler.js +175 -148
  418. package/dist/gateway/server-chat.js +83 -25
  419. package/dist/gateway/server-constants.js +10 -9
  420. package/dist/gateway/server-cron.js +1 -0
  421. package/dist/gateway/server-http.js +247 -54
  422. package/dist/gateway/server-maintenance.js +20 -5
  423. package/dist/gateway/server-methods/agent.js +162 -24
  424. package/dist/gateway/server-methods/chat.js +465 -130
  425. package/dist/gateway/server-methods/config.js +193 -152
  426. package/dist/gateway/server-methods/devices.js +17 -3
  427. package/dist/gateway/server-methods/models.js +11 -1
  428. package/dist/gateway/server-methods/nodes.helpers.js +12 -0
  429. package/dist/gateway/server-methods/nodes.js +251 -69
  430. package/dist/gateway/server-methods/push.js +53 -0
  431. package/dist/gateway/server-methods/sessions.js +64 -8
  432. package/dist/gateway/server-methods/usage.js +162 -75
  433. package/dist/gateway/server-node-events.js +29 -0
  434. package/dist/gateway/server-reload-handlers.js +2 -3
  435. package/dist/gateway/server-runtime-config.js +39 -13
  436. package/dist/gateway/server-runtime-state.js +2 -0
  437. package/dist/gateway/server-startup-memory.js +17 -11
  438. package/dist/gateway/server-ws-runtime.js +1 -0
  439. package/dist/gateway/server.impl.js +296 -139
  440. package/dist/gateway/session-preview.test-helpers.js +11 -0
  441. package/dist/gateway/session-utils.fs.js +32 -34
  442. package/dist/gateway/sessions-resolve.js +17 -5
  443. package/dist/gateway/startup-auth.js +126 -0
  444. package/dist/gateway/test-helpers.agent-results.js +15 -0
  445. package/dist/gateway/test-helpers.mocks.js +37 -14
  446. package/dist/gateway/test-helpers.openai-mock.js +14 -7
  447. package/dist/gateway/test-helpers.server.js +161 -77
  448. package/dist/gateway/tools-invoke-http.js +21 -10
  449. package/dist/hooks/bundled/bootstrap-extra-files/handler.js +3 -1
  450. package/dist/hooks/bundled/command-logger/handler.js +7 -2
  451. package/dist/hooks/bundled/session-memory/handler.js +170 -38
  452. package/dist/hooks/frontmatter.js +6 -6
  453. package/dist/hooks/gmail-watcher-lifecycle.js +23 -0
  454. package/dist/hooks/gmail-watcher.js +11 -6
  455. package/dist/hooks/internal-hooks.js +11 -1
  456. package/dist/hooks/llm-slug-generator.js +4 -1
  457. package/dist/hooks/workspace.js +47 -17
  458. package/dist/imessage/accounts.js +9 -20
  459. package/dist/imessage/monitor/inbound-processing.js +2 -1
  460. package/dist/infra/archive-path.js +49 -0
  461. package/dist/infra/archive.js +174 -73
  462. package/dist/infra/control-ui-assets.js +14 -6
  463. package/dist/infra/device-pairing.js +204 -144
  464. package/dist/infra/env.js +10 -5
  465. package/dist/infra/exec-approvals-allowlist.js +141 -70
  466. package/dist/infra/exec-approvals-analysis.js +78 -20
  467. package/dist/infra/exec-approvals.js +5 -17
  468. package/dist/infra/exec-safe-bin-policy.js +277 -0
  469. package/dist/infra/fixed-window-rate-limit.js +33 -0
  470. package/dist/infra/fs-safe.js +71 -39
  471. package/dist/infra/gateway-lock.js +6 -2
  472. package/dist/infra/git-root.js +61 -0
  473. package/dist/infra/heartbeat-active-hours.js +2 -2
  474. package/dist/infra/heartbeat-reason.js +40 -0
  475. package/dist/infra/heartbeat-runner.js +72 -32
  476. package/dist/infra/heartbeat-wake.js +6 -12
  477. package/dist/infra/host-env-security-policy.json +19 -0
  478. package/dist/infra/host-env-security.js +66 -0
  479. package/dist/infra/install-source-utils.js +91 -7
  480. package/dist/infra/net/ssrf.js +131 -38
  481. package/dist/infra/node-pairing.js +50 -105
  482. package/dist/infra/npm-integrity.js +45 -0
  483. package/dist/infra/npm-pack-install.js +40 -0
  484. package/dist/infra/outbound/bound-delivery-router.js +88 -0
  485. package/dist/infra/outbound/channel-adapters.js +20 -7
  486. package/dist/infra/outbound/channel-selection.js +12 -6
  487. package/dist/infra/outbound/envelope.js +1 -1
  488. package/dist/infra/outbound/format.js +12 -6
  489. package/dist/infra/outbound/message-action-runner.js +107 -327
  490. package/dist/infra/outbound/message.js +59 -36
  491. package/dist/infra/outbound/outbound-policy.js +52 -25
  492. package/dist/infra/outbound/outbound-send-service.js +58 -71
  493. package/dist/infra/outbound/payloads.js +14 -7
  494. package/dist/infra/outbound/session-binding-service.js +123 -0
  495. package/dist/infra/pairing-files.js +10 -0
  496. package/dist/infra/path-guards.js +25 -0
  497. package/dist/infra/plain-object.js +9 -0
  498. package/dist/infra/provider-usage.fetch.codex.js +7 -15
  499. package/dist/infra/provider-usage.fetch.gemini.js +14 -11
  500. package/dist/infra/provider-usage.fetch.shared.js +30 -1
  501. package/dist/infra/provider-usage.fetch.zai.js +10 -9
  502. package/dist/infra/push-apns.js +365 -0
  503. package/dist/infra/restart-sentinel.js +16 -1
  504. package/dist/infra/restart.js +229 -26
  505. package/dist/infra/retry-policy.js +4 -2
  506. package/dist/infra/retry.js +9 -5
  507. package/dist/infra/scp-host.js +54 -0
  508. package/dist/infra/session-cost-usage.js +107 -59
  509. package/dist/infra/session-maintenance-warning.js +3 -1
  510. package/dist/infra/shell-env.js +98 -34
  511. package/dist/infra/ssh-config.js +12 -6
  512. package/dist/infra/system-run-command.js +49 -4
  513. package/dist/infra/update-channels.js +10 -5
  514. package/dist/infra/update-startup.js +86 -9
  515. package/dist/line/accounts.js +5 -7
  516. package/dist/line/bot-access.js +8 -20
  517. package/dist/line/bot-handlers.js +3 -1
  518. package/dist/link-understanding/detect.js +15 -7
  519. package/dist/media/constants.js +15 -6
  520. package/dist/media/image-ops.js +7 -0
  521. package/dist/media/inbound-path-policy.js +114 -0
  522. package/dist/media/input-files.js +16 -0
  523. package/dist/media/local-roots.js +3 -2
  524. package/dist/media-understanding/apply.js +4 -1
  525. package/dist/media-understanding/concurrency.js +8 -20
  526. package/dist/memory/backend-config.js +45 -6
  527. package/dist/memory/embeddings.js +10 -4
  528. package/dist/memory/fs-utils.js +23 -0
  529. package/dist/memory/manager-search.js +12 -6
  530. package/dist/memory/manager-sync-ops.js +12 -2
  531. package/dist/memory/qmd-manager.js +466 -53
  532. package/dist/memory/query-expansion.js +167 -3
  533. package/dist/memory/status-format.js +10 -5
  534. package/dist/memory/sync-memory-files.js +1 -1
  535. package/dist/memory/test-manager.js +8 -0
  536. package/dist/node-host/invoke-system-run.js +281 -0
  537. package/dist/node-host/invoke.js +55 -337
  538. package/dist/pairing/pairing-store.js +22 -0
  539. package/dist/plugin-sdk/allow-from.js +1 -1
  540. package/dist/plugin-sdk/command-auth.js +3 -1
  541. package/dist/plugin-sdk/index.js +6 -3
  542. package/dist/plugin-sdk/temp-path.js +47 -0
  543. package/dist/plugin-sdk/webhook-targets.js +32 -0
  544. package/dist/plugins/bundled-dir.js +9 -6
  545. package/dist/plugins/discovery.js +217 -23
  546. package/dist/plugins/hook-runner-global.js +16 -0
  547. package/dist/plugins/hooks.js +50 -0
  548. package/dist/plugins/install.js +28 -16
  549. package/dist/plugins/loader.js +192 -26
  550. package/dist/plugins/logger.js +8 -0
  551. package/dist/plugins/manifest-registry.js +3 -0
  552. package/dist/plugins/path-safety.js +34 -0
  553. package/dist/plugins/registry.js +5 -2
  554. package/dist/plugins/runtime/index.js +271 -206
  555. package/dist/plugins/runtime.js +3 -17
  556. package/dist/plugins/update.js +78 -12
  557. package/dist/process/spawn-utils.js +14 -7
  558. package/dist/providers/github-copilot-models.js +4 -1
  559. package/dist/providers/github-copilot-token.js +11 -6
  560. package/dist/providers/qwen-portal-oauth.js +14 -6
  561. package/dist/routing/account-id.js +30 -0
  562. package/dist/routing/resolve-route.js +3 -7
  563. package/dist/routing/session-key.js +2 -16
  564. package/dist/security/audit-channel.js +100 -20
  565. package/dist/security/audit-extra.async.js +505 -179
  566. package/dist/security/audit-extra.js +12 -2
  567. package/dist/security/audit-extra.sync.js +421 -35
  568. package/dist/security/audit-fs.js +31 -13
  569. package/dist/security/audit.js +180 -370
  570. package/dist/security/dm-policy-shared.js +68 -0
  571. package/dist/security/external-content.js +46 -14
  572. package/dist/security/fix.js +49 -85
  573. package/dist/security/scan-paths.js +20 -0
  574. package/dist/security/secret-equal.js +3 -7
  575. package/dist/security/windows-acl.js +30 -15
  576. package/dist/shared/entry-status.js +6 -0
  577. package/dist/shared/frontmatter.js +5 -5
  578. package/dist/shared/node-list-parse.js +13 -0
  579. package/dist/shared/node-match.js +11 -4
  580. package/dist/shared/operator-scope-compat.js +42 -0
  581. package/dist/shared/text-chunking.js +29 -0
  582. package/dist/signal/accounts.js +7 -20
  583. package/dist/signal/monitor/event-handler.js +3 -1
  584. package/dist/slack/accounts.js +6 -19
  585. package/dist/slack/actions.js +11 -3
  586. package/dist/slack/blocks.test-helpers.js +31 -0
  587. package/dist/slack/monitor/auth.js +1 -1
  588. package/dist/slack/monitor/message-handler/dispatch.js +50 -29
  589. package/dist/slack/monitor/mrkdwn.js +8 -0
  590. package/dist/slack/monitor/replies.js +15 -7
  591. package/dist/slack/monitor/slash.js +22 -13
  592. package/dist/slack/resolve-channels.js +10 -5
  593. package/dist/slack/send.js +102 -12
  594. package/dist/slack/stream-mode.js +10 -0
  595. package/dist/slack/streaming.js +4 -2
  596. package/dist/telegram/accounts.js +19 -14
  597. package/dist/telegram/bot/helpers.js +3 -5
  598. package/dist/telegram/bot-access.js +35 -36
  599. package/dist/telegram/bot-handlers.js +120 -148
  600. package/dist/telegram/bot-message-context.js +68 -9
  601. package/dist/telegram/bot-message-dispatch.js +477 -210
  602. package/dist/telegram/bot-native-commands.js +16 -0
  603. package/dist/telegram/draft-stream.js +44 -8
  604. package/dist/telegram/inline-buttons.js +5 -15
  605. package/dist/telegram/monitor.js +11 -7
  606. package/dist/telegram/network-config.js +19 -7
  607. package/dist/telegram/reasoning-lane-coordinator.js +128 -0
  608. package/dist/telegram/send.js +3 -2
  609. package/dist/telegram/sent-message-cache.js +5 -6
  610. package/dist/telegram/status-reaction-variants.js +208 -0
  611. package/dist/telegram/sticker-cache.js +11 -9
  612. package/dist/terminal/prompt-select-styled.js +9 -0
  613. package/dist/terminal/theme.js +12 -12
  614. package/dist/test-utils/command-runner.js +6 -0
  615. package/dist/test-utils/internal-hook-event-payload.js +10 -0
  616. package/dist/test-utils/model-auth-mock.js +12 -0
  617. package/dist/test-utils/provider-usage-fetch.js +14 -0
  618. package/dist/test-utils/temp-home.js +33 -0
  619. package/dist/tts/tts.js +80 -567
  620. package/dist/tui/components/chat-log.js +50 -8
  621. package/dist/tui/theme/theme.js +10 -12
  622. package/dist/tui/tui-command-handlers.js +36 -27
  623. package/dist/tui/tui-event-handlers.js +122 -32
  624. package/dist/tui/tui-local-shell.js +16 -6
  625. package/dist/tui/tui.js +236 -48
  626. package/dist/utils/account-id.js +2 -4
  627. package/dist/utils/boolean.js +10 -5
  628. package/dist/utils/directive-tags.js +11 -0
  629. package/dist/utils/mask-api-key.js +10 -0
  630. package/dist/utils/queue-helpers.js +67 -12
  631. package/dist/utils/run-with-concurrency.js +39 -0
  632. package/dist/web/auto-reply/deliver-reply.js +8 -4
  633. package/dist/web/auto-reply/mentions.js +10 -5
  634. package/dist/web/auto-reply/monitor/group-members.js +14 -7
  635. package/dist/web/auto-reply/monitor/process-message.js +45 -24
  636. package/dist/web/inbound/access-control.js +5 -2
  637. package/dist/web/login-qr.js +12 -6
  638. package/dist/web/media.js +126 -15
  639. package/docs/tools/slash-commands.md +5 -1
  640. package/extensions/bluebubbles/src/monitor-processing.ts +580 -139
  641. package/extensions/bluebubbles/src/monitor.ts +208 -1950
  642. package/extensions/feishu/src/external-keys.ts +19 -0
  643. package/extensions/lobster/src/windows-spawn.ts +193 -0
  644. package/extensions/matrix/src/matrix/actions/limits.ts +6 -0
  645. package/extensions/mattermost/src/mattermost/reactions.test-helpers.ts +83 -0
  646. package/package.json +1 -1
@@ -4,6 +4,7 @@ import path from "node:path";
4
4
  import { resolveSessionFilePath, resolveSessionTranscriptPath, resolveSessionTranscriptPathInDir, } from "../config/sessions.js";
5
5
  import { resolveRequiredHomeDir } from "../infra/home-dir.js";
6
6
  import { hasInterSessionUserProvenance } from "../sessions/input-provenance.js";
7
+ import { stripInlineDirectiveTagsForDisplay } from "../utils/directive-tags.js";
7
8
  import { extractToolCallNames, hasToolCall } from "../utils/transcript-tools.js";
8
9
  import { stripEnvelope } from "./chat-sanitize.js";
9
10
  const sessionTitleFieldsCache = new Map();
@@ -284,7 +285,8 @@ export function readSessionTitleFieldsFromTranscript(sessionId, storePath, sessi
284
285
  }
285
286
  function extractTextFromContent(content) {
286
287
  if (typeof content === "string") {
287
- return content.trim() || null;
288
+ const normalized = stripInlineDirectiveTagsForDisplay(content).text.trim();
289
+ return normalized || null;
288
290
  }
289
291
  if (!Array.isArray(content)) {
290
292
  return null;
@@ -294,9 +296,9 @@ function extractTextFromContent(content) {
294
296
  continue;
295
297
  }
296
298
  if (part.type === "text" || part.type === "output_text" || part.type === "input_text") {
297
- const trimmed = part.text.trim();
298
- if (trimmed) {
299
- return trimmed;
299
+ const normalized = stripInlineDirectiveTagsForDisplay(part.text).text.trim();
300
+ if (normalized) {
301
+ return normalized;
300
302
  }
301
303
  }
302
304
  }
@@ -336,20 +338,15 @@ function extractFirstUserMessageFromTranscriptChunk(chunk, opts) {
336
338
  }
337
339
  return null;
338
340
  }
339
- export function readFirstUserMessageFromTranscript(sessionId, storePath, sessionFile, agentId, opts) {
341
+ function findExistingTranscriptPath(sessionId, storePath, sessionFile, agentId) {
340
342
  const candidates = resolveSessionTranscriptCandidates(sessionId, storePath, sessionFile, agentId);
341
- const filePath = candidates.find((p) => fs.existsSync(p));
342
- if (!filePath) {
343
- return null;
344
- }
343
+ return candidates.find((p) => fs.existsSync(p)) ?? null;
344
+ }
345
+ function withOpenTranscriptFd(filePath, read) {
345
346
  let fd = null;
346
347
  try {
347
348
  fd = fs.openSync(filePath, "r");
348
- const chunk = readTranscriptHeadChunk(fd);
349
- if (!chunk) {
350
- return null;
351
- }
352
- return extractFirstUserMessageFromTranscriptChunk(chunk, opts);
349
+ return read(fd);
353
350
  }
354
351
  catch {
355
352
  // file read error
@@ -361,6 +358,19 @@ export function readFirstUserMessageFromTranscript(sessionId, storePath, session
361
358
  }
362
359
  return null;
363
360
  }
361
+ export function readFirstUserMessageFromTranscript(sessionId, storePath, sessionFile, agentId, opts) {
362
+ const filePath = findExistingTranscriptPath(sessionId, storePath, sessionFile, agentId);
363
+ if (!filePath) {
364
+ return null;
365
+ }
366
+ return withOpenTranscriptFd(filePath, (fd) => {
367
+ const chunk = readTranscriptHeadChunk(fd);
368
+ if (!chunk) {
369
+ return null;
370
+ }
371
+ return extractFirstUserMessageFromTranscriptChunk(chunk, opts);
372
+ });
373
+ }
364
374
  const LAST_MSG_MAX_BYTES = 16384;
365
375
  const LAST_MSG_MAX_LINES = 20;
366
376
  function readLastMessagePreviewFromOpenTranscript(params) {
@@ -391,30 +401,18 @@ function readLastMessagePreviewFromOpenTranscript(params) {
391
401
  return null;
392
402
  }
393
403
  export function readLastMessagePreviewFromTranscript(sessionId, storePath, sessionFile, agentId) {
394
- const candidates = resolveSessionTranscriptCandidates(sessionId, storePath, sessionFile, agentId);
395
- const filePath = candidates.find((p) => fs.existsSync(p));
404
+ const filePath = findExistingTranscriptPath(sessionId, storePath, sessionFile, agentId);
396
405
  if (!filePath) {
397
406
  return null;
398
407
  }
399
- let fd = null;
400
- try {
401
- fd = fs.openSync(filePath, "r");
408
+ return withOpenTranscriptFd(filePath, (fd) => {
402
409
  const stat = fs.fstatSync(fd);
403
410
  const size = stat.size;
404
411
  if (size === 0) {
405
412
  return null;
406
413
  }
407
414
  return readLastMessagePreviewFromOpenTranscript({ fd, size });
408
- }
409
- catch {
410
- // file error
411
- }
412
- finally {
413
- if (fd !== null) {
414
- fs.closeSync(fd);
415
- }
416
- }
417
- return null;
415
+ });
418
416
  }
419
417
  const PREVIEW_READ_SIZES = [64 * 1024, 256 * 1024, 1024 * 1024];
420
418
  const PREVIEW_MAX_LINES = 200;
@@ -446,20 +444,20 @@ function truncatePreviewText(text, maxChars) {
446
444
  }
447
445
  function extractPreviewText(message) {
448
446
  if (typeof message.content === "string") {
449
- const trimmed = message.content.trim();
450
- return trimmed ? trimmed : null;
447
+ const normalized = stripInlineDirectiveTagsForDisplay(message.content).text.trim();
448
+ return normalized ? normalized : null;
451
449
  }
452
450
  if (Array.isArray(message.content)) {
453
451
  const parts = message.content
454
- .map((entry) => (typeof entry?.text === "string" ? entry.text : ""))
452
+ .map((entry) => typeof entry?.text === "string" ? stripInlineDirectiveTagsForDisplay(entry.text).text : "")
455
453
  .filter((text) => text.trim().length > 0);
456
454
  if (parts.length > 0) {
457
455
  return parts.join("\n").trim();
458
456
  }
459
457
  }
460
458
  if (typeof message.text === "string") {
461
- const trimmed = message.text.trim();
462
- return trimmed ? trimmed : null;
459
+ const normalized = stripInlineDirectiveTagsForDisplay(message.text).text.trim();
460
+ return normalized ? normalized : null;
463
461
  }
464
462
  return null;
465
463
  }
@@ -1,8 +1,8 @@
1
- import { loadSessionStore } from "../config/sessions.js";
1
+ import { loadSessionStore, updateSessionStore } from "../config/sessions.js";
2
2
  import { parseSessionLabel } from "../sessions/session-label.js";
3
3
  import { ErrorCodes, errorShape, } from "./protocol/index.js";
4
- import { listSessionsFromStore, loadCombinedSessionStoreForGateway, resolveGatewaySessionStoreTarget, } from "./session-utils.js";
5
- export function resolveSessionKeyFromResolveParams(params) {
4
+ import { listSessionsFromStore, loadCombinedSessionStoreForGateway, pruneLegacyStoreKeys, resolveGatewaySessionStoreTarget, } from "./session-utils.js";
5
+ export async function resolveSessionKeyFromResolveParams(params) {
6
6
  const { cfg, p } = params;
7
7
  const key = typeof p.key === "string" ? p.key.trim() : "";
8
8
  const hasKey = key.length > 0;
@@ -25,13 +25,25 @@ export function resolveSessionKeyFromResolveParams(params) {
25
25
  if (hasKey) {
26
26
  const target = resolveGatewaySessionStoreTarget({ cfg, key });
27
27
  const store = loadSessionStore(target.storePath);
28
- const existingKey = target.storeKeys.find((candidate) => store[candidate]);
29
- if (!existingKey) {
28
+ if (store[target.canonicalKey]) {
29
+ return { ok: true, key: target.canonicalKey };
30
+ }
31
+ const legacyKey = target.storeKeys.find((candidate) => store[candidate]);
32
+ if (!legacyKey) {
30
33
  return {
31
34
  ok: false,
32
35
  error: errorShape(ErrorCodes.INVALID_REQUEST, `No session found: ${key}`),
33
36
  };
34
37
  }
38
+ await updateSessionStore(target.storePath, (s) => {
39
+ const liveTarget = resolveGatewaySessionStoreTarget({ cfg, key, store: s });
40
+ const canonicalKey = liveTarget.canonicalKey;
41
+ // Migrate the first legacy entry to the canonical key.
42
+ if (!s[canonicalKey] && s[legacyKey]) {
43
+ s[canonicalKey] = s[legacyKey];
44
+ }
45
+ pruneLegacyStoreKeys({ store: s, canonicalKey, candidates: liveTarget.storeKeys });
46
+ });
35
47
  return { ok: true, key: target.canonicalKey };
36
48
  }
37
49
  if (hasSessionId) {
@@ -0,0 +1,126 @@
1
+ import crypto from "node:crypto";
2
+ import { writeConfigFile } from "../config/config.js";
3
+ import { resolveGatewayAuth } from "./auth.js";
4
+ export function mergeGatewayAuthConfig(base, override) {
5
+ const merged = { ...base };
6
+ if (!override) {
7
+ return merged;
8
+ }
9
+ if (override.mode !== undefined) {
10
+ merged.mode = override.mode;
11
+ }
12
+ if (override.token !== undefined) {
13
+ merged.token = override.token;
14
+ }
15
+ if (override.password !== undefined) {
16
+ merged.password = override.password;
17
+ }
18
+ if (override.allowTailscale !== undefined) {
19
+ merged.allowTailscale = override.allowTailscale;
20
+ }
21
+ if (override.rateLimit !== undefined) {
22
+ merged.rateLimit = override.rateLimit;
23
+ }
24
+ if (override.trustedProxy !== undefined) {
25
+ merged.trustedProxy = override.trustedProxy;
26
+ }
27
+ return merged;
28
+ }
29
+ export function mergeGatewayTailscaleConfig(base, override) {
30
+ const merged = { ...base };
31
+ if (!override) {
32
+ return merged;
33
+ }
34
+ if (override.mode !== undefined) {
35
+ merged.mode = override.mode;
36
+ }
37
+ if (override.resetOnExit !== undefined) {
38
+ merged.resetOnExit = override.resetOnExit;
39
+ }
40
+ return merged;
41
+ }
42
+ function resolveGatewayAuthFromConfig(params) {
43
+ const tailscaleConfig = mergeGatewayTailscaleConfig(params.cfg.gateway?.tailscale, params.tailscaleOverride);
44
+ return resolveGatewayAuth({
45
+ authConfig: params.cfg.gateway?.auth,
46
+ authOverride: params.authOverride,
47
+ env: params.env,
48
+ tailscaleMode: tailscaleConfig.mode ?? "off",
49
+ });
50
+ }
51
+ function shouldPersistGeneratedToken(params) {
52
+ if (!params.persistRequested) {
53
+ return false;
54
+ }
55
+ // Keep CLI/runtime mode overrides ephemeral: startup should not silently
56
+ // mutate durable auth policy when mode was chosen by an override flag.
57
+ if (params.resolvedAuth.modeSource === "override") {
58
+ return false;
59
+ }
60
+ return true;
61
+ }
62
+ export async function ensureGatewayStartupAuth(params) {
63
+ const env = params.env ?? process.env;
64
+ const persistRequested = params.persist === true;
65
+ const resolved = resolveGatewayAuthFromConfig({
66
+ cfg: params.cfg,
67
+ env,
68
+ authOverride: params.authOverride,
69
+ tailscaleOverride: params.tailscaleOverride,
70
+ });
71
+ if (resolved.mode !== "token" || (resolved.token?.trim().length ?? 0) > 0) {
72
+ assertHooksTokenSeparateFromGatewayAuth({ cfg: params.cfg, auth: resolved });
73
+ return { cfg: params.cfg, auth: resolved, persistedGeneratedToken: false };
74
+ }
75
+ const generatedToken = crypto.randomBytes(24).toString("hex");
76
+ const nextCfg = {
77
+ ...params.cfg,
78
+ gateway: {
79
+ ...params.cfg.gateway,
80
+ auth: {
81
+ ...params.cfg.gateway?.auth,
82
+ mode: "token",
83
+ token: generatedToken,
84
+ },
85
+ },
86
+ };
87
+ const persist = shouldPersistGeneratedToken({
88
+ persistRequested,
89
+ resolvedAuth: resolved,
90
+ });
91
+ if (persist) {
92
+ await writeConfigFile(nextCfg);
93
+ }
94
+ const nextAuth = resolveGatewayAuthFromConfig({
95
+ cfg: nextCfg,
96
+ env,
97
+ authOverride: params.authOverride,
98
+ tailscaleOverride: params.tailscaleOverride,
99
+ });
100
+ assertHooksTokenSeparateFromGatewayAuth({ cfg: nextCfg, auth: nextAuth });
101
+ return {
102
+ cfg: nextCfg,
103
+ auth: nextAuth,
104
+ generatedToken,
105
+ persistedGeneratedToken: persist,
106
+ };
107
+ }
108
+ export function assertHooksTokenSeparateFromGatewayAuth(params) {
109
+ if (params.cfg.hooks?.enabled !== true) {
110
+ return;
111
+ }
112
+ const hooksToken = typeof params.cfg.hooks.token === "string" ? params.cfg.hooks.token.trim() : "";
113
+ if (!hooksToken) {
114
+ return;
115
+ }
116
+ const gatewayToken = params.auth.mode === "token" && typeof params.auth.token === "string"
117
+ ? params.auth.token.trim()
118
+ : "";
119
+ if (!gatewayToken) {
120
+ return;
121
+ }
122
+ if (hooksToken !== gatewayToken) {
123
+ return;
124
+ }
125
+ throw new Error("Invalid config: hooks.token must not match gateway auth token. Set a distinct hooks.token for hook ingress.");
126
+ }
@@ -0,0 +1,15 @@
1
+ export function extractPayloadText(result) {
2
+ const record = result;
3
+ const payloads = Array.isArray(record.payloads) ? record.payloads : [];
4
+ const texts = payloads
5
+ .map((p) => (p && typeof p === "object" ? p.text : undefined))
6
+ .filter((t) => typeof t === "string" && t.trim().length > 0);
7
+ return texts.join("\n").trim();
8
+ }
9
+ export function buildAssistantDeltaResult(params) {
10
+ const runId = params.opts?.runId ?? "";
11
+ for (const delta of params.deltas) {
12
+ params.emit({ runId, stream: "assistant", data: { delta } });
13
+ }
14
+ return { payloads: [{ text: params.text }] };
15
+ }
@@ -1,6 +1,6 @@
1
1
  import crypto from "node:crypto";
2
- import fs from "node:fs/promises";
3
2
  import fsSync from "node:fs";
3
+ import fs from "node:fs/promises";
4
4
  import os from "node:os";
5
5
  import path from "node:path";
6
6
  import { vi } from "vitest";
@@ -147,6 +147,7 @@ const hoisted = vi.hoisted(() => ({
147
147
  waitCalls: [],
148
148
  waitResults: new Map(),
149
149
  },
150
+ testTailscaleWhois: { value: null },
150
151
  getReplyFromConfig: vi.fn().mockResolvedValue(undefined),
151
152
  sendWhatsAppMock: vi.fn().mockResolvedValue({ messageId: "msg-1", toJid: "jid-1" }),
152
153
  }));
@@ -168,9 +169,9 @@ const testConfigRoot = {
168
169
  export const setTestConfigRoot = (root) => {
169
170
  testConfigRoot.value = root;
170
171
  process.env.POOLBOT_CONFIG_PATH = path.join(root, "poolbot.json");
171
- process.env.CLAWDBOT_CONFIG_PATH = path.join(root, "poolbot.json");
172
172
  };
173
173
  export const testTailnetIPv4 = hoisted.testTailnetIPv4;
174
+ export const testTailscaleWhois = hoisted.testTailscaleWhois;
174
175
  export const piSdkMock = hoisted.piSdkMock;
175
176
  export const cronIsolatedRun = hoisted.cronIsolatedRun;
176
177
  export const agentCommand = hoisted.agentCommand;
@@ -222,6 +223,13 @@ vi.mock("../infra/tailnet.js", () => ({
222
223
  pickPrimaryTailnetIPv4: () => testTailnetIPv4.value,
223
224
  pickPrimaryTailnetIPv6: () => undefined,
224
225
  }));
226
+ vi.mock("../infra/tailscale.js", async () => {
227
+ const actual = await vi.importActual("../infra/tailscale.js");
228
+ return {
229
+ ...actual,
230
+ readTailscaleWhoisIdentity: async () => testTailscaleWhois.value,
231
+ };
232
+ });
225
233
  vi.mock("../config/sessions.js", async () => {
226
234
  const actual = await vi.importActual("../config/sessions.js");
227
235
  return {
@@ -350,8 +358,8 @@ vi.mock("../config/config.js", async () => {
350
358
  ? fileAgents.defaults
351
359
  : {};
352
360
  const defaults = {
353
- model: { primary: "anthropic/claude-opus-4-5" },
354
- workspace: path.join(os.tmpdir(), "clawd-gateway-test"),
361
+ model: { primary: "anthropic/claude-opus-4-6" },
362
+ workspace: path.join(os.tmpdir(), "poolbot-gateway-test"),
355
363
  ...fileDefaults,
356
364
  ...testState.agentConfig,
357
365
  };
@@ -391,38 +399,46 @@ vi.mock("../config/config.js", async () => {
391
399
  ...fileSession,
392
400
  mainKey: fileSession.mainKey ?? "main",
393
401
  };
394
- if (typeof testState.sessionStorePath === "string")
402
+ if (typeof testState.sessionStorePath === "string") {
395
403
  session.store = testState.sessionStorePath;
396
- if (testState.sessionConfig)
404
+ }
405
+ if (testState.sessionConfig) {
397
406
  Object.assign(session, testState.sessionConfig);
407
+ }
398
408
  const fileGateway = fileConfig.gateway &&
399
409
  typeof fileConfig.gateway === "object" &&
400
410
  !Array.isArray(fileConfig.gateway)
401
411
  ? { ...fileConfig.gateway }
402
412
  : {};
403
- if (testState.gatewayBind)
413
+ if (testState.gatewayBind) {
404
414
  fileGateway.bind = testState.gatewayBind;
405
- if (testState.gatewayAuth)
415
+ }
416
+ if (testState.gatewayAuth) {
406
417
  fileGateway.auth = testState.gatewayAuth;
407
- if (testState.gatewayControlUi)
418
+ }
419
+ if (testState.gatewayControlUi) {
408
420
  fileGateway.controlUi = testState.gatewayControlUi;
421
+ }
409
422
  const gateway = Object.keys(fileGateway).length > 0 ? fileGateway : undefined;
410
423
  const fileCanvasHost = fileConfig.canvasHost &&
411
424
  typeof fileConfig.canvasHost === "object" &&
412
425
  !Array.isArray(fileConfig.canvasHost)
413
426
  ? { ...fileConfig.canvasHost }
414
427
  : {};
415
- if (typeof testState.canvasHostPort === "number")
428
+ if (typeof testState.canvasHostPort === "number") {
416
429
  fileCanvasHost.port = testState.canvasHostPort;
430
+ }
417
431
  const canvasHost = Object.keys(fileCanvasHost).length > 0 ? fileCanvasHost : undefined;
418
432
  const hooks = testState.hooksConfig ?? fileConfig.hooks;
419
433
  const fileCron = fileConfig.cron && typeof fileConfig.cron === "object" && !Array.isArray(fileConfig.cron)
420
434
  ? { ...fileConfig.cron }
421
435
  : {};
422
- if (typeof testState.cronEnabled === "boolean")
436
+ if (typeof testState.cronEnabled === "boolean") {
423
437
  fileCron.enabled = testState.cronEnabled;
424
- if (typeof testState.cronStorePath === "string")
438
+ }
439
+ if (typeof testState.cronStorePath === "string") {
425
440
  fileCron.store = testState.cronStorePath;
441
+ }
426
442
  const cron = Object.keys(fileCron).length > 0 ? fileCron : undefined;
427
443
  const config = {
428
444
  ...fileConfig,
@@ -503,7 +519,14 @@ vi.mock("../cli/deps.js", async () => {
503
519
  }),
504
520
  };
505
521
  });
522
+ vi.mock("../plugins/loader.js", async () => {
523
+ const actual = await vi.importActual("../plugins/loader.js");
524
+ return {
525
+ ...actual,
526
+ loadPoolBotPlugins: () => pluginRegistryState.registry,
527
+ };
528
+ });
529
+ process.env.POOLBOT_SKIP_CHANNELS = "1";
530
+ process.env.POOLBOT_SKIP_CRON = "1";
506
531
  process.env.POOLBOT_SKIP_CHANNELS = "1";
507
- process.env.CLAWDBOT_SKIP_CHANNELS = "1";
508
532
  process.env.POOLBOT_SKIP_CRON = "1";
509
- process.env.CLAWDBOT_SKIP_CRON = "1";
@@ -1,8 +1,9 @@
1
1
  function extractLastUserText(input) {
2
2
  for (let i = input.length - 1; i >= 0; i -= 1) {
3
3
  const item = input[i];
4
- if (!item || item.role !== "user")
4
+ if (!item || item.role !== "user") {
5
5
  continue;
6
+ }
6
7
  const content = item.content;
7
8
  if (Array.isArray(content)) {
8
9
  const text = content
@@ -13,8 +14,9 @@ function extractLastUserText(input) {
13
14
  .map((c) => c.text)
14
15
  .join("\n")
15
16
  .trim();
16
- if (text)
17
+ if (text) {
17
18
  return text;
19
+ }
18
20
  }
19
21
  }
20
22
  return "";
@@ -22,8 +24,9 @@ function extractLastUserText(input) {
22
24
  function extractToolOutput(input) {
23
25
  for (const itemRaw of input) {
24
26
  const item = itemRaw;
25
- if (!item || item.type !== "function_call_output")
27
+ if (!item || item.type !== "function_call_output") {
26
28
  continue;
29
+ }
27
30
  return typeof item.output === "string" ? item.output : "";
28
31
  }
29
32
  return "";
@@ -98,14 +101,18 @@ async function* fakeOpenAIResponsesStream(params) {
98
101
  };
99
102
  }
100
103
  function decodeBodyText(body) {
101
- if (!body)
104
+ if (!body) {
102
105
  return "";
103
- if (typeof body === "string")
106
+ }
107
+ if (typeof body === "string") {
104
108
  return body;
105
- if (body instanceof Uint8Array)
109
+ }
110
+ if (body instanceof Uint8Array) {
106
111
  return Buffer.from(body).toString("utf8");
107
- if (body instanceof ArrayBuffer)
112
+ }
113
+ if (body instanceof ArrayBuffer) {
108
114
  return Buffer.from(new Uint8Array(body)).toString("utf8");
115
+ }
109
116
  return "";
110
117
  }
111
118
  async function buildOpenAIResponsesSse(params) {