@cjhyy/code-shell-core 0.5.0-rc.2 → 0.6.0-rc.2

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 (387) hide show
  1. package/README.md +13 -10
  2. package/dist/agent/agent-definition-registry.d.ts +3 -0
  3. package/dist/agent/agent-definition-registry.js +3 -1
  4. package/dist/agent/agent-definition.d.ts +15 -0
  5. package/dist/agent/agent-definition.js +27 -3
  6. package/dist/arena/context/context-tools.js +47 -4
  7. package/dist/arena/ledger.js +9 -1
  8. package/dist/arena/strategies/utils.d.ts +1 -4
  9. package/dist/arena/strategies/utils.js +7 -84
  10. package/dist/automation/cron-expr.d.ts +10 -0
  11. package/dist/automation/cron-expr.js +23 -5
  12. package/dist/automation/runner.d.ts +21 -4
  13. package/dist/automation/runner.js +48 -12
  14. package/dist/automation/scheduler.d.ts +38 -0
  15. package/dist/automation/scheduler.js +89 -12
  16. package/dist/automation/store.js +5 -2
  17. package/dist/capability-control/disabled-lists.d.ts +25 -0
  18. package/dist/capability-control/disabled-lists.js +57 -0
  19. package/dist/capability-control/overlay.d.ts +15 -0
  20. package/dist/capability-control/overlay.js +27 -0
  21. package/dist/cc-orchestrator/agent-adapter.d.ts +50 -0
  22. package/dist/cc-orchestrator/agent-adapter.js +133 -0
  23. package/dist/cc-orchestrator/cc-capability.d.ts +19 -0
  24. package/dist/cc-orchestrator/cc-capability.js +53 -0
  25. package/dist/cc-orchestrator/codex-session-discovery.d.ts +24 -0
  26. package/dist/cc-orchestrator/codex-session-discovery.js +191 -0
  27. package/dist/cc-orchestrator/codex-session-history.d.ts +25 -0
  28. package/dist/cc-orchestrator/codex-session-history.js +187 -0
  29. package/dist/cc-orchestrator/external-agent-changes.d.ts +19 -0
  30. package/dist/cc-orchestrator/external-agent-changes.js +214 -0
  31. package/dist/cc-orchestrator/external-agent-driver.d.ts +18 -0
  32. package/dist/cc-orchestrator/external-agent-driver.js +69 -0
  33. package/dist/cc-orchestrator/index.d.ts +8 -0
  34. package/dist/cc-orchestrator/index.js +8 -0
  35. package/dist/cc-orchestrator/relevance-judge.d.ts +15 -0
  36. package/dist/cc-orchestrator/relevance-judge.js +29 -0
  37. package/dist/cc-orchestrator/session-discovery.d.ts +46 -0
  38. package/dist/cc-orchestrator/session-discovery.js +125 -0
  39. package/dist/cc-orchestrator/session-history.d.ts +19 -0
  40. package/dist/cc-orchestrator/session-history.js +67 -0
  41. package/dist/cli/agent-server-stdio.d.ts +15 -1
  42. package/dist/cli/agent-server-stdio.js +115 -17
  43. package/dist/cli/agent-server-tcp.js +40 -26
  44. package/dist/context/compaction.d.ts +56 -0
  45. package/dist/context/compaction.js +186 -0
  46. package/dist/context/manager.js +25 -4
  47. package/dist/cost-tracker.js +5 -61
  48. package/dist/credentials/cipher.d.ts +49 -0
  49. package/dist/credentials/cipher.js +45 -0
  50. package/dist/credentials/cookie-jar.d.ts +24 -0
  51. package/dist/credentials/cookie-jar.js +40 -0
  52. package/dist/credentials/index.d.ts +7 -0
  53. package/dist/credentials/index.js +5 -0
  54. package/dist/credentials/inject-credential-tool.d.ts +20 -0
  55. package/dist/credentials/inject-credential-tool.js +130 -0
  56. package/dist/credentials/store.d.ts +72 -0
  57. package/dist/credentials/store.js +184 -0
  58. package/dist/credentials/types.d.ts +56 -0
  59. package/dist/credentials/use-credential-tool.d.ts +29 -0
  60. package/dist/credentials/use-credential-tool.js +205 -0
  61. package/dist/credentials/use-gate.d.ts +56 -0
  62. package/dist/credentials/use-gate.js +52 -0
  63. package/dist/data/model-metadata.d.ts +77 -0
  64. package/dist/data/model-metadata.js +56 -0
  65. package/dist/data/model-metadata.json +216 -0
  66. package/dist/data/openrouter-models.d.ts +18 -7
  67. package/dist/data/openrouter-models.js +35 -8
  68. package/dist/engine/aux-key.d.ts +10 -0
  69. package/dist/engine/aux-key.js +11 -0
  70. package/dist/engine/dynamic-tool-defs.d.ts +19 -0
  71. package/dist/engine/dynamic-tool-defs.js +36 -0
  72. package/dist/engine/engine.d.ts +267 -138
  73. package/dist/engine/engine.js +957 -191
  74. package/dist/engine/friendly-error.d.ts +18 -0
  75. package/dist/engine/friendly-error.js +63 -0
  76. package/dist/engine/goal.d.ts +145 -0
  77. package/dist/engine/goal.js +144 -0
  78. package/dist/engine/image-policy.d.ts +13 -0
  79. package/dist/engine/image-policy.js +24 -0
  80. package/dist/engine/model-connections-pool.d.ts +17 -0
  81. package/dist/engine/model-connections-pool.js +66 -0
  82. package/dist/engine/model-facade.d.ts +10 -0
  83. package/dist/engine/model-facade.js +25 -0
  84. package/dist/engine/patch-orphaned-tools.js +3 -0
  85. package/dist/engine/resolve-llm-config.d.ts +16 -0
  86. package/dist/engine/resolve-llm-config.js +44 -0
  87. package/dist/engine/runtime.js +2 -1
  88. package/dist/engine/sandbox-cache-key.d.ts +10 -0
  89. package/dist/engine/sandbox-cache-key.js +9 -0
  90. package/dist/engine/sandbox-config.d.ts +31 -0
  91. package/dist/engine/sandbox-config.js +38 -0
  92. package/dist/engine/session-usage.d.ts +19 -0
  93. package/dist/engine/session-usage.js +25 -0
  94. package/dist/engine/steer-queue.d.ts +32 -0
  95. package/dist/engine/steer-queue.js +26 -0
  96. package/dist/engine/streaming-tool-queue.d.ts +12 -0
  97. package/dist/engine/streaming-tool-queue.js +50 -10
  98. package/dist/engine/turn-loop.d.ts +67 -3
  99. package/dist/engine/turn-loop.js +292 -41
  100. package/dist/engine/types.d.ts +175 -0
  101. package/dist/engine/types.js +13 -0
  102. package/dist/external-agents/config.d.ts +2 -0
  103. package/dist/external-agents/config.js +15 -0
  104. package/dist/external-agents/types.d.ts +31 -0
  105. package/dist/external-agents/types.js +1 -0
  106. package/dist/git/utils.js +11 -6
  107. package/dist/git/worktree.d.ts +48 -0
  108. package/dist/git/worktree.js +86 -10
  109. package/dist/hooks/goal-stop-hook.d.ts +28 -0
  110. package/dist/hooks/goal-stop-hook.js +186 -9
  111. package/dist/hooks/registry.d.ts +8 -0
  112. package/dist/hooks/registry.js +19 -0
  113. package/dist/hooks/shell-runner.js +10 -21
  114. package/dist/index.d.ts +49 -6
  115. package/dist/index.js +60 -4
  116. package/dist/llm/capabilities/param-specs.d.ts +14 -0
  117. package/dist/llm/capabilities/param-specs.js +62 -0
  118. package/dist/llm/capabilities/rules.js +4 -0
  119. package/dist/llm/capabilities/types.d.ts +10 -0
  120. package/dist/llm/client-base.d.ts +28 -1
  121. package/dist/llm/client-base.js +119 -13
  122. package/dist/llm/model-cache.js +4 -2
  123. package/dist/llm/model-pool.d.ts +14 -0
  124. package/dist/llm/model-pool.js +13 -0
  125. package/dist/llm/provider-auth.d.ts +41 -0
  126. package/dist/llm/provider-auth.js +76 -0
  127. package/dist/llm/provider-catalog.d.ts +4 -0
  128. package/dist/llm/providers/anthropic.js +64 -14
  129. package/dist/llm/providers/openai.d.ts +36 -0
  130. package/dist/llm/providers/openai.js +257 -51
  131. package/dist/llm/reasoning-setting.d.ts +3 -3
  132. package/dist/llm/reasoning-setting.js +9 -1
  133. package/dist/llm/stream-watchdog.js +5 -1
  134. package/dist/llm/token-counter.js +9 -2
  135. package/dist/llm/types.d.ts +4 -0
  136. package/dist/logging/sanitize-messages.js +22 -0
  137. package/dist/lsp/manager.d.ts +1 -1
  138. package/dist/lsp/manager.js +40 -10
  139. package/dist/model-catalog/builtin.d.ts +12 -0
  140. package/dist/model-catalog/builtin.js +407 -0
  141. package/dist/model-catalog/gen-connections.d.ts +20 -0
  142. package/dist/model-catalog/gen-connections.js +28 -0
  143. package/dist/model-catalog/index.d.ts +41 -0
  144. package/dist/model-catalog/index.js +90 -0
  145. package/dist/model-catalog/params.d.ts +20 -0
  146. package/dist/model-catalog/params.js +45 -0
  147. package/dist/model-catalog/resolve.d.ts +48 -0
  148. package/dist/model-catalog/resolve.js +33 -0
  149. package/dist/model-catalog/save-entry.d.ts +32 -0
  150. package/dist/model-catalog/save-entry.js +104 -0
  151. package/dist/model-catalog/types.d.ts +561 -0
  152. package/dist/model-catalog/types.js +93 -0
  153. package/dist/model-catalog/upsert.d.ts +9 -0
  154. package/dist/model-catalog/upsert.js +8 -0
  155. package/dist/onboarding.d.ts +12 -82
  156. package/dist/onboarding.js +61 -326
  157. package/dist/plugins/gitOps.d.ts +19 -0
  158. package/dist/plugins/gitOps.js +73 -4
  159. package/dist/plugins/installer/checkUpdate.d.ts +16 -0
  160. package/dist/plugins/installer/checkUpdate.js +32 -0
  161. package/dist/plugins/installer/codex/convertCommands.d.ts +19 -0
  162. package/dist/plugins/installer/codex/convertCommands.js +46 -0
  163. package/dist/plugins/installer/codex/convertMcp.d.ts +5 -2
  164. package/dist/plugins/installer/codex/convertMcp.js +45 -5
  165. package/dist/plugins/installer/install.js +25 -1
  166. package/dist/plugins/installer/installFromArchive.d.ts +43 -0
  167. package/dist/plugins/installer/installFromArchive.js +134 -0
  168. package/dist/plugins/installer/installFromSource.js +8 -2
  169. package/dist/plugins/installer/loadPluginAgents.js +6 -2
  170. package/dist/plugins/installer/loadPluginMcp.d.ts +9 -2
  171. package/dist/plugins/installer/loadPluginMcp.js +35 -2
  172. package/dist/plugins/installer/pruneDisabled.d.ts +24 -0
  173. package/dist/plugins/installer/pruneDisabled.js +73 -0
  174. package/dist/plugins/installer/types.d.ts +5 -2
  175. package/dist/plugins/installer/types.js +1 -0
  176. package/dist/plugins/installer/uninstall.js +4 -0
  177. package/dist/plugins/installer/unzip.d.ts +14 -0
  178. package/dist/plugins/installer/unzip.js +82 -0
  179. package/dist/plugins/installer/update.d.ts +14 -0
  180. package/dist/plugins/installer/update.js +53 -21
  181. package/dist/plugins/loadPluginHooks.d.ts +47 -1
  182. package/dist/plugins/loadPluginHooks.js +73 -1
  183. package/dist/plugins/marketplaceManager.d.ts +7 -0
  184. package/dist/plugins/marketplaceManager.js +20 -0
  185. package/dist/plugins/pluginCommandHook.js +4 -18
  186. package/dist/plugins/pluginContent.d.ts +30 -0
  187. package/dist/plugins/pluginContent.js +83 -0
  188. package/dist/plugins/pluginInstaller.d.ts +13 -0
  189. package/dist/plugins/pluginInstaller.js +42 -8
  190. package/dist/plugins/schemas.js +1 -0
  191. package/dist/plugins/types.d.ts +6 -0
  192. package/dist/preset/index.d.ts +7 -1
  193. package/dist/preset/index.js +96 -6
  194. package/dist/product/types.d.ts +1 -1
  195. package/dist/prompt/composer.d.ts +27 -0
  196. package/dist/prompt/composer.js +67 -21
  197. package/dist/prompt/instruction-scanner.js +5 -3
  198. package/dist/prompt/section-loader.js +1 -0
  199. package/dist/prompt/sections/base.md +1 -0
  200. package/dist/prompt/sections/browser.md +10 -0
  201. package/dist/prompt/sections/coding.md +4 -0
  202. package/dist/protocol/chat-session-manager.d.ts +8 -2
  203. package/dist/protocol/chat-session-manager.js +36 -0
  204. package/dist/protocol/chat-session.d.ts +65 -0
  205. package/dist/protocol/chat-session.js +94 -2
  206. package/dist/protocol/client.d.ts +27 -0
  207. package/dist/protocol/client.js +38 -0
  208. package/dist/protocol/server.d.ts +112 -0
  209. package/dist/protocol/server.js +586 -16
  210. package/dist/protocol/transport.js +3 -2
  211. package/dist/protocol/types.d.ts +46 -0
  212. package/dist/protocol/types.js +16 -0
  213. package/dist/quota/credentials.d.ts +3 -0
  214. package/dist/quota/credentials.js +80 -0
  215. package/dist/quota/index.d.ts +36 -0
  216. package/dist/quota/index.js +155 -0
  217. package/dist/quota/types.d.ts +48 -0
  218. package/dist/quota/types.js +13 -0
  219. package/dist/review/review-prompt.d.ts +28 -0
  220. package/dist/review/review-prompt.js +81 -0
  221. package/dist/run/FileRunStore.js +8 -3
  222. package/dist/run/RunApprovalBackend.js +25 -5
  223. package/dist/run/RunManager.d.ts +12 -0
  224. package/dist/run/RunManager.js +35 -0
  225. package/dist/run/factory.d.ts +1 -1
  226. package/dist/runtime/background-shell.d.ts +139 -0
  227. package/dist/runtime/background-shell.js +495 -0
  228. package/dist/runtime/output-clean.d.ts +24 -0
  229. package/dist/runtime/output-clean.js +41 -0
  230. package/dist/runtime/ring-file.d.ts +64 -0
  231. package/dist/runtime/ring-file.js +174 -0
  232. package/dist/runtime/safe-spawn.js +15 -34
  233. package/dist/runtime/spawn-common.d.ts +148 -0
  234. package/dist/runtime/spawn-common.js +303 -0
  235. package/dist/runtime/truncate-output.d.ts +22 -0
  236. package/dist/runtime/truncate-output.js +49 -0
  237. package/dist/runtime/utf8-cut.d.ts +11 -0
  238. package/dist/runtime/utf8-cut.js +23 -0
  239. package/dist/services/auto-dream.d.ts +4 -0
  240. package/dist/services/auto-dream.js +26 -26
  241. package/dist/services/diagnostics.d.ts +1 -2
  242. package/dist/services/diagnostics.js +12 -7
  243. package/dist/services/extract-memories.d.ts +14 -1
  244. package/dist/services/extract-memories.js +45 -6
  245. package/dist/services/memory-orchestrator.d.ts +21 -0
  246. package/dist/services/memory-orchestrator.js +125 -50
  247. package/dist/services/session-memory.js +24 -12
  248. package/dist/session/file-history.d.ts +124 -1
  249. package/dist/session/file-history.js +222 -6
  250. package/dist/session/memory.d.ts +116 -2
  251. package/dist/session/memory.js +250 -28
  252. package/dist/session/session-manager.d.ts +40 -0
  253. package/dist/session/session-manager.js +113 -3
  254. package/dist/session/simple-diff.d.ts +23 -0
  255. package/dist/session/simple-diff.js +84 -0
  256. package/dist/session/transcript.d.ts +25 -1
  257. package/dist/session/transcript.js +35 -2
  258. package/dist/session/undo-target.d.ts +67 -0
  259. package/dist/session/undo-target.js +144 -0
  260. package/dist/settings/disk-defaults.d.ts +9 -2
  261. package/dist/settings/disk-defaults.js +11 -2
  262. package/dist/settings/feature-flags.d.ts +64 -0
  263. package/dist/settings/feature-flags.js +61 -0
  264. package/dist/settings/manager.d.ts +68 -1
  265. package/dist/settings/manager.js +266 -29
  266. package/dist/settings/migrate-config.d.ts +45 -0
  267. package/dist/settings/migrate-config.js +125 -0
  268. package/dist/settings/schema-export.d.ts +25 -0
  269. package/dist/settings/schema-export.js +38 -0
  270. package/dist/settings/schema.d.ts +1186 -771
  271. package/dist/settings/schema.js +268 -97
  272. package/dist/skills/scanner.d.ts +9 -0
  273. package/dist/skills/scanner.js +30 -2
  274. package/dist/stt/resolve-transcribe.d.ts +31 -0
  275. package/dist/stt/resolve-transcribe.js +108 -0
  276. package/dist/stt/transcribe.d.ts +51 -0
  277. package/dist/stt/transcribe.js +65 -0
  278. package/dist/tool-system/browser-bridge.d.ts +226 -0
  279. package/dist/tool-system/browser-bridge.js +163 -0
  280. package/dist/tool-system/builtin/agent-heartbeat.d.ts +49 -0
  281. package/dist/tool-system/builtin/agent-heartbeat.js +89 -0
  282. package/dist/tool-system/builtin/agent-notifications.d.ts +12 -3
  283. package/dist/tool-system/builtin/agent-notifications.js +9 -3
  284. package/dist/tool-system/builtin/agent-output-file.d.ts +38 -0
  285. package/dist/tool-system/builtin/agent-output-file.js +72 -0
  286. package/dist/tool-system/builtin/agent-registry.d.ts +12 -0
  287. package/dist/tool-system/builtin/agent-registry.js +8 -0
  288. package/dist/tool-system/builtin/agent.d.ts +21 -1
  289. package/dist/tool-system/builtin/agent.js +489 -42
  290. package/dist/tool-system/builtin/apply-patch/applier.js +66 -8
  291. package/dist/tool-system/builtin/apply-patch/backup-targets.d.ts +10 -0
  292. package/dist/tool-system/builtin/apply-patch/backup-targets.js +30 -0
  293. package/dist/tool-system/builtin/apply-patch/index.js +0 -15
  294. package/dist/tool-system/builtin/background-jobs.d.ts +76 -0
  295. package/dist/tool-system/builtin/background-jobs.js +124 -0
  296. package/dist/tool-system/builtin/background-shell-tools.d.ts +20 -0
  297. package/dist/tool-system/builtin/background-shell-tools.js +108 -0
  298. package/dist/tool-system/builtin/background-work.d.ts +67 -0
  299. package/dist/tool-system/builtin/background-work.js +86 -0
  300. package/dist/tool-system/builtin/bash-output-style.d.ts +32 -0
  301. package/dist/tool-system/builtin/bash-output-style.js +40 -0
  302. package/dist/tool-system/builtin/bash.d.ts +5 -2
  303. package/dist/tool-system/builtin/bash.js +98 -62
  304. package/dist/tool-system/builtin/browser-tools.d.ts +33 -0
  305. package/dist/tool-system/builtin/browser-tools.js +312 -0
  306. package/dist/tool-system/builtin/cancel-goal.d.ts +31 -0
  307. package/dist/tool-system/builtin/cancel-goal.js +64 -0
  308. package/dist/tool-system/builtin/check-quota.d.ts +15 -0
  309. package/dist/tool-system/builtin/check-quota.js +34 -0
  310. package/dist/tool-system/builtin/config.js +7 -0
  311. package/dist/tool-system/builtin/cron.d.ts +7 -0
  312. package/dist/tool-system/builtin/cron.js +55 -3
  313. package/dist/tool-system/builtin/drive-claude-code.d.ts +30 -0
  314. package/dist/tool-system/builtin/drive-claude-code.js +157 -0
  315. package/dist/tool-system/builtin/edit-model-catalog.d.ts +3 -0
  316. package/dist/tool-system/builtin/edit-model-catalog.js +94 -0
  317. package/dist/tool-system/builtin/edit.js +20 -16
  318. package/dist/tool-system/builtin/eol.d.ts +29 -0
  319. package/dist/tool-system/builtin/eol.js +37 -0
  320. package/dist/tool-system/builtin/file-cache.d.ts +6 -0
  321. package/dist/tool-system/builtin/file-cache.js +8 -0
  322. package/dist/tool-system/builtin/generate-image.d.ts +35 -0
  323. package/dist/tool-system/builtin/generate-image.js +278 -50
  324. package/dist/tool-system/builtin/generate-video.d.ts +55 -0
  325. package/dist/tool-system/builtin/generate-video.js +361 -0
  326. package/dist/tool-system/builtin/glob.js +0 -7
  327. package/dist/tool-system/builtin/grep.js +6 -8
  328. package/dist/tool-system/builtin/image-providers.d.ts +86 -0
  329. package/dist/tool-system/builtin/image-providers.js +190 -0
  330. package/dist/tool-system/builtin/image-uploader.d.ts +33 -0
  331. package/dist/tool-system/builtin/image-uploader.js +74 -0
  332. package/dist/tool-system/builtin/index.d.ts +7 -1
  333. package/dist/tool-system/builtin/index.js +249 -25
  334. package/dist/tool-system/builtin/mcp-tools.js +23 -3
  335. package/dist/tool-system/builtin/memory.js +45 -7
  336. package/dist/tool-system/builtin/notebook-edit.js +0 -7
  337. package/dist/tool-system/builtin/powershell.js +4 -1
  338. package/dist/tool-system/builtin/read.js +10 -10
  339. package/dist/tool-system/builtin/repl.js +4 -1
  340. package/dist/tool-system/builtin/skill.js +9 -0
  341. package/dist/tool-system/builtin/sleep.js +3 -2
  342. package/dist/tool-system/builtin/tool-search.js +25 -7
  343. package/dist/tool-system/builtin/video-providers.d.ts +154 -0
  344. package/dist/tool-system/builtin/video-providers.js +235 -0
  345. package/dist/tool-system/builtin/web-fetch.js +12 -2
  346. package/dist/tool-system/builtin/web-search.js +21 -7
  347. package/dist/tool-system/builtin/worktree.d.ts +2 -1
  348. package/dist/tool-system/builtin/worktree.js +31 -4
  349. package/dist/tool-system/builtin/write.js +0 -6
  350. package/dist/tool-system/context.d.ts +154 -6
  351. package/dist/tool-system/executor.d.ts +3 -1
  352. package/dist/tool-system/executor.js +172 -88
  353. package/dist/tool-system/investigation-guard.js +1 -1
  354. package/dist/tool-system/mcp-manager.d.ts +42 -4
  355. package/dist/tool-system/mcp-manager.js +186 -20
  356. package/dist/tool-system/path-policy.d.ts +5 -0
  357. package/dist/tool-system/path-policy.js +307 -8
  358. package/dist/tool-system/permission.d.ts +36 -1
  359. package/dist/tool-system/permission.js +281 -69
  360. package/dist/tool-system/plan-mode-allowlist.d.ts +13 -2
  361. package/dist/tool-system/plan-mode-allowlist.js +24 -2
  362. package/dist/tool-system/registry.d.ts +1 -0
  363. package/dist/tool-system/registry.js +16 -2
  364. package/dist/tool-system/sandbox/index.d.ts +8 -0
  365. package/dist/tool-system/sandbox/index.js +7 -2
  366. package/dist/tool-system/validate-tool-metadata.d.ts +36 -0
  367. package/dist/tool-system/validate-tool-metadata.js +63 -0
  368. package/dist/types.d.ts +217 -6
  369. package/dist/updater.js +20 -9
  370. package/dist/utils/envUtils.d.ts +0 -9
  371. package/dist/utils/envUtils.js +3 -28
  372. package/dist/utils/exec.d.ts +40 -0
  373. package/dist/utils/exec.js +144 -0
  374. package/dist/utils/json.d.ts +12 -0
  375. package/dist/utils/json.js +92 -0
  376. package/dist/utils/theme.d.ts +1 -1
  377. package/dist/utils/theme.js +1 -1
  378. package/dist/utils/toolDisplay.js +0 -1
  379. package/package.json +13 -7
  380. package/dist/agent/coordinator.d.ts +0 -49
  381. package/dist/agent/coordinator.js +0 -77
  382. package/dist/settings/manager.test.js +0 -73
  383. package/dist/tool-system/builtin/remote-trigger.d.ts +0 -6
  384. package/dist/tool-system/builtin/remote-trigger.js +0 -54
  385. package/dist/tool-system/builtin/send-message.d.ts +0 -6
  386. package/dist/tool-system/builtin/send-message.js +0 -47
  387. /package/dist/{settings/manager.test.d.ts → credentials/types.js} +0 -0
@@ -0,0 +1,361 @@
1
+ /**
2
+ * Built-in GenerateVideo tool (TODO 7.1 块3) — text-to-video via a
3
+ * {@link VideoProvider} adapter (submit / poll / download).
4
+ *
5
+ * Video generation is always slow (tens of seconds to minutes), so this tool
6
+ * is fire-and-forget by design: it submits the job, returns a handle
7
+ * immediately, and polls in the BACKGROUND. When the job finishes it writes
8
+ * the file to `<cwd>/.code-shell/generated_videos/` and enqueues a completion
9
+ * notification (same notificationQueue path as background agents / shells), so
10
+ * the main turn is never blocked (consistent with TODO 3.2 / 4.1).
11
+ *
12
+ * Concrete provider adapters (Seedance / Kling) are not wired yet — their
13
+ * private APIs need confirmed docs. Until then the only resolvable provider is
14
+ * the test-injected fake, so in production this tool is dormant (returns a
15
+ * "no video provider configured" message) rather than half-working.
16
+ */
17
+ import { writeFile, mkdir } from "node:fs/promises";
18
+ import { join } from "node:path";
19
+ import { SettingsManager } from "../../settings/manager.js";
20
+ import { notificationQueue } from "./agent-notifications.js";
21
+ import { backgroundJobRegistry } from "./background-jobs.js";
22
+ import { logger } from "../../logging/logger.js";
23
+ import { getVideoProvider, DEFAULT_VIDEO_MODEL, } from "./video-providers.js";
24
+ import { getImageUploader } from "./image-uploader.js";
25
+ import { effectiveApiKey } from "./generate-image.js";
26
+ import { getMergedCatalog, findCatalogEntry } from "../../model-catalog/index.js";
27
+ import { genInstancesFromConnections } from "../../model-catalog/gen-connections.js";
28
+ const MAX_IMAGES = 9;
29
+ /**
30
+ * Normalize image inputs (URLs or local paths) into public URLs the provider
31
+ * can consume. `images[]` wins over the single `image`. Local paths are
32
+ * uploaded via the injected {@link ImageUploader}; URLs pass through. Caps at
33
+ * {@link MAX_IMAGES} (fal reference-to-video allows up to 9).
34
+ */
35
+ export async function __normalizeImagesForTests(images, image, uploader, creds, signal) {
36
+ const raw = images && images.length ? images : image ? [image] : [];
37
+ if (raw.length > MAX_IMAGES) {
38
+ return { ok: false, error: `too many images: ${raw.length} (max ${MAX_IMAGES})` };
39
+ }
40
+ const urls = [];
41
+ for (const item of raw) {
42
+ const r = await uploader.toUrl(item, creds, signal);
43
+ if (!r.ok)
44
+ return { ok: false, error: r.error };
45
+ urls.push(r.url);
46
+ }
47
+ return { ok: true, urls };
48
+ }
49
+ /** Video provider `kind`s that have an adapter, in resolution preference. */
50
+ const VIDEO_PROVIDER_KINDS = ["fal"];
51
+ const DEFAULT_POLL_INTERVAL_MS = 5_000;
52
+ /** Safety cap so a stuck job's background loop can't poll forever. */
53
+ const MAX_POLL_MS = 15 * 60 * 1000;
54
+ export const generateVideoToolDef = {
55
+ name: "GenerateVideo",
56
+ description: "Generate a video from a text prompt. The job runs in the background (video generation is " +
57
+ "slow); you are notified automatically when it finishes, and the .mp4 is saved into the " +
58
+ "workspace. Do NOT sleep or poll — continue with other work. Requires a configured video " +
59
+ "provider.",
60
+ inputSchema: {
61
+ type: "object",
62
+ properties: {
63
+ prompt: { type: "string", description: "Description of the video to generate" },
64
+ provider: {
65
+ type: "string",
66
+ description: "Video provider kind to use. Defaults to the first configured video provider.",
67
+ },
68
+ model: { type: "string", description: "Video model id. Defaults to the provider's default." },
69
+ image: { type: "string", description: "Image URL (http/https) for image-to-video. When set, an image-to-video model is used." },
70
+ images: {
71
+ type: "array",
72
+ items: { type: "string" },
73
+ description: "Image URLs or local file paths for image/reference-to-video. 1 image → image-to-video; 2+ → reference-to-video (max 9). Local paths are auto-uploaded. Refer to them in prompt as @Image1, @Image2.",
74
+ },
75
+ videos: {
76
+ type: "array",
77
+ items: { type: "string" },
78
+ description: "Reference/continuation video URLs (http/https only — NOT local paths) for video extension. Forces reference-to-video (Seedance model required). Up to 3. Refer to them in prompt as @Video1, @Video2 (e.g. \"continue from @Video1\").",
79
+ },
80
+ },
81
+ required: ["prompt"],
82
+ },
83
+ };
84
+ // Test seam: inject a VideoProvider so the background poll loop can be tested
85
+ // end-to-end without a real adapter or network. Null → normal resolution.
86
+ let injectedProvider = null;
87
+ export function __setVideoProviderForTests(p) {
88
+ injectedProvider = p;
89
+ }
90
+ /**
91
+ * Tool-visibility guard: GenerateVideo is hidden until a video provider is
92
+ * actually configured. With no real adapters wired yet (VIDEO_PROVIDER_KINDS
93
+ * is empty), this returns false in production so the model never sees a tool
94
+ * it can't use — the tool becomes visible automatically once an adapter +
95
+ * matching settings provider exist. Short TTL cache like GenerateImage.
96
+ */
97
+ const availCache = new Map();
98
+ const AVAIL_TTL_MS = 1000;
99
+ export function isGenerateVideoAvailable(cwd = process.cwd(), nowMs = Date.now()) {
100
+ const hit = availCache.get(cwd);
101
+ if (hit && nowMs - hit.at < AVAIL_TTL_MS)
102
+ return hit.value;
103
+ let value = false;
104
+ try {
105
+ value = resolveVideoProvider(cwd) !== null;
106
+ }
107
+ catch {
108
+ value = false;
109
+ }
110
+ availCache.set(cwd, { at: nowMs, value });
111
+ return value;
112
+ }
113
+ /**
114
+ * List configured, usable video providers (TODO 7.1). Returns [] when no
115
+ * adapters are wired (VIDEO_PROVIDER_KINDS empty) or none configured.
116
+ */
117
+ export function listConfiguredVideoProviders(cwd = process.cwd()) {
118
+ try {
119
+ const settings = new SettingsManager(cwd, "full").get();
120
+ // Canonical videoGen.providers[] first (TODO 7.1) — but only kinds that
121
+ // have a wired adapter (VIDEO_PROVIDER_KINDS); a configured-but-unadapted
122
+ // entry isn't usable yet.
123
+ const videoGen = settings.videoGen;
124
+ if (videoGen?.providers?.length) {
125
+ const list = videoGen.providers;
126
+ return list
127
+ .filter((p) => !!effectiveApiKey(p, list) && getVideoProvider(p.kind) !== null)
128
+ .map((p) => ({ id: p.id, kind: p.kind, catalogId: p.catalogId }));
129
+ }
130
+ // Legacy LLM providers[] back-compat (field dropped from schema; read via
131
+ // .passthrough() with an inline cast).
132
+ const legacyProviders = settings.providers ?? [];
133
+ return legacyProviders
134
+ .filter((p) => p.apiKey && VIDEO_PROVIDER_KINDS.includes(p.kind))
135
+ .map((p) => ({ kind: p.kind }));
136
+ }
137
+ catch {
138
+ return [];
139
+ }
140
+ }
141
+ /** Dynamic GenerateVideo description naming configured providers (TODO 7.1). */
142
+ export function generateVideoToolDefFor(cwd) {
143
+ const providers = listConfiguredVideoProviders(cwd);
144
+ if (providers.length === 0)
145
+ return generateVideoToolDef;
146
+ const names = providers.map((p) => p.id ?? p.kind).join(", ");
147
+ const catalog = getMergedCatalog();
148
+ const paramLines = providers
149
+ .map((p) => {
150
+ const entry = findCatalogEntry(catalog, p.catalogId, p.kind);
151
+ return entry?.paramsDoc ? ` - ${p.id ?? p.kind}: ${entry.paramsDoc}` : null;
152
+ })
153
+ .filter((x) => x !== null);
154
+ const paramsBlock = paramLines.length ? `\nParams per provider:\n${paramLines.join("\n")}` : "";
155
+ return {
156
+ ...generateVideoToolDef,
157
+ description: generateVideoToolDef.description +
158
+ ` Configured provider(s): ${names}. Pass \`provider\` to pick one.` +
159
+ paramsBlock,
160
+ };
161
+ }
162
+ function resolveVideoProvider(cwd, preferKind) {
163
+ const settings = new SettingsManager(cwd, "full").get();
164
+ // 0. Unified store (统一模型接入方案): modelConnections (tag=video) +
165
+ // credentials, taking precedence over legacy videoGen.providers[].
166
+ const conns = settings.modelConnections;
167
+ const creds = settings.credentials;
168
+ if (Array.isArray(conns) && conns.some((c) => c.tag === "video")) {
169
+ const list = genInstancesFromConnections(conns, (Array.isArray(creds) ? creds : []), getMergedCatalog(), "video");
170
+ const def = settings.defaults?.video;
171
+ const usable = (p) => !!p.apiKey && getVideoProvider(p.kind) !== null;
172
+ const credsOf = (p) => ({ baseUrl: p.baseUrl, apiKey: p.apiKey });
173
+ if (preferKind) {
174
+ const chosen = list.find((p) => (p.id === preferKind || p.kind === preferKind) && usable(p));
175
+ if (chosen)
176
+ return { kind: chosen.kind, creds: credsOf(chosen), defaultModel: chosen.defaultModel };
177
+ return null;
178
+ }
179
+ const preferred = def ? list.find((p) => p.id === def) : undefined;
180
+ const chosen = (preferred && usable(preferred) ? preferred : undefined) ?? list.find(usable);
181
+ if (chosen)
182
+ return { kind: chosen.kind, creds: credsOf(chosen), defaultModel: chosen.defaultModel };
183
+ if (def || preferKind)
184
+ return null;
185
+ }
186
+ const videoGen = settings.videoGen;
187
+ if (videoGen?.providers?.length) {
188
+ const list = videoGen.providers;
189
+ const usable = (p) => !!effectiveApiKey(p, list) && getVideoProvider(p.kind) !== null;
190
+ const credsOf = (p) => ({ baseUrl: p.baseUrl, apiKey: effectiveApiKey(p, list) });
191
+ if (preferKind) {
192
+ const chosen = list.find((p) => (p.id === preferKind || p.kind === preferKind) && usable(p));
193
+ if (chosen)
194
+ return { kind: chosen.kind, creds: credsOf(chosen), defaultModel: chosen.defaultModel };
195
+ return null;
196
+ }
197
+ const preferred = videoGen.defaultProvider
198
+ ? list.find((p) => p.id === videoGen.defaultProvider)
199
+ : undefined;
200
+ const chosen = (preferred && usable(preferred) ? preferred : undefined) ?? list.find(usable);
201
+ if (chosen)
202
+ return { kind: chosen.kind, creds: credsOf(chosen), defaultModel: chosen.defaultModel };
203
+ return null;
204
+ }
205
+ // Back-compat: scan legacy LLM providers[] for a video-capable kind. The
206
+ // field was dropped from the schema; un-migrated settings.json still carry it
207
+ // via .passthrough(), so read it through an inline cast.
208
+ const legacyProviders = settings.providers ?? [];
209
+ const kinds = preferKind ? [preferKind] : VIDEO_PROVIDER_KINDS;
210
+ for (const kind of kinds) {
211
+ const provider = legacyProviders.find((p) => p.kind === kind);
212
+ if (provider && provider.apiKey) {
213
+ return { kind, creds: { baseUrl: provider.baseUrl, apiKey: provider.apiKey } };
214
+ }
215
+ }
216
+ return null;
217
+ }
218
+ export function __resolveVideoProviderForTests(cwd, preferKind) {
219
+ return resolveVideoProvider(cwd, preferKind);
220
+ }
221
+ export async function generateVideoTool(args, ctx) {
222
+ const prompt = args.prompt;
223
+ if (typeof prompt !== "string" || !prompt.trim()) {
224
+ return "Error: prompt is required";
225
+ }
226
+ const cwd = ctx?.cwd ?? process.cwd();
227
+ const sessionId = ctx?.sessionId;
228
+ const preferKind = typeof args.provider === "string" && args.provider ? args.provider : undefined;
229
+ const overrideModel = typeof args.model === "string" && args.model ? args.model : undefined;
230
+ const image = typeof args.image === "string" && args.image ? args.image : undefined;
231
+ const imagesArg = Array.isArray(args.images)
232
+ ? args.images.filter((x) => typeof x === "string")
233
+ : undefined;
234
+ // videos pass through verbatim to fal's video_urls (no upload) — http(s) only.
235
+ const videosArg = Array.isArray(args.videos)
236
+ ? args.videos.filter((x) => typeof x === "string")
237
+ : undefined;
238
+ const pollIntervalMs = typeof args.pollIntervalMs === "number" && args.pollIntervalMs > 0
239
+ ? args.pollIntervalMs
240
+ : DEFAULT_POLL_INTERVAL_MS;
241
+ // Resolve the provider + adapter. The test seam wins so the background loop
242
+ // is exercised without a real adapter.
243
+ let kind;
244
+ let creds;
245
+ let adapter;
246
+ let defaultModel;
247
+ if (injectedProvider) {
248
+ adapter = injectedProvider;
249
+ kind = injectedProvider.kind;
250
+ creds = { baseUrl: "test", apiKey: "test" };
251
+ }
252
+ else {
253
+ const resolved = resolveVideoProvider(cwd, preferKind);
254
+ if (!resolved) {
255
+ return preferKind
256
+ ? `Error: no video provider of kind "${preferKind}" available. Configure it (with an apiKey) in settings.`
257
+ : "Error: no video provider available. Video generation requires a configured video provider (none are wired yet).";
258
+ }
259
+ const a = getVideoProvider(resolved.kind);
260
+ if (!a)
261
+ return `Error: video generation is not supported for provider kind "${resolved.kind}".`;
262
+ adapter = a;
263
+ kind = resolved.kind;
264
+ creds = resolved.creds;
265
+ defaultModel = resolved.defaultModel;
266
+ }
267
+ const model = overrideModel ?? defaultModel ?? DEFAULT_VIDEO_MODEL[kind] ?? kind;
268
+ // Normalize image inputs (local paths → uploaded URLs) before submit. The
269
+ // provider only ever receives URLs and routes t2v/i2v/ref2v by count.
270
+ const uploader = getImageUploader(kind) ?? getImageUploader("fal");
271
+ const norm = await __normalizeImagesForTests(imagesArg, image, uploader, { baseUrl: creds.baseUrl, apiKey: creds.apiKey }, ctx?.signal);
272
+ if (!norm.ok)
273
+ return `Error: ${norm.error}`;
274
+ const submit = await adapter.submit({ prompt, model, image: undefined, images: norm.urls, videos: videosArg, creds, signal: ctx?.signal });
275
+ if (!submit.ok) {
276
+ return `Error submitting video job: ${submit.error}`;
277
+ }
278
+ const jobId = submit.jobId;
279
+ // Background poll → download → write → notify. Fire-and-forget: never await.
280
+ // Register the job so it shows up in the goal judge's background-task list
281
+ // (so the judge can tell "waiting on a finite render" from "nothing left to
282
+ // do" — the s-mqe0ox7n-a8d11c26 busy-loop bug). The video does NOT park the
283
+ // engine anymore; its completion notification wakes the idle session (server
284
+ // maybeWakeIdleSession). The registry is keyed by the fal jobId namespaced so
285
+ // two providers can't collide.
286
+ const jobKey = `video-${jobId}`;
287
+ const promptPreview = prompt.length > 80 ? `${prompt.slice(0, 80)}…` : prompt;
288
+ backgroundJobRegistry.start(jobKey, sessionId ?? "", `生成视频中:${promptPreview}`);
289
+ void pollToCompletion(adapter, jobId, creds, cwd, sessionId, prompt, pollIntervalMs)
290
+ .then((outcome) => backgroundJobRegistry.finish(jobKey, outcome))
291
+ .catch((err) => backgroundJobRegistry.finish(jobKey, { status: "failed", finalText: err.message }));
292
+ return [
293
+ `Video generation started in the background.`,
294
+ `job_id: ${jobId} (internal — do not show to user)`,
295
+ `prompt: ${prompt}`,
296
+ ``,
297
+ `It will be saved into .code-shell/generated_videos/ and you'll be notified automatically when it finishes.`,
298
+ `If you have no other work right now, END YOUR TURN — the system wakes you when the video is ready. NEVER run \`sleep\` or poll the provider yourself.`,
299
+ ].join("\n");
300
+ }
301
+ async function pollToCompletion(adapter, jobId, creds, cwd, sessionId, prompt, pollIntervalMs) {
302
+ const started = Date.now();
303
+ try {
304
+ for (;;) {
305
+ if (Date.now() - started > MAX_POLL_MS) {
306
+ const msg = `video job ${jobId} timed out after ${Math.round(MAX_POLL_MS / 1000)}s`;
307
+ notifyVideo(sessionId, "failed", prompt, undefined, msg);
308
+ return { status: "failed", finalText: msg };
309
+ }
310
+ const res = await adapter.poll({ jobId, creds });
311
+ if (!res.ok) {
312
+ notifyVideo(sessionId, "failed", prompt, undefined, res.error);
313
+ return { status: "failed", finalText: res.error };
314
+ }
315
+ if (res.status === "failed") {
316
+ notifyVideo(sessionId, "failed", prompt, undefined, res.error);
317
+ return { status: "failed", finalText: res.error };
318
+ }
319
+ if (res.status === "succeeded")
320
+ break;
321
+ await new Promise((r) => setTimeout(r, pollIntervalMs));
322
+ }
323
+ const dl = await adapter.download({ jobId, creds });
324
+ if (!dl.ok) {
325
+ notifyVideo(sessionId, "failed", prompt, undefined, dl.error);
326
+ return { status: "failed", finalText: dl.error };
327
+ }
328
+ const dir = join(cwd, ".code-shell", "generated_videos");
329
+ await mkdir(dir, { recursive: true });
330
+ const path = join(dir, `${Date.now()}.${dl.ext || "mp4"}`);
331
+ await writeFile(path, dl.bytes);
332
+ notifyVideo(sessionId, "completed", prompt, path, undefined, dl.url);
333
+ return { status: "completed", finalText: path };
334
+ }
335
+ catch (err) {
336
+ notifyVideo(sessionId, "failed", prompt, undefined, err.message);
337
+ return { status: "failed", finalText: err.message };
338
+ }
339
+ }
340
+ function notifyVideo(sessionId, status, prompt, path, error, url) {
341
+ if (!sessionId) {
342
+ logger.warn("video_completion_without_session", { status });
343
+ return;
344
+ }
345
+ // Include the fal-hosted URL on success so the model can pass it to a follow-up
346
+ // GenerateVideo `videos:[url]` to extend this clip (no re-upload). Expiring URL.
347
+ const extendHint = url
348
+ ? ` To extend this video, call GenerateVideo again with videos:["${url}"] (Seedance model). URL may expire.`
349
+ : "";
350
+ notificationQueue.enqueue({
351
+ agentId: `video-${Date.now()}`,
352
+ name: "video generation",
353
+ description: status === "completed"
354
+ ? `Video generated: ${path} (prompt: ${prompt})`
355
+ : `Video generation failed (prompt: ${prompt})`,
356
+ status,
357
+ finalText: status === "completed" ? `Video saved to ${path}.${extendHint}` : undefined,
358
+ error: status === "failed" ? error : undefined,
359
+ enqueuedAt: Date.now(),
360
+ }, sessionId);
361
+ }
@@ -4,7 +4,6 @@
4
4
  import { glob } from "glob";
5
5
  import { stat } from "node:fs/promises";
6
6
  import * as path from "node:path";
7
- import { enforcePathPolicy } from "../path-policy.js";
8
7
  export const globToolDef = {
9
8
  name: "Glob",
10
9
  description: "Fast file pattern matching. Returns matching file paths sorted by modification time. " +
@@ -32,12 +31,6 @@ export async function globTool(args, ctx) {
32
31
  ? argPath
33
32
  : path.resolve(baseDir, argPath)
34
33
  : baseDir;
35
- // Path policy: refuse to glob a search root the policy classifies as
36
- // ask/deny for read. Stops a Glob("**/*", "/home/user/.ssh") from
37
- // enumerating the keys directory under the existence-check radar.
38
- const blocked = enforcePathPolicy(cwd, "read", ctx?.cwd);
39
- if (blocked)
40
- return blocked;
41
34
  try {
42
35
  const matches = await glob(pattern, {
43
36
  cwd,
@@ -4,7 +4,6 @@
4
4
  import { execFile } from "node:child_process";
5
5
  import { promisify } from "node:util";
6
6
  import { resolve, sep, isAbsolute } from "node:path";
7
- import { enforcePathPolicy } from "../path-policy.js";
8
7
  const execFileAsync = promisify(execFile);
9
8
  /**
10
9
  * Strip the cwd prefix from each line so results display as relative
@@ -59,11 +58,6 @@ export async function grepTool(args, ctx) {
59
58
  ? argPath
60
59
  : resolve(baseDir, argPath)
61
60
  : baseDir;
62
- // Path policy: reading file contents under ~/.ssh, ~/.aws etc. by way
63
- // of grep is the same exfiltration risk as Read. Gate the search root.
64
- const blocked = enforcePathPolicy(searchPath, "read", ctx?.cwd);
65
- if (blocked)
66
- return blocked;
67
61
  const fileGlob = args.glob;
68
62
  const context = args.context || 0;
69
63
  const maxResults = args.max_results || 50;
@@ -77,7 +71,7 @@ export async function grepTool(args, ctx) {
77
71
  if (isNoMatchExit(rgErr))
78
72
  return "No matches found.";
79
73
  try {
80
- return await runGrep(pattern, searchPath, context, maxResults, outputMode, caseInsensitive);
74
+ return await runGrep(pattern, searchPath, fileGlob, context, maxResults, outputMode, caseInsensitive);
81
75
  }
82
76
  catch (grepErr) {
83
77
  if (isNoMatchExit(grepErr))
@@ -122,7 +116,7 @@ async function runRipgrep(pattern, path, fileGlob, context, maxResults, outputMo
122
116
  }
123
117
  return result;
124
118
  }
125
- async function runGrep(pattern, path, context, maxResults, outputMode, caseInsensitive) {
119
+ async function runGrep(pattern, path, fileGlob, context, maxResults, outputMode, caseInsensitive) {
126
120
  const args = ["-r", "--color=never"];
127
121
  if (caseInsensitive)
128
122
  args.push("-i");
@@ -138,6 +132,10 @@ async function runGrep(pattern, path, context, maxResults, outputMode, caseInsen
138
132
  args.push("-C", String(context));
139
133
  }
140
134
  args.push("-m", String(maxResults));
135
+ // Honor the file glob so the grep fallback matches ripgrep's --glob behavior
136
+ // (previously the glob was silently dropped on the fallback path).
137
+ if (fileGlob)
138
+ args.push(`--include=${fileGlob}`);
141
139
  args.push("-E", pattern);
142
140
  args.push("--exclude-dir=node_modules", "--exclude-dir=.git", "--exclude-dir=dist");
143
141
  args.push(path);
@@ -0,0 +1,86 @@
1
+ /**
2
+ * ImageProvider — adapter interface for text-to-image generation (TODO 7.1).
3
+ *
4
+ * Lifts the hardcoded OpenAI `gpt-image-2` call out of generate-image.ts so
5
+ * GenerateImage can target multiple providers (OpenAI now; Gemini next) and
6
+ * take an optional provider/model. Each adapter takes resolved credentials +
7
+ * the request and returns a base64 PNG (or an error string). The tool layer
8
+ * owns credential resolution from settings, file writing, and user-facing
9
+ * formatting — adapters are pure "creds + prompt → bytes".
10
+ *
11
+ * `fetch` is injected so adapters are unit-testable without network. Production
12
+ * call sites pass the global `fetch`.
13
+ */
14
+ export interface ImageProviderCreds {
15
+ baseUrl: string;
16
+ apiKey: string;
17
+ }
18
+ /** A decoded reference/input image for image-to-image (edit) requests. */
19
+ export interface InputImage {
20
+ /** File name hint (used as the multipart part filename). */
21
+ filename: string;
22
+ /** MIME type, e.g. "image/png" | "image/jpeg" | "image/webp". */
23
+ mimeType: string;
24
+ /** Raw bytes (NOT base64) — the tool layer decodes the workspace file. */
25
+ bytes: Uint8Array;
26
+ }
27
+ export interface ImageGenerateRequest {
28
+ prompt: string;
29
+ size: string;
30
+ quality: string;
31
+ model: string;
32
+ creds: ImageProviderCreds;
33
+ /**
34
+ * Optional reference images. When present, this becomes an image-TO-image
35
+ * (edit) request rather than text-to-image: the provider conditions the
36
+ * output on these inputs (OpenAI `/images/edits`, Gemini inline_data parts).
37
+ * Empty/undefined = plain text-to-image.
38
+ */
39
+ inputImages?: InputImage[];
40
+ /** Optional cancellation signal forwarded to fetch. */
41
+ signal?: AbortSignal;
42
+ }
43
+ export type ImageGenerateResult = {
44
+ ok: true;
45
+ b64: string;
46
+ } | {
47
+ ok: false;
48
+ error: string;
49
+ };
50
+ export interface ImageProvider {
51
+ /** Adapter id — matches the settings provider `kind` it consumes. */
52
+ readonly kind: string;
53
+ generate(req: ImageGenerateRequest): Promise<ImageGenerateResult>;
54
+ }
55
+ /**
56
+ * OpenAI Images API adapter (`/images/generations`, b64_json). Identical wire
57
+ * behavior to the pre-refactor generate-image.ts: POST model/prompt/size/
58
+ * quality/n, read data[0].b64_json.
59
+ */
60
+ export declare class OpenAIImageProvider implements ImageProvider {
61
+ private readonly fetchImpl;
62
+ readonly kind = "openai";
63
+ constructor(fetchImpl?: typeof fetch);
64
+ generate(req: ImageGenerateRequest): Promise<ImageGenerateResult>;
65
+ }
66
+ /**
67
+ * Gemini Images adapter — the `generateContent` endpoint
68
+ * (`/models/{model}:generateContent`), API key in the `x-goog-api-key`
69
+ * header, prompt as a text content-part, PNG returned base64 in
70
+ * `candidates[].content.parts[].inline_data.data` (REST may camelCase it to
71
+ * `inlineData`; we read both). Wire shape per ai.google.dev image-generation
72
+ * docs. The OpenAI-style `size`/`quality` args don't map 1:1 to Gemini's
73
+ * aspectRatio/imageSize, so we only forward the prompt + IMAGE modality and
74
+ * leave Gemini's own defaults for dimensions (a later pass can map size →
75
+ * aspectRatio if needed).
76
+ */
77
+ export declare class GeminiImageProvider implements ImageProvider {
78
+ private readonly fetchImpl;
79
+ readonly kind = "google";
80
+ constructor(fetchImpl?: typeof fetch);
81
+ generate(req: ImageGenerateRequest): Promise<ImageGenerateResult>;
82
+ }
83
+ /** Default model per provider kind when the caller doesn't specify one. */
84
+ export declare const DEFAULT_IMAGE_MODEL: Record<string, string>;
85
+ /** Registry of available image-provider adapters, keyed by `kind`. */
86
+ export declare function getImageProvider(kind: string, fetchImpl?: typeof fetch): ImageProvider | null;