mixdog 1.3.5 → 1.4.1

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/NOTICE.md +2 -2
  2. package/README.md +2 -2
  3. package/package.json +2 -11
  4. package/scripts/check-voice-runtime-inputs.mjs +25 -0
  5. package/scripts/daemon-stub.mjs +1 -1
  6. package/scripts/gate-local.mjs +16 -5
  7. package/scripts/latest-guard.mjs +21 -9
  8. package/scripts/lib/isolated-test-env.mjs +10 -5
  9. package/scripts/lib/run-node-tests.mjs +37 -37
  10. package/scripts/lib/scoped-temp.d.mts +16 -0
  11. package/scripts/lib/scoped-temp.mjs +123 -0
  12. package/scripts/lib/stale-temp.mjs +44 -0
  13. package/scripts/native-release-status.mjs +2 -2
  14. package/scripts/post-release-check.mjs +1 -6
  15. package/scripts/pptx-kit-index.mjs +17 -4
  16. package/scripts/recall-history-cases.json +1 -1
  17. package/scripts/suite-health.mjs +20 -2
  18. package/scripts/test-data-dir.mjs +10 -7
  19. package/scripts/test.mjs +7 -11
  20. package/src/agents/reviewer/AGENT.md +7 -11
  21. package/src/agents/reviewer/agent.json +1 -1
  22. package/src/app.mjs +4 -0
  23. package/src/defaults/shipped-history.json +22 -1
  24. package/src/defaults/skills/browser-use/SKILL.md +62 -12
  25. package/src/defaults/skills/code-tidy/SKILL.md +142 -270
  26. package/src/defaults/skills/code-tidy/references/agent-cleanup.md +4 -4
  27. package/src/defaults/skills/code-tidy/references/cleanup-report.md +31 -76
  28. package/src/defaults/skills/code-tidy/references/dead-code.md +6 -12
  29. package/src/defaults/skills/computer-use/SKILL.md +35 -9
  30. package/src/defaults/skills/setup/SKILL.md +22 -0
  31. package/src/defaults/skills/setup/references/actions.md +39 -5
  32. package/src/defaults/skills/setup/references/surfaces.md +11 -2
  33. package/src/defaults/skills/visualize/SKILL.md +2 -1
  34. package/src/lib/rules-builder.cjs +39 -20
  35. package/src/output-styles/common.md +2 -2
  36. package/src/output-styles/simple.md +1 -1
  37. package/src/rules/agent/AGENT.md +11 -10
  38. package/src/rules/lead/LEAD.md +23 -20
  39. package/src/rules/shared/05-tool-calls.md +5 -6
  40. package/src/rules/shared/10-tool-workflow.md +4 -0
  41. package/src/rules/shared/45-destructive.md +0 -2
  42. package/src/rules/shared/50-execution.md +2 -0
  43. package/src/rules/shared/60-verification.md +7 -5
  44. package/src/rules/shared/70-delivery.md +7 -9
  45. package/src/runtime/agent/orchestrator/agent-runtime/agent-progress-watchdog.mjs +29 -6
  46. package/src/runtime/agent/orchestrator/agent-runtime/cache-strategy.mjs +2 -3
  47. package/src/runtime/agent/orchestrator/agent-runtime/title-completion.mjs +3 -1
  48. package/src/runtime/agent/orchestrator/agent-trace-format.mjs +3 -1
  49. package/src/runtime/agent/orchestrator/cache-break-trace.mjs +2 -0
  50. package/src/runtime/agent/orchestrator/config.mjs +17 -1
  51. package/src/runtime/agent/orchestrator/context/collect.mjs +3 -0
  52. package/src/runtime/agent/orchestrator/context/deferred-tools.mjs +73 -68
  53. package/src/runtime/agent/orchestrator/context/skill-catalog.mjs +57 -2
  54. package/src/runtime/agent/orchestrator/mcp/agent-connectors.mjs +3 -3
  55. package/src/runtime/agent/orchestrator/mcp/client-transport.mjs +176 -72
  56. package/src/runtime/agent/orchestrator/mcp/client.mjs +19 -0
  57. package/src/runtime/agent/orchestrator/mcp/oauth-login.mjs +5 -2
  58. package/src/runtime/agent/orchestrator/providers/account-pool.mjs +192 -133
  59. package/src/runtime/agent/orchestrator/providers/admission-scheduler.mjs +42 -6
  60. package/src/runtime/agent/orchestrator/providers/anthropic-api-recovery.mjs +1 -1
  61. package/src/runtime/agent/orchestrator/providers/anthropic-api-request.mjs +7 -3
  62. package/src/runtime/agent/orchestrator/providers/anthropic-api-transport.mjs +8 -2
  63. package/src/runtime/agent/orchestrator/providers/anthropic-cache-warm.mjs +165 -0
  64. package/src/runtime/agent/orchestrator/providers/anthropic-max-tokens-recovery.mjs +6 -2
  65. package/src/runtime/agent/orchestrator/providers/anthropic-messages.mjs +2 -2
  66. package/src/runtime/agent/orchestrator/providers/anthropic-oauth-client-version.mjs +1 -1
  67. package/src/runtime/agent/orchestrator/providers/anthropic-oauth-credentials.mjs +4 -1
  68. package/src/runtime/agent/orchestrator/providers/anthropic-oauth-request/gzip-post.mjs +14 -14
  69. package/src/runtime/agent/orchestrator/providers/anthropic-oauth-request/initial-status.mjs +3 -1
  70. package/src/runtime/agent/orchestrator/providers/anthropic-oauth.mjs +159 -69
  71. package/src/runtime/agent/orchestrator/providers/anthropic-overload-fallback.mjs +25 -3
  72. package/src/runtime/agent/orchestrator/providers/anthropic-sse.mjs +70 -33
  73. package/src/runtime/agent/orchestrator/providers/anthropic-turn-result.mjs +2 -2
  74. package/src/runtime/agent/orchestrator/providers/anthropic.mjs +135 -87
  75. package/src/runtime/agent/orchestrator/providers/antigravity-transport.mjs +123 -102
  76. package/src/runtime/agent/orchestrator/providers/cache-warm-admission.mjs +90 -0
  77. package/src/runtime/agent/orchestrator/providers/command-code-oauth-login.mjs +1 -10
  78. package/src/runtime/agent/orchestrator/providers/cursor-wire-transport.mjs +25 -9
  79. package/src/runtime/agent/orchestrator/providers/cursor.mjs +25 -13
  80. package/src/runtime/agent/orchestrator/providers/devin-wire-transport.mjs +1 -1
  81. package/src/runtime/agent/orchestrator/providers/devin.mjs +3 -0
  82. package/src/runtime/agent/orchestrator/providers/grok-oauth-login.mjs +210 -20
  83. package/src/runtime/agent/orchestrator/providers/lib/anthropic-prefix-trace.mjs +76 -11
  84. package/src/runtime/agent/orchestrator/providers/lib/anthropic-request-utils.mjs +45 -6
  85. package/src/runtime/agent/orchestrator/providers/lib/first-output-window.mjs +58 -0
  86. package/src/runtime/agent/orchestrator/providers/lib/listen-on.mjs +14 -0
  87. package/src/runtime/agent/orchestrator/providers/lib/oauth-token-utils.mjs +17 -3
  88. package/src/runtime/agent/orchestrator/providers/media-normalization.mjs +52 -10
  89. package/src/runtime/agent/orchestrator/providers/mimo-oauth-login.mjs +1 -10
  90. package/src/runtime/agent/orchestrator/providers/model-proxy-channel.d.mts +8 -1
  91. package/src/runtime/agent/orchestrator/providers/model-proxy-channel.mjs +1 -0
  92. package/src/runtime/agent/orchestrator/providers/npm-cli-version.mjs +11 -3
  93. package/src/runtime/agent/orchestrator/providers/oauth-credential-probes.mjs +2 -1
  94. package/src/runtime/agent/orchestrator/providers/openai-compat-chat-send.mjs +1 -0
  95. package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream/chunk-events.mjs +9 -2
  96. package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream/stream-state.mjs +7 -0
  97. package/src/runtime/agent/orchestrator/providers/openai-compat-chat-stream.mjs +14 -3
  98. package/src/runtime/agent/orchestrator/providers/openai-compat-responses-events.mjs +4 -2
  99. package/src/runtime/agent/orchestrator/providers/openai-compat-responses.mjs +1 -0
  100. package/src/runtime/agent/orchestrator/providers/openai-compat-stream-common.mjs +5 -3
  101. package/src/runtime/agent/orchestrator/providers/openai-compat-stream.mjs +16 -3
  102. package/src/runtime/agent/orchestrator/providers/openai-compat-xai-send.mjs +1 -0
  103. package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state/response-events/output-items.mjs +5 -2
  104. package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state/response-events.mjs +13 -3
  105. package/src/runtime/agent/orchestrator/providers/openai-http-sse-response-state.mjs +13 -2
  106. package/src/runtime/agent/orchestrator/providers/openai-http-sse-watchdogs.mjs +81 -42
  107. package/src/runtime/agent/orchestrator/providers/openai-oauth-http-sse.mjs +8 -0
  108. package/src/runtime/agent/orchestrator/providers/openai-oauth-login.mjs +136 -5
  109. package/src/runtime/agent/orchestrator/providers/openai-oauth-tokens.mjs +10 -9
  110. package/src/runtime/agent/orchestrator/providers/openai-ws-send/send-context.mjs +22 -3
  111. package/src/runtime/agent/orchestrator/providers/openai-ws-send-attempts/attempt-context.mjs +43 -5
  112. package/src/runtime/agent/orchestrator/providers/openai-ws-send-attempts/handshake-failure.mjs +3 -1
  113. package/src/runtime/agent/orchestrator/providers/openai-ws-send-attempts/stream-failure.mjs +6 -3
  114. package/src/runtime/agent/orchestrator/providers/openai-ws-stream/event-switch.mjs +20 -12
  115. package/src/runtime/agent/orchestrator/providers/openai-ws-stream.mjs +7 -1
  116. package/src/runtime/agent/orchestrator/providers/openai-ws-watchdogs.mjs +48 -22
  117. package/src/runtime/agent/orchestrator/providers/provider-error-kind.mjs +65 -1
  118. package/src/runtime/agent/orchestrator/providers/quota-reading.mjs +38 -12
  119. package/src/runtime/agent/orchestrator/providers/registry.mjs +38 -0
  120. package/src/runtime/agent/orchestrator/providers/retry-executor.mjs +39 -7
  121. package/src/runtime/agent/orchestrator/providers/statusline-route-meta.mjs +6 -0
  122. package/src/runtime/agent/orchestrator/runtime-core/ask-user-tool-defs.mjs +49 -16
  123. package/src/runtime/agent/orchestrator/runtime-core/compaction-config-keys.mjs +62 -0
  124. package/src/runtime/agent/orchestrator/runtime-core/config-helpers.mjs +37 -16
  125. package/src/runtime/agent/orchestrator/runtime-core/deferred-tool-delta.mjs +100 -23
  126. package/src/runtime/agent/orchestrator/runtime-core/orchestration.mjs +7 -6
  127. package/src/runtime/agent/orchestrator/runtime-core/session-text.mjs +9 -3
  128. package/src/runtime/agent/orchestrator/runtime-core/tool-bridge.mjs +19 -4
  129. package/src/runtime/agent/orchestrator/runtime-core/tool-catalog.mjs +125 -30
  130. package/src/runtime/agent/orchestrator/runtime-core/tool-defs.mjs +3 -1
  131. package/src/runtime/agent/orchestrator/runtime-core/workflow.mjs +5 -2
  132. package/src/runtime/agent/orchestrator/session/cache/scoped-cache.mjs +1 -3
  133. package/src/runtime/agent/orchestrator/session/cache-warm.mjs +798 -0
  134. package/src/runtime/agent/orchestrator/session/catalog-db/schema.mjs +4 -1
  135. package/src/runtime/agent/orchestrator/session/compact/execution-tail.mjs +1 -8
  136. package/src/runtime/agent/orchestrator/session/compact/messages.mjs +23 -0
  137. package/src/runtime/agent/orchestrator/session/compact/observation-supersession.mjs +103 -23
  138. package/src/runtime/agent/orchestrator/session/compact/runner.mjs +280 -45
  139. package/src/runtime/agent/orchestrator/session/compaction-archive-capture.mjs +475 -58
  140. package/src/runtime/agent/orchestrator/session/compaction-archive.mjs +42 -17
  141. package/src/runtime/agent/orchestrator/session/context-utils.mjs +13 -1
  142. package/src/runtime/agent/orchestrator/session/conversation-import/claude.mjs +163 -22
  143. package/src/runtime/agent/orchestrator/session/conversation-import/codex.mjs +132 -17
  144. package/src/runtime/agent/orchestrator/session/conversation-import/convert.mjs +38 -7
  145. package/src/runtime/agent/orchestrator/session/conversation-import/imported-session.mjs +3 -0
  146. package/src/runtime/agent/orchestrator/session/conversation-import/turns.mjs +90 -22
  147. package/src/runtime/agent/orchestrator/session/eager-dispatch.mjs +4 -1
  148. package/src/runtime/agent/orchestrator/session/human-gate/gate.mjs +11 -5
  149. package/src/runtime/agent/orchestrator/session/human-gate/outbound-policy.mjs +0 -2
  150. package/src/runtime/agent/orchestrator/session/human-gate/requests.mjs +36 -4
  151. package/src/runtime/agent/orchestrator/session/human-gate/store.mjs +1 -1
  152. package/src/runtime/agent/orchestrator/session/loop/compact-policy.mjs +51 -25
  153. package/src/runtime/agent/orchestrator/session/loop/fresh-context.mjs +37 -3
  154. package/src/runtime/agent/orchestrator/session/loop/loop-state.mjs +3 -1
  155. package/src/runtime/agent/orchestrator/session/loop/no-tool-turn.mjs +1 -1
  156. package/src/runtime/agent/orchestrator/session/loop/pre-dispatch-deny.mjs +1 -1
  157. package/src/runtime/agent/orchestrator/session/loop/provider-tool-exclusions.mjs +13 -5
  158. package/src/runtime/agent/orchestrator/session/loop/route-fallback.mjs +31 -3
  159. package/src/runtime/agent/orchestrator/session/loop/send-phase.mjs +20 -3
  160. package/src/runtime/agent/orchestrator/session/loop/tool-exec/after-hook.mjs +2 -1
  161. package/src/runtime/agent/orchestrator/session/loop/tool-exec/before-hook.mjs +5 -4
  162. package/src/runtime/agent/orchestrator/session/loop/tool-exec/dispatch.mjs +16 -2
  163. package/src/runtime/agent/orchestrator/session/loop/tool-exec.mjs +16 -1
  164. package/src/runtime/agent/orchestrator/session/loop/tool-exposure-migration.mjs +49 -21
  165. package/src/runtime/agent/orchestrator/session/loop/tool-helpers.mjs +3 -10
  166. package/src/runtime/agent/orchestrator/session/loop/tool-phase.mjs +12 -3
  167. package/src/runtime/agent/orchestrator/session/manager/ask-queue.mjs +12 -2
  168. package/src/runtime/agent/orchestrator/session/manager/ask-session.mjs +19 -1
  169. package/src/runtime/agent/orchestrator/session/manager/ask-turn-execute.mjs +133 -90
  170. package/src/runtime/agent/orchestrator/session/manager/ask-turn-loop-options.mjs +3 -3
  171. package/src/runtime/agent/orchestrator/session/manager/ask-turn-settle.mjs +3 -1
  172. package/src/runtime/agent/orchestrator/session/manager/ask-turn-state.mjs +31 -4
  173. package/src/runtime/agent/orchestrator/session/manager/compaction-runner.mjs +30 -18
  174. package/src/runtime/agent/orchestrator/session/manager/owner-route-fallbacks.mjs +24 -14
  175. package/src/runtime/agent/orchestrator/session/manager/pending-message-entry.mjs +11 -2
  176. package/src/runtime/agent/orchestrator/session/manager/provider-replay.mjs +13 -0
  177. package/src/runtime/agent/orchestrator/session/manager/route-fallback-chain.mjs +130 -0
  178. package/src/runtime/agent/orchestrator/session/manager/rules-cache.mjs +27 -9
  179. package/src/runtime/agent/orchestrator/session/manager/runtime-liveness.mjs +81 -8
  180. package/src/runtime/agent/orchestrator/session/manager/session-close.mjs +2 -0
  181. package/src/runtime/agent/orchestrator/session/manager/session-lifecycle.mjs +27 -8
  182. package/src/runtime/agent/orchestrator/session/manager/session-prompt-composition.mjs +12 -5
  183. package/src/runtime/agent/orchestrator/session/manager/session-record.mjs +1 -1
  184. package/src/runtime/agent/orchestrator/session/manager/tool-resolution.mjs +9 -4
  185. package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint-context.mjs +4 -0
  186. package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint-journal.mjs +102 -15
  187. package/src/runtime/agent/orchestrator/session/manager/turn-checkpoint.mjs +21 -5
  188. package/src/runtime/agent/orchestrator/session/manager/turn-interruption.mjs +9 -0
  189. package/src/runtime/agent/orchestrator/session/pre-send-compact.mjs +24 -9
  190. package/src/runtime/agent/orchestrator/session/prompt-cache-idle-gaps.mjs +113 -0
  191. package/src/runtime/agent/orchestrator/session/prompt-cache-touch-store.mjs +150 -0
  192. package/src/runtime/agent/orchestrator/session/restart-prefix-parity.fixture.mjs +154 -0
  193. package/src/runtime/agent/orchestrator/session/routine-result.mjs +36 -9
  194. package/src/runtime/agent/orchestrator/session/sensitive-projection.mjs +100 -0
  195. package/src/runtime/agent/orchestrator/session/sensitive-values.mjs +257 -0
  196. package/src/runtime/agent/orchestrator/session/side-question-store.mjs +20 -7
  197. package/src/runtime/agent/orchestrator/session/side-question.mjs +18 -0
  198. package/src/runtime/agent/orchestrator/session/skill-update-notice.mjs +60 -0
  199. package/src/runtime/agent/orchestrator/session/store/live-state.mjs +6 -3
  200. package/src/runtime/agent/orchestrator/session/store/save-delta.mjs +9 -5
  201. package/src/runtime/agent/orchestrator/session/store/serialize.mjs +9 -8
  202. package/src/runtime/agent/orchestrator/session/store/session-delete.mjs +7 -0
  203. package/src/runtime/agent/orchestrator/session/store/session-persistence-events.mjs +29 -0
  204. package/src/runtime/agent/orchestrator/session/store-agent-worker-rows.mjs +8 -6
  205. package/src/runtime/agent/orchestrator/session/store-summary-catalog.mjs +16 -2
  206. package/src/runtime/agent/orchestrator/session/store-summary-fields.mjs +15 -0
  207. package/src/runtime/agent/orchestrator/session/store-summary-index.mjs +81 -22
  208. package/src/runtime/agent/orchestrator/session/store-summary-reader.mjs +92 -3
  209. package/src/runtime/agent/orchestrator/session/stored-attachment-history.mjs +32 -0
  210. package/src/runtime/agent/orchestrator/session/thinking-binding.mjs +108 -0
  211. package/src/runtime/agent/orchestrator/session/tool-batch/pre-dispatch.mjs +2 -2
  212. package/src/runtime/agent/orchestrator/session/tool-batch/record-outcome.mjs +2 -1
  213. package/src/runtime/agent/orchestrator/session/transcript-restore/restore.mjs +79 -3
  214. package/src/runtime/agent/orchestrator/session/transcript-restore/tool-result-status.mjs +9 -7
  215. package/src/runtime/agent/orchestrator/session/transcript-restore/tool-result-text.mjs +2 -2
  216. package/src/runtime/agent/orchestrator/session/turn-failure.mjs +5 -1
  217. package/src/runtime/agent/orchestrator/stall-policy.mjs +23 -0
  218. package/src/runtime/agent/orchestrator/tools/builtin/arg-guard.mjs +5 -2
  219. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/backgrounded-result.mjs +12 -1
  220. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/invocation-plan.mjs +2 -2
  221. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/misuse-guard.mjs +240 -0
  222. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/result-format.mjs +1 -1
  223. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/shell-cwd.mjs +38 -0
  224. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool/spawn-env.mjs +4 -2
  225. package/src/runtime/agent/orchestrator/tools/builtin/bash-tool.mjs +31 -6
  226. package/src/runtime/agent/orchestrator/tools/builtin/builtin-tools.mjs +110 -26
  227. package/src/runtime/agent/orchestrator/tools/builtin/cache-layers.mjs +7 -1
  228. package/src/runtime/agent/orchestrator/tools/builtin/git-command-tool.mjs +31 -5
  229. package/src/runtime/agent/orchestrator/tools/builtin/git-worktree-tool.mjs +22 -8
  230. package/src/runtime/agent/orchestrator/tools/builtin/lib/scoped-search-flight.mjs +9 -5
  231. package/src/runtime/agent/orchestrator/tools/builtin/read-single-stream.mjs +7 -1
  232. package/src/runtime/agent/orchestrator/tools/builtin/read-streaming.mjs +6 -3
  233. package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-dispatch.mjs +1 -1
  234. package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-publication.mjs +23 -12
  235. package/src/runtime/agent/orchestrator/tools/builtin/read-tool/batch-snapshot.mjs +6 -1
  236. package/src/runtime/agent/orchestrator/tools/builtin/read-tool.mjs +1 -8
  237. package/src/runtime/agent/orchestrator/tools/builtin/shell-runtime.mjs +7 -1
  238. package/src/runtime/agent/orchestrator/tools/code-graph/dispatch/federation.mjs +3 -1
  239. package/src/runtime/agent/orchestrator/tools/code-graph-tool-defs.mjs +1 -1
  240. package/src/runtime/agent/orchestrator/tools/graph-manifest.json +13 -13
  241. package/src/runtime/agent/orchestrator/tools/lib/isolated-test-env.mjs +4 -3
  242. package/src/runtime/agent/orchestrator/tools/lib/shell-warm-standby.mjs +26 -4
  243. package/src/runtime/agent/orchestrator/tools/shell-command.mjs +36 -13
  244. package/src/runtime/browser-bridge/action-schema.mjs +13 -2
  245. package/src/runtime/browser-bridge/client.mjs +73 -8
  246. package/src/runtime/browser-bridge/input-fields.mjs +8 -9
  247. package/src/runtime/browser-bridge/mail-links.mjs +107 -0
  248. package/src/runtime/browser-bridge/tool-defs.mjs +1 -1
  249. package/src/runtime/channels/lib/config.mjs +6 -61
  250. package/src/runtime/channels/lib/crash-log.mjs +1 -1
  251. package/src/runtime/channels/lib/event-pipeline.mjs +4 -19
  252. package/src/runtime/channels/lib/event-queue.mjs +3 -18
  253. package/src/runtime/channels/lib/owned-runtime/automation-services.mjs +2 -2
  254. package/src/runtime/channels/lib/owned-runtime/automation-start.mjs +3 -4
  255. package/src/runtime/channels/lib/owned-runtime/config-reload.mjs +4 -59
  256. package/src/runtime/channels/lib/owned-runtime/owned-start.mjs +33 -115
  257. package/src/runtime/channels/lib/owned-runtime/owned-stop.mjs +5 -22
  258. package/src/runtime/channels/lib/owned-runtime/state.mjs +2 -8
  259. package/src/runtime/channels/lib/owned-runtime.mjs +6 -23
  260. package/src/runtime/channels/lib/parent-bridge.mjs +2 -2
  261. package/src/runtime/channels/lib/runtime-paths.mjs +4 -43
  262. package/src/runtime/channels/lib/scheduler.mjs +33 -147
  263. package/src/runtime/channels/lib/schedules-db.mjs +34 -11
  264. package/src/runtime/channels/lib/status-snapshot.mjs +1 -1
  265. package/src/runtime/channels/lib/tool-dispatch.mjs +1 -2
  266. package/src/runtime/channels/lib/webhook/signature.mjs +4 -1
  267. package/src/runtime/channels/lib/webhooks-db.mjs +5 -9
  268. package/src/runtime/channels/lib/whisper-port.mjs +10 -1
  269. package/src/runtime/channels/lib/worker-bootstrap.mjs +0 -1
  270. package/src/runtime/channels/lib/worker-ipc.mjs +0 -1
  271. package/src/runtime/channels/lib/worker-main.mjs +10 -34
  272. package/src/runtime/computer-bridge/action-schema.mjs +42 -1
  273. package/src/runtime/computer-bridge/actions.mjs +9 -1
  274. package/src/runtime/computer-bridge/client.mjs +180 -8
  275. package/src/runtime/computer-bridge/core-actions.mjs +2 -2
  276. package/src/runtime/computer-bridge/error-recovery.mjs +28 -2
  277. package/src/runtime/computer-bridge/linux-action-capabilities.mjs +24 -5
  278. package/src/runtime/computer-bridge/linux-readiness.d.mts +7 -2
  279. package/src/runtime/computer-bridge/linux-readiness.mjs +65 -23
  280. package/src/runtime/computer-bridge/pending-continuation.mjs +1 -1
  281. package/src/runtime/connectors/connector-accounts-mcp.mjs +230 -0
  282. package/src/runtime/connectors/gmail-app-password.mjs +172 -39
  283. package/src/runtime/connectors/google-mcp.mjs +10 -12
  284. package/src/runtime/local-provider/server-process.mjs +2 -1
  285. package/src/runtime/media/adapters/gemini-video.mjs +4 -1
  286. package/src/runtime/media/adapters/xai-media.mjs +2 -1
  287. package/src/runtime/memory/lib/embedding-worker.mjs +6 -3
  288. package/src/runtime/memory/lib/memory-action-handlers/cycle-backfill-action.mjs +1 -7
  289. package/src/runtime/memory/lib/memory-chunk-quality.mjs +1 -6
  290. package/src/runtime/memory/lib/pg/adapter.mjs +77 -70
  291. package/src/runtime/memory/lib/pg/supervisor.mjs +24 -12
  292. package/src/runtime/memory/lib/runtime-fetcher.mjs +23 -5
  293. package/src/runtime/office/authoring/pdf-author-action.mjs +1 -6
  294. package/src/runtime/office/design/design-art-direction.mjs +29 -27
  295. package/src/runtime/office/pdf/pdf-writer.mjs +6 -1
  296. package/src/runtime/office/portable/portable-snapshot-docx.mjs +7 -1
  297. package/src/runtime/office/portable/portable-snapshot-shared.mjs +6 -1
  298. package/src/runtime/office/quality/assurance-rendered.mjs +9 -2
  299. package/src/runtime/office/quality/assurance-structure-docx.mjs +3 -1
  300. package/src/runtime/office/quality/design-review.mjs +1 -5
  301. package/src/runtime/office/quality/document-brief.mjs +1 -5
  302. package/src/runtime/office/quality/forced-break-pages.mjs +9 -6
  303. package/src/runtime/office/quality/quality-pipeline.mjs +1 -1
  304. package/src/runtime/session-search/session-search-db.mjs +73 -9
  305. package/src/runtime/session-search/session-search-ingest.mjs +110 -20
  306. package/src/runtime/shared/abort-race.mjs +89 -0
  307. package/src/runtime/shared/agent-avatar.d.mts +0 -1
  308. package/src/runtime/shared/agent-kind.mjs +4 -3
  309. package/src/runtime/shared/bot-owned-work.mjs +56 -0
  310. package/src/runtime/shared/bounded-download.mjs +8 -3
  311. package/src/runtime/shared/config.mjs +2 -13
  312. package/src/runtime/shared/connector-accounts.mjs +20 -10
  313. package/src/runtime/shared/connector-catalog.d.mts +29 -0
  314. package/src/runtime/shared/connector-catalog.mjs +150 -0
  315. package/src/runtime/shared/connector-triggers.mjs +22 -19
  316. package/src/runtime/shared/defaults-separation.mjs +2 -17
  317. package/src/runtime/shared/delegated-approval-host.mjs +103 -11
  318. package/src/runtime/shared/err-text.mjs +24 -15
  319. package/src/runtime/shared/fetch-safe-listen.d.mts +16 -0
  320. package/src/runtime/shared/fetch-safe-listen.mjs +50 -0
  321. package/src/runtime/shared/file-permissions.d.mts +0 -8
  322. package/src/runtime/shared/file-permissions.mjs +0 -11
  323. package/src/runtime/shared/git-direct.test-support.mjs +19 -0
  324. package/src/runtime/shared/handoff-artifacts.d.mts +2 -1
  325. package/src/runtime/shared/handoff-artifacts.mjs +18 -8
  326. package/src/runtime/shared/heartbeat-interval.d.mts +4 -0
  327. package/src/runtime/shared/heartbeat-interval.mjs +19 -0
  328. package/src/runtime/shared/idle-auto-clear-gate.mjs +126 -0
  329. package/src/runtime/shared/llm/cost.mjs +5 -1
  330. package/src/runtime/shared/llm/usage-rollup.mjs +1 -1
  331. package/src/runtime/shared/loopback-listener.mjs +25 -2
  332. package/src/runtime/shared/mixy-presence.mjs +22 -0
  333. package/src/runtime/shared/model-route-chain.d.mts +7 -2
  334. package/src/runtime/shared/model-route-chain.mjs +22 -4
  335. package/src/runtime/shared/open-url.mjs +10 -0
  336. package/src/runtime/shared/orchestration.d.mts +2 -0
  337. package/src/runtime/shared/pg-schema-db.mjs +27 -16
  338. package/src/runtime/shared/profile-config.cjs +1 -1
  339. package/src/runtime/shared/prompt-origin.d.mts +4 -0
  340. package/src/runtime/shared/prompt-origin.mjs +21 -0
  341. package/src/runtime/shared/provider-accounts.mjs +7 -1
  342. package/src/runtime/shared/provider-display-name.mjs +29 -0
  343. package/src/runtime/shared/provider-timeout-phase.mjs +2 -0
  344. package/src/runtime/shared/routine-trigger.d.mts +2 -0
  345. package/src/runtime/shared/routine-trigger.mjs +10 -0
  346. package/src/runtime/shared/sensitive-path-rules.d.mts +2 -10
  347. package/src/runtime/shared/sensitive-path-rules.mjs +19 -41
  348. package/src/runtime/shared/session-activity-signal.mjs +48 -1
  349. package/src/runtime/shared/session-scratch.mjs +37 -0
  350. package/src/runtime/shared/session-sidebar-host.d.mts +1 -1
  351. package/src/runtime/shared/session-sidebar-host.mjs +7 -3
  352. package/src/runtime/shared/session-turn-prelude.mjs +18 -0
  353. package/src/runtime/shared/tool-card-model/agent-surface.mjs +1 -3
  354. package/src/runtime/shared/tool-card-model/card-status.mjs +15 -2
  355. package/src/runtime/shared/tool-result-summary.mjs +2 -15
  356. package/src/runtime/shared/tool-surface.mjs +3 -0
  357. package/src/runtime/shared/tool-work-units.mjs +2 -0
  358. package/src/runtime/shared/turn-snapshot-store.mjs +13 -6
  359. package/src/runtime/shared/worktrees/contract.mjs +4 -1
  360. package/src/runtime/shared/worktrees/git.mjs +15 -0
  361. package/src/runtime/shared/worktrees/manager.mjs +87 -38
  362. package/src/runtime/shared/worktrees/test-support.mjs +14 -13
  363. package/src/runtime/terminal-bridge/client.mjs +10 -1
  364. package/src/runtime/visualize-bridge/client.mjs +29 -8
  365. package/src/runtime/visualize-bridge/tool-defs.mjs +22 -8
  366. package/src/runtime/visualize-bridge/tool-meta.d.mts +5 -0
  367. package/src/runtime/visualize-bridge/tool-meta.mjs +22 -0
  368. package/src/runtime/web-search/lib/fetch-pipeline.mjs +2 -2
  369. package/src/session-runtime/agent-home-delivery.mjs +489 -185
  370. package/src/session-runtime/agent-task-sessions.mjs +467 -229
  371. package/src/session-runtime/agent-tool-routing.mjs +8 -41
  372. package/src/session-runtime/boot/apis.mjs +9 -0
  373. package/src/session-runtime/boot/infrastructure.mjs +4 -0
  374. package/src/session-runtime/boot/providers.mjs +3 -0
  375. package/src/session-runtime/boot/tools.mjs +11 -2
  376. package/src/session-runtime/bot-status.mjs +12 -6
  377. package/src/session-runtime/bot-target.mjs +38 -0
  378. package/src/session-runtime/channel-config-api.mjs +6 -1
  379. package/src/session-runtime/config-lifecycle.mjs +6 -0
  380. package/src/session-runtime/connector-merge-migration.mjs +305 -0
  381. package/src/session-runtime/conversation-import/codex-titles.mjs +88 -0
  382. package/src/session-runtime/conversation-import/discovery.mjs +271 -25
  383. package/src/session-runtime/conversation-import/service.mjs +26 -5
  384. package/src/session-runtime/handoff-attachments.mjs +82 -31
  385. package/src/session-runtime/internal-tool-executor/ask-user-tool.mjs +144 -41
  386. package/src/session-runtime/internal-tool-executor/bridge-tools.mjs +3 -0
  387. package/src/session-runtime/internal-tool-executor/reaction-tool.mjs +4 -1
  388. package/src/session-runtime/internal-tool-executor/workspace-tools.mjs +8 -2
  389. package/src/session-runtime/lifecycle/cold-heir.mjs +11 -6
  390. package/src/session-runtime/lifecycle/inheritance.mjs +16 -3
  391. package/src/session-runtime/lifecycle/session-catalog.mjs +12 -2
  392. package/src/session-runtime/lifecycle/teardown/runtime-stops.mjs +50 -4
  393. package/src/session-runtime/lifecycle/teardown.mjs +23 -5
  394. package/src/session-runtime/mcp-glue/server-catalog.mjs +55 -3
  395. package/src/session-runtime/mcp-oauth-login.mjs +5 -3
  396. package/src/session-runtime/mixy-heartbeat.mjs +153 -33
  397. package/src/session-runtime/model-route/set-route.mjs +11 -2
  398. package/src/session-runtime/notification-bus.mjs +31 -117
  399. package/src/session-runtime/notification-completion-queue.mjs +54 -0
  400. package/src/session-runtime/notification-listeners.mjs +76 -0
  401. package/src/session-runtime/owned-automation-run.mjs +2 -1
  402. package/src/session-runtime/prewarm/channel-start.mjs +3 -7
  403. package/src/session-runtime/provider-catalog-cache.mjs +82 -36
  404. package/src/session-runtime/provider-models/catalog-load.mjs +23 -6
  405. package/src/session-runtime/provider-models.mjs +4 -2
  406. package/src/session-runtime/resource-mcp-api.mjs +143 -224
  407. package/src/session-runtime/resource-mcp-connector-accounts.mjs +163 -0
  408. package/src/session-runtime/resource-mcp-oauth-api.mjs +217 -0
  409. package/src/session-runtime/resource-mcp-secrets.mjs +82 -0
  410. package/src/session-runtime/resource-mcp-servers.mjs +78 -0
  411. package/src/session-runtime/resource-mcp-store.mjs +49 -0
  412. package/src/session-runtime/resource-recall-api.mjs +6 -1
  413. package/src/session-runtime/routine-owner.mjs +40 -9
  414. package/src/session-runtime/runtime-feature-gates.mjs +5 -1
  415. package/src/session-runtime/services/agent-tool/close-flow.mjs +3 -0
  416. package/src/session-runtime/services/agent-tool/execute.mjs +14 -9
  417. package/src/session-runtime/services/agent-tool/job-views/agent-list.mjs +20 -4
  418. package/src/session-runtime/services/agent-tool/model-select.mjs +48 -7
  419. package/src/session-runtime/services/agent-tool/render.mjs +71 -17
  420. package/src/session-runtime/services/agent-tool/spawn-preset.mjs +13 -4
  421. package/src/session-runtime/services/agent-tool/tag-registry.mjs +1 -0
  422. package/src/session-runtime/services/agent-tool/tool-def.mjs +9 -9
  423. package/src/session-runtime/services/agent-tool/worker-index/awaiting-user-sync.mjs +51 -0
  424. package/src/session-runtime/services/agent-tool/worker-index/disposal.mjs +55 -0
  425. package/src/session-runtime/services/agent-tool/worker-index/released-store.mjs +123 -0
  426. package/src/session-runtime/services/agent-tool/worker-index/restart-settlement.mjs +112 -0
  427. package/src/session-runtime/services/agent-tool/worker-index/row-reads.mjs +36 -0
  428. package/src/session-runtime/services/agent-tool/worker-index/row-shape.mjs +2 -0
  429. package/src/session-runtime/services/agent-tool/worker-index/row-store.mjs +17 -4
  430. package/src/session-runtime/services/agent-tool/worker-index/row-writes.mjs +58 -0
  431. package/src/session-runtime/services/agent-tool/worker-index.mjs +41 -241
  432. package/src/session-runtime/services/agent-tool/worker-rows.mjs +3 -0
  433. package/src/session-runtime/services/channel-admin.mjs +7 -13
  434. package/src/session-runtime/services/channel-session-router.mjs +4 -2
  435. package/src/session-runtime/services/provider-admin.mjs +2 -1
  436. package/src/session-runtime/services/seeds.mjs +0 -28
  437. package/src/session-runtime/session-compaction-sync.mjs +27 -0
  438. package/src/session-runtime/session-create/session-options.mjs +1 -0
  439. package/src/session-runtime/settings-builtin-tools-api.mjs +11 -0
  440. package/src/session-runtime/settings-compaction-api.mjs +2 -40
  441. package/src/session-runtime/settings-system-api.mjs +13 -1
  442. package/src/session-runtime/setup-tool/agent-settings-actions.mjs +65 -0
  443. package/src/session-runtime/setup-tool/executor.mjs +145 -22
  444. package/src/session-runtime/setup-tool/extended-actions.mjs +8 -3
  445. package/src/session-runtime/setup-tool/session-route-actions.mjs +152 -0
  446. package/src/session-runtime/setup-tool/settings-contract.mjs +4 -3
  447. package/src/session-runtime/setup-tool/tool-defs.mjs +64 -5
  448. package/src/session-runtime/tool-policy/agent-profile-fold.mjs +17 -13
  449. package/src/session-runtime/tool-policy/policy-stage.mjs +17 -2
  450. package/src/session-runtime/turn/turn-run/ask-callbacks.mjs +1 -0
  451. package/src/session-runtime/workflow-agents-api/agent-editor.mjs +5 -1
  452. package/src/session-runtime/workflow-agents-api/agent-route.mjs +15 -4
  453. package/src/session-runtime/workflow-agents-api/onboarding.mjs +3 -3
  454. package/src/session-runtime/workflow-agents-api/style-and-mode.mjs +4 -0
  455. package/src/session-runtime/workspace/transitions.mjs +25 -0
  456. package/src/session-runtime/workspace/worktree-tool.mjs +26 -9
  457. package/src/standalone/channel-transport/client-registry/client-records.mjs +65 -0
  458. package/src/standalone/channel-transport/client-registry/client-registration.mjs +118 -0
  459. package/src/standalone/channel-transport/client-registry.mjs +24 -163
  460. package/src/standalone/channel-transport.mjs +1 -1
  461. package/src/standalone/daemon-channels-loader.mjs +10 -8
  462. package/src/standalone/daemon-session-control/list-page.mjs +72 -0
  463. package/src/standalone/daemon-session-control/request.mjs +51 -0
  464. package/src/standalone/daemon-session-control/room-host.mjs +57 -0
  465. package/src/standalone/daemon-session-control/route-control.mjs +48 -0
  466. package/src/standalone/daemon-session-control/send-turn.mjs +60 -0
  467. package/src/standalone/daemon-session-control/worktree-control.mjs +40 -0
  468. package/src/standalone/daemon-session-control.mjs +142 -190
  469. package/src/standalone/daemon.mjs +26 -3
  470. package/src/standalone/session-client.mjs +7 -3
  471. package/src/standalone/session-protocol.mjs +5 -0
  472. package/src/standalone/session-service/agent-tree/agent-child.mjs +1 -0
  473. package/src/standalone/session-service/agent-tree/agent-turns.mjs +16 -12
  474. package/src/standalone/session-service/quota-resume.mjs +3 -0
  475. package/src/standalone/session-service/retention/busy.mjs +65 -1
  476. package/src/standalone/session-service/session-calls/session-action.mjs +30 -2
  477. package/src/standalone/session-service/session-calls/session-views.mjs +8 -0
  478. package/src/standalone/session-tool-output.mjs +15 -7
  479. package/src/standalone/session-transport/client-registry/client-grace.mjs +12 -9
  480. package/src/tui/app/app-view/floating-panel.jsx +7 -4
  481. package/src/tui/app/model-options.mjs +3 -28
  482. package/src/tui/app/model-picker/route-selection/fast-parameters.mjs +1 -3
  483. package/src/tui/app/model-picker/route-selection.mjs +5 -6
  484. package/src/tui/app/provider-setup/oauth-actions.mjs +38 -20
  485. package/src/tui/app/provider-setup/provider-items.mjs +8 -2
  486. package/src/tui/app/provider-setup-picker.mjs +9 -5
  487. package/src/tui/components/QuestionPanel.jsx +13 -4
  488. package/src/tui/dist/index.mjs +133 -92
  489. package/src/tui/session/agent-job-feed/model-notification.mjs +3 -0
  490. package/src/tui/session/initial-state.mjs +3 -0
  491. package/src/tui/session/notice-surface.mjs +7 -1
  492. package/src/tui/session/queue-helpers.mjs +3 -42
  493. package/src/tui/session/session-api/routes-agent-definitions.mjs +14 -2
  494. package/src/tui/session/session-api/routes-write.mjs +5 -1
  495. package/src/tui/session/session-api/routes.mjs +1 -0
  496. package/src/tui/session/session-api/settings.mjs +17 -1
  497. package/src/tui/session/session-flow/auto-clear.mjs +4 -33
  498. package/src/tui/session/session-flow/drain-closed-queue.mjs +38 -0
  499. package/src/tui/session/session-flow/drain-enqueue.mjs +86 -0
  500. package/src/tui/session/session-flow/drain-retry.mjs +35 -0
  501. package/src/tui/session/session-flow/drain.mjs +118 -149
  502. package/src/tui/session/session-flow/queue/entry-shape.mjs +5 -0
  503. package/src/tui/session/session-flow/queue/take-entries.mjs +16 -2
  504. package/src/tui/session/tool-approval-delegation.mjs +64 -0
  505. package/src/tui/session/tool-approval-request.mjs +39 -0
  506. package/src/tui/session/tool-approval-settle.mjs +62 -0
  507. package/src/tui/session/tool-approval.mjs +69 -115
  508. package/src/tui/session/tui-steering-persist.mjs +8 -1
  509. package/src/tui/session/turn-stream.mjs +19 -2
  510. package/src/tui/session/turn.mjs +1 -0
  511. package/src/ui/statusline-agents.mjs +1 -3
  512. package/src/vendor/statusline/bin/statusline-route.mjs +1 -219
  513. package/src/vendor/statusline/src/gateway/route-meta.mjs +35 -13
  514. package/scripts/code-graph-description-contract.mjs +0 -188
  515. package/src/runtime/channels/lib/owned-runtime/ownership-refresh.mjs +0 -36
@@ -115,8 +115,7 @@ function releaseSchedulerRuntime(scheduler) {
115
115
  releaseOwnedSchedulerLock();
116
116
  }
117
117
  class Scheduler {
118
- nonInteractive;
119
- interactive;
118
+ schedules;
120
119
  promptsDir;
121
120
  tickTimer = null;
122
121
  lastFired = /* @__PURE__ */ new Map();
@@ -124,65 +123,28 @@ class Scheduler {
124
123
  running = /* @__PURE__ */ new Set();
125
124
  // Names whose row is being renamed: no fire starts under them meanwhile.
126
125
  renaming = /* @__PURE__ */ new Set();
127
- injectFn = null;
128
- injectReadyFn = null;
129
- pendingCheck = null;
130
126
  // Injected by the host: (schedule, { prompt }) => Promise<{ result }>.
131
127
  scheduleRunner = null;
132
- // Activity tracking
133
- lastActivity = 0;
134
- // timestamp of last inbound message
135
128
  deferred = /* @__PURE__ */ new Map();
136
129
  // name -> deferred-until timestamp
137
130
  cronJobs = /* @__PURE__ */ new Map();
138
131
  // name -> node-cron ScheduledTask for cron-expression entries
139
132
  oneShotTimers = /* @__PURE__ */ new Map();
140
133
  // name -> setTimeout handle for when_at one-shot entries
141
- constructor(nonInteractive, interactive) {
142
- this.nonInteractive = nonInteractive.filter((s) => s.enabled !== false);
143
- this.interactive = interactive.filter((s) => s.enabled !== false);
134
+ constructor(schedules) {
135
+ this.schedules = schedules.filter((s) => s.enabled !== false);
144
136
  this.promptsDir = join(DATA_DIR, 'prompts');
145
- for (const s of [...this.nonInteractive, ...this.interactive]) {
137
+ for (const s of this.schedules) {
146
138
  if (s.lastFiredAt) this.lastFired.set(s.name, new Date(s.lastFiredAt).toISOString());
147
139
  }
148
140
  this.refreshSkipCache();
149
141
  }
150
- setInjectHandler(fn) {
151
- this.injectFn = fn;
152
- }
153
- /** Probe for a live Lead bridge seat. When set, the interactive
154
- * inject only fires while it reports true; otherwise the visible-session
155
- * fallback keeps the fire from being lost. Unset → inject when wired. */
156
- setInjectReadyCheck(fn) {
157
- this.injectReadyFn = typeof fn === 'function' ? fn : null;
158
- }
159
- injectReady() {
160
- if (!this.injectReadyFn) return true;
161
- try {
162
- return !!this.injectReadyFn();
163
- } catch {
164
- return false;
165
- }
166
- }
167
- setPendingCheck(fn) {
168
- this.pendingCheck = typeof fn === 'function' ? fn : null;
169
- }
170
142
  setScheduleRunner(fn) {
171
143
  this.scheduleRunner = typeof fn === 'function' ? fn : null;
172
144
  }
173
- noteActivity() {
174
- this.lastActivity = Date.now();
175
- }
176
- /** Every loaded schedule with its routing type, non-interactive first. */
177
- typedSchedules() {
178
- return [
179
- ...this.nonInteractive.map((schedule) => ({ schedule, type: 'non-interactive' })),
180
- ...this.interactive.map((schedule) => ({ schedule, type: 'interactive' })),
181
- ];
182
- }
183
- /** Find a loaded schedule def by name (either routing bucket). */
145
+ /** Find a loaded schedule def by name. */
184
146
  findSchedule(name) {
185
- return [...this.nonInteractive, ...this.interactive].find((s) => s.name === name) ?? null;
147
+ return this.schedules.find((s) => s.name === name) ?? null;
186
148
  }
187
149
  /** Rebuild the in-memory deferred cache (used by the status snapshot) from
188
150
  * the loaded rows' deferred_until values. Called on construct + reload so
@@ -190,7 +152,7 @@ class Scheduler {
190
152
  refreshSkipCache() {
191
153
  this.deferred.clear();
192
154
  const now = Date.now();
193
- for (const s of [...this.nonInteractive, ...this.interactive]) {
155
+ for (const s of this.schedules) {
194
156
  const until = s.deferredUntil ? new Date(s.deferredUntil).getTime() : 0;
195
157
  if (until > now) this.deferred.set(s.name, until);
196
158
  }
@@ -237,56 +199,6 @@ class Scheduler {
237
199
  if (skippedUntil && now < skippedUntil) until = Math.max(until, skippedUntil);
238
200
  return until;
239
201
  }
240
- /** Get current session activity state.
241
- * Returns { lastActivityMs, pendingWork } — callers apply their own
242
- * thresholds. pendingWork is true when pendingCheck() reports work in
243
- * flight. lastActivityMs is 0 when no activity has been recorded. */
244
- getSessionState() {
245
- let pendingWork = false;
246
- try {
247
- if (this.pendingCheck) pendingWork = !!this.pendingCheck();
248
- } catch {
249
- /* probe failure is not fatal */
250
- }
251
- return { lastActivityMs: this.lastActivity, pendingWork };
252
- }
253
- /** Returns true when the session is considered idle (no pending work and
254
- * lastActivityMs is either 0 or older than the given threshold).
255
- * threshold defaults to 15 minutes but callers should pass their own. */
256
- isSessionIdle(thresholdMs = 15 * 6e4) {
257
- const { lastActivityMs, pendingWork } = this.getSessionState();
258
- if (pendingWork) return false;
259
- if (lastActivityMs === 0) return true;
260
- return Date.now() - lastActivityMs >= thresholdMs;
261
- }
262
- /** Get time context for prompt enrichment */
263
- getTimeContext() {
264
- const now = /* @__PURE__ */ new Date();
265
- const days = ['Sunday', 'Monday', 'Tuesday', 'Wednesday', 'Thursday', 'Friday', 'Saturday'];
266
- const dow = now.getDay();
267
- return {
268
- hour: now.getHours(),
269
- minute: now.getMinutes(),
270
- dayOfWeek: days[dow],
271
- isWeekend: dow === 0 || dow === 6,
272
- };
273
- }
274
- /** Wrap prompt with session context metadata */
275
- wrapPrompt(name, prompt, type) {
276
- const { lastActivityMs, pendingWork } = this.getSessionState();
277
- let state = 'recent';
278
- if (pendingWork) state = 'active';
279
- else if (lastActivityMs === 0) state = 'idle';
280
- const time = this.getTimeContext();
281
- const header = [
282
- `[schedule: ${name} | type: ${type} | session: ${state}]`,
283
- `[time: ${time.dayOfWeek} ${String(time.hour).padStart(2, '0')}:${String(time.minute).padStart(2, '0')} | weekend: ${time.isWeekend}]`,
284
- `Before starting any work, briefly tell the user what you're about to do in one short sentence.`,
285
- ].join('\n');
286
- return `${header}
287
-
288
- ${prompt}`;
289
- }
290
202
  static SCHEDULER_LOCK = join(resolveRuntimeRoot(), 'scheduler.lock');
291
203
  static INSTANCE_UUID = randomUUID();
292
204
  static _exitHookInstalled = false;
@@ -345,8 +257,7 @@ ${prompt}`;
345
257
 
346
258
  start() {
347
259
  if (this.tickTimer) return;
348
- const total = this.nonInteractive.length + this.interactive.length;
349
- if (total === 0) {
260
+ if (this.schedules.length === 0) {
350
261
  process.stderr.write('mixdog scheduler: no schedules configured\n');
351
262
  return;
352
263
  }
@@ -365,7 +276,7 @@ ${prompt}`;
365
276
  Scheduler._exitHookInstalled = true;
366
277
  process.on('exit', releaseOwnedSchedulerLock);
367
278
  }
368
- logSchedule(`${this.nonInteractive.length} non-interactive, ${this.interactive.length} interactive\n`);
279
+ logSchedule(`${this.schedules.length} schedules\n`);
369
280
  this.registerCronJobs();
370
281
  this.tick();
371
282
  this.tickTimer = setInterval(() => this.tick(), TICK_INTERVAL);
@@ -373,14 +284,14 @@ ${prompt}`;
373
284
  /** Register schedule entries. `when_cron` entries bind to node-cron (dow
374
285
  * field covers the day guard); `when_at` entries arm a one-shot timer. */
375
286
  registerCronJobs() {
376
- for (const { schedule: s, type } of this.typedSchedules()) {
287
+ for (const s of this.schedules) {
377
288
  if (s.whenCron) {
378
289
  if (!isCronExpression(s.whenCron)) {
379
290
  process.stderr.write(`mixdog scheduler: invalid cron "${s.name}" (${s.whenCron}) — skipped\n`);
380
291
  continue;
381
292
  }
382
293
  try {
383
- const task = cron.schedule(s.whenCron, (ctx) => this.onCronFire(s, type, ctx?.date), {
294
+ const task = cron.schedule(s.whenCron, (ctx) => this.onCronFire(s, ctx?.date), {
384
295
  timezone: s.timezone || undefined,
385
296
  name: s.name,
386
297
  });
@@ -397,13 +308,13 @@ ${prompt}`;
397
308
  process.stderr.write(`mixdog scheduler: failed to register cron "${s.name}" (${s.whenCron}): ${err}\n`);
398
309
  }
399
310
  } else if (s.whenAt) {
400
- this.armOneShot(s, type);
311
+ this.armOneShot(s);
401
312
  }
402
313
  }
403
314
  }
404
315
  /** Fire path for a cron-triggered entry. node-cron's dow field covers the
405
316
  * day guard, so there is no separate days filter. Persists last_fired_at. */
406
- async onCronFire(schedule, type, scheduledDate = null) {
317
+ async onCronFire(schedule, scheduledDate = null) {
407
318
  const startedAt = /* @__PURE__ */ new Date();
408
319
  const scheduledAt =
409
320
  scheduledDate instanceof Date && Number.isFinite(scheduledDate.getTime()) ? scheduledDate : startedAt;
@@ -438,7 +349,7 @@ ${prompt}`;
438
349
  this.recordRefusal(schedule, refusal);
439
350
  return;
440
351
  }
441
- const fired = await this.fireTimed(schedule, type, { awaitDispatch: true, reserved: true });
352
+ const fired = await this.fireTimed(schedule, { awaitDispatch: true, reserved: true });
442
353
  // An overlap skip is recorded as a skip, never as a failed run.
443
354
  if (!fired && skippedSince(schedule, startedAt)) return;
444
355
  if (!fired) {
@@ -481,7 +392,7 @@ ${prompt}`;
481
392
  * entries (misfire recovery at start) fire immediately. setTimeout's
482
393
  * ~24.8-day (2^31-1 ms) ceiling is handled by re-arming for far-future
483
394
  * instants instead of firing early. */
484
- armOneShot(schedule, type) {
395
+ armOneShot(schedule) {
485
396
  const fireAt = new Date(schedule.whenAt).getTime();
486
397
  if (!Number.isFinite(fireAt)) {
487
398
  process.stderr.write(`mixdog scheduler: invalid when_at for "${schedule.name}" (${schedule.whenAt}) — skipped\n`);
@@ -489,11 +400,11 @@ ${prompt}`;
489
400
  }
490
401
  const delay = fireAt - Date.now();
491
402
  if (delay > MAX_TIMER_DELAY_MS) {
492
- const timer = setTimeout(() => this.armOneShot(schedule, type), MAX_TIMER_DELAY_MS);
403
+ const timer = setTimeout(() => this.armOneShot(schedule), MAX_TIMER_DELAY_MS);
493
404
  this.oneShotTimers.set(schedule.name, timer);
494
405
  return;
495
406
  }
496
- const timer = setTimeout(() => this.fireOneShot(schedule, type), Math.max(0, delay));
407
+ const timer = setTimeout(() => this.fireOneShot(schedule), Math.max(0, delay));
497
408
  this.oneShotTimers.set(schedule.name, timer);
498
409
  schedule.nextFireAt = new Date(fireAt).toISOString();
499
410
  void setNextFire(schedule.name, new Date(fireAt)).catch(() => {});
@@ -521,7 +432,7 @@ ${prompt}`;
521
432
  * Idempotent: if last_fired_at is already set (a prior fire whose markDone
522
433
  * failed left the row 'active'), do NOT fire again — only retry markDone so
523
434
  * the stuck-active entry stops re-arming/misfiring. */
524
- async fireOneShot(schedule, type) {
435
+ async fireOneShot(schedule) {
525
436
  this.oneShotTimers.delete(schedule.name);
526
437
  const now = /* @__PURE__ */ new Date();
527
438
  if (schedule.lastFiredAt) {
@@ -530,7 +441,7 @@ ${prompt}`;
530
441
  return;
531
442
  }
532
443
  if (this.shouldSkip(schedule.name)) {
533
- this.rearmDeferredOneShot(schedule, type);
444
+ this.rearmDeferredOneShot(schedule);
534
445
  return;
535
446
  }
536
447
  // Mark done ONLY after a successful fire. A false/throwing fireTimed
@@ -546,7 +457,7 @@ ${prompt}`;
546
457
  // dispatch outcome — a truthy fireTimed alone (cron's fire-and-forget
547
458
  // contract) would retire the entry even when schedulerLlm() later
548
459
  // rejects. Only a resolved dispatch counts as a real fire here.
549
- const fired = await this.fireTimed(schedule, type, { awaitDispatch: true, reserved });
460
+ const fired = await this.fireTimed(schedule, { awaitDispatch: true, reserved });
550
461
  if (!fired && skippedSince(schedule, now)) {
551
462
  logSchedule(`one-shot "${schedule.name}" skipped (previous run in progress) — leaving pending for retry\n`);
552
463
  return;
@@ -571,13 +482,13 @@ ${prompt}`;
571
482
  * already elapsed and tickAsync is a no-op, so simply returning would mean
572
483
  * it never fires until a restart. Re-arm for the deferral expiry (the
573
484
  * later of when_at and deferred/skipped-until) so it fires on its own. */
574
- rearmDeferredOneShot(schedule, type) {
485
+ rearmDeferredOneShot(schedule) {
575
486
  const until = this.skipUntil(schedule.name);
576
487
  const fireAt = new Date(schedule.whenAt).getTime();
577
488
  const target = Math.max(Number.isFinite(fireAt) ? fireAt : 0, until);
578
489
  const delay = Math.min(Math.max(target - Date.now(), 1), MAX_TIMER_DELAY_MS);
579
490
  logSchedule(`one-shot "${schedule.name}" deferred/skipped — re-arming for ${new Date(target).toISOString()}\n`);
580
- const timer = setTimeout(() => this.fireOneShot(schedule, type), delay);
491
+ const timer = setTimeout(() => this.fireOneShot(schedule), delay);
581
492
  this.oneShotTimers.set(schedule.name, timer);
582
493
  schedule.nextFireAt = new Date(target).toISOString();
583
494
  void setNextFire(schedule.name, new Date(target)).catch(() => {});
@@ -643,15 +554,13 @@ ${prompt}`;
643
554
  this.oneShotTimers.delete(name);
644
555
  this.lastFired.delete(name);
645
556
  this.deferred.delete(name);
646
- this.nonInteractive = this.nonInteractive.filter((s) => s.name !== name);
647
- this.interactive = this.interactive.filter((s) => s.name !== name);
557
+ this.schedules = this.schedules.filter((s) => s.name !== name);
648
558
  }
649
- reloadConfig(nonInteractive, interactive, options = {}) {
650
- this.nonInteractive = nonInteractive.filter((s) => s.enabled !== false);
651
- this.interactive = interactive.filter((s) => s.enabled !== false);
559
+ reloadConfig(schedules, options = {}) {
560
+ this.schedules = schedules.filter((s) => s.enabled !== false);
652
561
  this.promptsDir = join(DATA_DIR, 'prompts');
653
562
  // A name that no longer exists must not keep (or later regain) a stamp.
654
- const live = new Set([...this.nonInteractive, ...this.interactive].map((s) => s.name));
563
+ const live = new Set(this.schedules.map((s) => s.name));
655
564
  for (const name of this.lastFired.keys()) if (!live.has(name)) this.lastFired.delete(name);
656
565
  // Defer/skip state is persisted (deferred_until / skipped_until) and
657
566
  // re-read from the reloaded rows, so a reload no longer drops it.
@@ -664,10 +573,9 @@ ${prompt}`;
664
573
  this.restart();
665
574
  }
666
575
  getStatus() {
667
- return this.typedSchedules().map(({ schedule: s, type }) => ({
576
+ return this.schedules.map((s) => ({
668
577
  name: s.name,
669
578
  time: s.whenCron ?? s.whenAt ?? null,
670
- type,
671
579
  running: this.running.has(s.name),
672
580
  lastFired: this.lastFired.get(s.name) ?? s.lastFiredAt ?? null,
673
581
  lastSuccess: s.lastSuccessAt ?? null,
@@ -679,14 +587,13 @@ ${prompt}`;
679
587
  const timed = this.findSchedule(name);
680
588
  if (timed) {
681
589
  if (this.running.has(name)) return `"${name}" is already running`;
682
- const isNonInteractive = this.nonInteractive.includes(timed);
683
590
  const now = /* @__PURE__ */ new Date();
684
591
  const hhmm = `${String(now.getHours()).padStart(2, '0')}:${String(now.getMinutes()).padStart(2, '0')}`;
685
592
  const dateStr = `${now.getFullYear()}-${String(now.getMonth() + 1).padStart(2, '0')}-${String(now.getDate()).padStart(2, '0')}`;
686
593
  // Match onCronFire: record lastFired only when fireTimed actually
687
594
  // proceeds past its running/precondition guards (resolves truthy),
688
595
  // and reflect a non-fire in the returned status.
689
- const fired = await this.fireTimed(timed, isNonInteractive ? 'non-interactive' : 'interactive');
596
+ const fired = await this.fireTimed(timed);
690
597
  if (fired) {
691
598
  this.lastFired.set(name, `${dateStr}T${hhmm}`);
692
599
  return `triggered "${name}"`;
@@ -708,7 +615,7 @@ ${prompt}`;
708
615
  // interval is kept for future cadence-driven work and lifecycle parity.
709
616
  }
710
617
  // ── Fire timed schedule ─────────────────────────────────────────────
711
- async fireTimed(schedule, type, opts = {}) {
618
+ async fireTimed(schedule, opts = {}) {
712
619
  const prompt = this.resolvePrompt(schedule);
713
620
  if (!prompt) {
714
621
  process.stderr.write(`mixdog scheduler: prompt not found for "${schedule.name}"
@@ -716,7 +623,7 @@ ${prompt}`;
716
623
  this.notifyFailure(schedule, 'prompt not found — fire skipped');
717
624
  return false;
718
625
  }
719
- return await this.fireTimedPrompt(schedule, type, prompt, opts);
626
+ return await this.fireTimedPrompt(schedule, prompt, opts);
720
627
  }
721
628
  /** Why a fire of `name` may not start now: 'renaming', 'running' or null. */
722
629
  fireRefusal(name) {
@@ -739,14 +646,13 @@ ${prompt}`;
739
646
  }
740
647
  /** Fire a timed schedule with the given prompt content. `reserved`: the
741
648
  * caller already holds the name in `running` and releases it itself. */
742
- async fireTimedPrompt(schedule, type, prompt, { awaitDispatch = false, reserved = false } = {}) {
743
- logSchedule(`firing ${schedule.name} (${type})\n`);
649
+ async fireTimedPrompt(schedule, prompt, { awaitDispatch = false, reserved = false } = {}) {
650
+ logSchedule(`firing ${schedule.name}\n`);
744
651
  const refusal = reserved ? null : this.fireRefusal(schedule.name);
745
652
  if (refusal) {
746
653
  this.recordRefusal(schedule, refusal);
747
654
  return false;
748
655
  }
749
- if (type === 'interactive' && this.injectIntoLead(schedule, type, prompt)) return true;
750
656
  if (!reserved) this.running.add(schedule.name);
751
657
  // Cron (recurring) keeps the fire-and-forget contract: return truthy now
752
658
  // and swallow async failures. A one-shot (awaitDispatch) instead awaits
@@ -757,28 +663,8 @@ ${prompt}`;
757
663
  if (awaitDispatch) return await dispatch;
758
664
  return true;
759
665
  }
760
- /** Interactive schedules enqueue into the live Lead session's command
761
- * queue as system-generated task notifications (priority 'later'),
762
- * exactly like inbound channel messages — enqueue counts as the fire.
763
- * False when no live Lead seat is attached or the inject fails, so the
764
- * visible-session run remains the fallback and a fire is never lost. */
765
- injectIntoLead(schedule, type, prompt) {
766
- if (!this.injectFn || !this.injectReady()) return false;
767
- try {
768
- const wrapped = this.wrapPrompt(schedule.name, prompt, type);
769
- this.injectFn('', `schedule:${schedule.name}`, ' ', { type: 'schedule', instruction: wrapped });
770
- logSchedule(`${schedule.name}: injected into Lead session queue (interactive fire)\n`);
771
- return true;
772
- } catch (err) {
773
- logSchedule(
774
- `${schedule.name}: Lead inject failed (${err?.message || err}) — falling back to visible session run\n`
775
- );
776
- return false;
777
- }
778
- }
779
666
  /** Fires run as VISIBLE schedule sessions (desktop Recent / TUI resume)
780
- * via runScheduleSession; the wrapped prompt keeps the schedule context
781
- * header. Resolves true on success; a failure rejects for awaitDispatch
667
+ * via runScheduleSession. Resolves true on success; a failure rejects for awaitDispatch
782
668
  * callers and resolves false (after a logged notice) for fire-and-forget
783
669
  * cron fires. */
784
670
  dispatchScheduleRun(schedule, prompt, awaitDispatch) {
@@ -26,8 +26,6 @@ CREATE TABLE IF NOT EXISTS scheduler.schedules (
26
26
  when_at timestamptz,
27
27
  when_cron text,
28
28
  timezone text,
29
- target text NOT NULL CHECK (target IN ('channel','session')),
30
- channel_id text,
31
29
  model text,
32
30
  cwd text,
33
31
  workflow text,
@@ -90,8 +88,6 @@ function rowToDef(row) {
90
88
  whenAt: row.when_at,
91
89
  whenCron: row.when_cron,
92
90
  timezone: row.timezone,
93
- target: row.target,
94
- channelId: row.channel_id,
95
91
  cwd: row.cwd,
96
92
  attachments: row.attachments || null,
97
93
  delivery: row.delivery || null,
@@ -115,8 +111,32 @@ function rowToDef(row) {
115
111
  };
116
112
  }
117
113
 
114
+ // A table created by an older release still has `target` as a NOT NULL column
115
+ // with no default, so an insert must keep filling it; every schedule runs as a
116
+ // session. A table created now has no such column. The schema is probed once
117
+ // per connection; the column is never read, altered or dropped.
118
+ const requiredTargetColumn = new WeakMap();
119
+ function hasRequiredTargetColumn(db) {
120
+ if (!requiredTargetColumn.has(db)) {
121
+ requiredTargetColumn.set(
122
+ db,
123
+ db
124
+ .query(
125
+ `SELECT column_name FROM information_schema.columns
126
+ WHERE table_schema = 'scheduler' AND table_name = 'schedules' AND column_name = 'target'`
127
+ )
128
+ .then(({ rows }) => rows.some((row) => row.column_name === 'target'))
129
+ .catch((error) => {
130
+ requiredTargetColumn.delete(db);
131
+ throw error;
132
+ })
133
+ );
134
+ }
135
+ return requiredTargetColumn.get(db);
136
+ }
137
+
118
138
  const COLS =
119
- 'name, description, when_at, when_cron, timezone, target, channel_id, cwd, attachments, delivery, prompt, enabled, status, last_fired_at, last_scheduled_at, last_started_at, last_success_at, last_failed_at, last_skipped_at, owner_agent_id, consecutive_failures, result_delivery, next_fire_at, deferred_until, skipped_until, created_at, updated_at';
139
+ 'name, description, when_at, when_cron, timezone, cwd, attachments, delivery, prompt, enabled, status, last_fired_at, last_scheduled_at, last_started_at, last_success_at, last_failed_at, last_skipped_at, owner_agent_id, consecutive_failures, result_delivery, next_fire_at, deferred_until, skipped_until, created_at, updated_at';
120
140
 
121
141
  // ---------------------------------------------------------------------------
122
142
  // Public API
@@ -148,8 +168,6 @@ export async function upsertSchedule(def, { dataDir } = {}) {
148
168
  def.whenAt ?? null,
149
169
  def.whenCron ?? null,
150
170
  def.timezone ?? null,
151
- def.target,
152
- def.channelId ?? null,
153
171
  def.cwd ?? null,
154
172
  def.attachments ? JSON.stringify(def.attachments) : null,
155
173
  def.delivery ?? null,
@@ -159,18 +177,23 @@ export async function upsertSchedule(def, { dataDir } = {}) {
159
177
  def.nextFireAt ?? null,
160
178
  def.ownerAgentId || 'lead',
161
179
  ];
180
+ let legacyTarget = '';
181
+ let legacyTargetValue = '';
182
+ if (await hasRequiredTargetColumn(db)) {
183
+ params.push('session');
184
+ legacyTarget = ', target';
185
+ legacyTargetValue = `,$${params.length}`;
186
+ }
162
187
  const { rows } = await db.query(
163
188
  `INSERT INTO scheduler.schedules
164
- (name, description, when_at, when_cron, timezone, target, channel_id, cwd, attachments, delivery, prompt, enabled, status, next_fire_at, owner_agent_id)
165
- VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12,$13,$14,$15)
189
+ (name, description, when_at, when_cron, timezone, cwd, attachments, delivery, prompt, enabled, status, next_fire_at, owner_agent_id${legacyTarget})
190
+ VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12,$13${legacyTargetValue})
166
191
  ON CONFLICT (name) DO UPDATE SET
167
192
  owner_agent_id = EXCLUDED.owner_agent_id,
168
193
  description = EXCLUDED.description,
169
194
  when_at = EXCLUDED.when_at,
170
195
  when_cron = EXCLUDED.when_cron,
171
196
  timezone = EXCLUDED.timezone,
172
- target = EXCLUDED.target,
173
- channel_id = EXCLUDED.channel_id,
174
197
  cwd = EXCLUDED.cwd,
175
198
  attachments = EXCLUDED.attachments,
176
199
  delivery = EXCLUDED.delivery,
@@ -57,7 +57,7 @@ function* armedScheduleFires(scheduler) {
57
57
  const fireAt = cronTaskNextFireAt(task);
58
58
  if (fireAt !== null) yield { name, fireAt, kind: 'cron' };
59
59
  }
60
- const defs = [...(scheduler.nonInteractive || []), ...(scheduler.interactive || [])];
60
+ const defs = scheduler.schedules || [];
61
61
  for (const name of (scheduler.oneShotTimers || new Map()).keys()) {
62
62
  if (scheduler.shouldSkip?.(name)) continue;
63
63
  const def = defs.find((s) => s.name === name);
@@ -1,6 +1,5 @@
1
1
  // Worker/HTTP runtime-lifecycle dispatch (activate_channel_bridge /
2
- // reload_config). Channel messaging — forwarder, transcript binding, typing —
3
- // is deleted with Discord/Telegram; only the automation lifecycle remains.
2
+ // reload_config). Only the automation lifecycle is dispatched here.
4
3
  // Lifecycle functions are threaded in as a bag of lazy getters so the module
5
4
  // reads the live file-level references at call time.
6
5
  import { scheduleErrorFields } from './schedule-errors.mjs';
@@ -46,7 +46,10 @@ function verifySignature(secret, rawBody, signatureValue, parser) {
46
46
  if (!vMatch || !tMatch) return false;
47
47
  const ts = Number(tMatch[1]);
48
48
  if (!Number.isFinite(ts) || Math.abs(Date.now() - ts * 1000) > STRIPE_TOLERANCE_MS) return false;
49
- const expected = crypto.createHmac('sha256', secret).update(Buffer.concat([Buffer.from(`${tMatch[1]}.`), Buffer.from(rawBody)])).digest('hex');
49
+ const expected = crypto
50
+ .createHmac('sha256', secret)
51
+ .update(Buffer.concat([Buffer.from(`${tMatch[1]}.`), Buffer.from(rawBody)]))
52
+ .digest('hex');
50
53
  return hexDigestsEqual(vMatch[1], expected);
51
54
  }
52
55
  const expected = crypto.createHmac('sha256', secret).update(rawBody).digest('hex');
@@ -26,8 +26,7 @@ CREATE SCHEMA IF NOT EXISTS webhooks;
26
26
  CREATE TABLE IF NOT EXISTS webhooks.endpoints (
27
27
  name text PRIMARY KEY,
28
28
  description text NOT NULL DEFAULT '',
29
- channel_id text,
30
- role text NOT NULL DEFAULT '',
29
+ role text NOT NULL DEFAULT '',
31
30
  model text,
32
31
  parser text,
33
32
  secret text,
@@ -87,14 +86,13 @@ const getDb = createPgSchemaDb({
87
86
  // The stored payload itself is never projected here (readEndpointLastPayload
88
87
  // is its only read path); rows carry a presence flag.
89
88
  const ENDPOINT_COLS =
90
- 'name, description, channel_id, parser, secret, cwd, attachments, delivery, instructions, enabled, owner_agent_id, last_event_at, last_success_at, last_failed_at, last_skipped_at, consecutive_failures, result_delivery, (last_payload IS NOT NULL) AS has_last_payload, created_at, updated_at';
89
+ 'name, description, parser, secret, cwd, attachments, delivery, instructions, enabled, owner_agent_id, last_event_at, last_success_at, last_failed_at, last_skipped_at, consecutive_failures, result_delivery, (last_payload IS NOT NULL) AS has_last_payload, created_at, updated_at';
91
90
 
92
91
  function rowToEndpoint(row) {
93
92
  if (!row) return null;
94
93
  return {
95
94
  name: row.name,
96
95
  description: row.description,
97
- channelId: row.channel_id,
98
96
  parser: row.parser,
99
97
  cwd: row.cwd,
100
98
  attachments: row.attachments || null,
@@ -180,7 +178,6 @@ export async function upsertEndpoint(def, { dataDir } = {}) {
180
178
  const params = [
181
179
  def.name,
182
180
  def.description ?? '',
183
- def.channelId ?? null,
184
181
  '',
185
182
  def.parser ?? null,
186
183
  def.secret ?? null,
@@ -195,13 +192,12 @@ export async function upsertEndpoint(def, { dataDir } = {}) {
195
192
  // not the definition.
196
193
  const { rows } = await db.query(
197
194
  `INSERT INTO webhooks.endpoints
198
- (name, description, channel_id, role, parser, secret, cwd, attachments, delivery, instructions, enabled, owner_agent_id)
199
- VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11,$12)
195
+ (name, description, role, parser, secret, cwd, attachments, delivery, instructions, enabled, owner_agent_id)
196
+ VALUES ($1,$2,$3,$4,$5,$6,$7,$8,$9,$10,$11)
200
197
  ON CONFLICT (name) DO UPDATE SET
201
198
  owner_agent_id = EXCLUDED.owner_agent_id,
202
199
  description = EXCLUDED.description,
203
- channel_id = EXCLUDED.channel_id,
204
- role = EXCLUDED.role,
200
+ role = EXCLUDED.role,
205
201
  parser = EXCLUDED.parser,
206
202
  secret = EXCLUDED.secret,
207
203
  cwd = EXCLUDED.cwd,
@@ -1,6 +1,7 @@
1
1
  import net from 'node:net';
2
2
  import path from 'node:path';
3
3
  import { execFile } from 'node:child_process';
4
+ import { FETCH_BLOCKED_PORTS, FETCH_SAFE_ATTEMPTS } from '../../shared/fetch-safe-listen.mjs';
4
5
 
5
6
  // whisper.cpp cannot bind port 0 itself. Ask the OS for an available port,
6
7
  // release the reservation immediately before spawn, then verify the listener's
@@ -15,9 +16,17 @@ export function selectWhisperPort(host, preferred) {
15
16
  server.close((error) => (error ? reject(error) : resolve(selected)));
16
17
  });
17
18
  });
19
+ // The server is reached with fetch, which refuses a "bad port" the OS may assign.
20
+ const reserveFetchSafe = async () => {
21
+ for (let attempt = 0; attempt <= FETCH_SAFE_ATTEMPTS; attempt += 1) {
22
+ const port = await reserve(0);
23
+ if (!FETCH_BLOCKED_PORTS.has(port)) return port;
24
+ }
25
+ throw new Error('no fetch-safe loopback port was assigned');
26
+ };
18
27
  return reserve(preferred).catch((error) => {
19
28
  if (error.code !== 'EADDRINUSE' && error.code !== 'EACCES') throw error;
20
- return reserve(0);
29
+ return reserveFetchSafe();
21
30
  });
22
31
  }
23
32
 
@@ -102,7 +102,6 @@ export function runWorkerBootstrap({
102
102
  // Publish owner identity immediately so the SessionStart shim's
103
103
  // owner_lead_alive() sees a live owner and uses the full connect budget
104
104
  // instead of the 5s no-owner grace (fixes missing recap/core on restart).
105
- // providerReady intentionally omitted — readiness stays gated until connect.
106
105
  try {
107
106
  refreshActiveInstance(instanceId);
108
107
  } catch (e) {
@@ -11,7 +11,6 @@ export function runWorkerIpc({
11
11
  clearServerPid,
12
12
  instanceId,
13
13
  statusState: _statusState,
14
- getProvider: _getProvider,
15
14
  getConfig: _getConfig,
16
15
  handleMemoryCallResponse,
17
16
  handleToolCall,