@pellux/goodvibes-tui 0.18.4

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 (732) hide show
  1. package/.goodvibes/GOODVIBES.md +35 -0
  2. package/.goodvibes/agents/reviewer.md +89 -0
  3. package/.goodvibes/skills/add-provider/SKILL.md +199 -0
  4. package/CHANGELOG.md +1681 -0
  5. package/README.md +1607 -0
  6. package/bin/goodvibes +66 -0
  7. package/docs/README.md +32 -0
  8. package/docs/foundation-artifacts/README.md +16 -0
  9. package/docs/foundation-artifacts/knowledge-graphql.graphql +397 -0
  10. package/docs/foundation-artifacts/knowledge-store.sql +183 -0
  11. package/docs/foundation-artifacts/operator-contract.json +55157 -0
  12. package/docs/foundation-artifacts/peer-contract.json +2384 -0
  13. package/package.json +114 -0
  14. package/scripts/postinstall.mjs +203 -0
  15. package/src/acp/connection.ts +447 -0
  16. package/src/acp/index.ts +7 -0
  17. package/src/acp/manager.ts +133 -0
  18. package/src/adapters/bluebubbles/index.ts +127 -0
  19. package/src/adapters/discord/index.ts +297 -0
  20. package/src/adapters/github/index.ts +73 -0
  21. package/src/adapters/google-chat/index.ts +119 -0
  22. package/src/adapters/imessage/index.ts +92 -0
  23. package/src/adapters/index.ts +15 -0
  24. package/src/adapters/matrix/index.ts +116 -0
  25. package/src/adapters/mattermost/index.ts +151 -0
  26. package/src/adapters/msteams/index.ts +180 -0
  27. package/src/adapters/ntfy/index.ts +118 -0
  28. package/src/adapters/signal/index.ts +92 -0
  29. package/src/adapters/slack/index.ts +323 -0
  30. package/src/adapters/telegram/index.ts +160 -0
  31. package/src/adapters/types.ts +97 -0
  32. package/src/adapters/webhook/index.ts +178 -0
  33. package/src/adapters/whatsapp/index.ts +135 -0
  34. package/src/agents/message-bus-core.ts +312 -0
  35. package/src/agents/message-bus.ts +2 -0
  36. package/src/agents/orchestrator-prompts.ts +351 -0
  37. package/src/agents/orchestrator-runner.ts +668 -0
  38. package/src/agents/orchestrator.ts +437 -0
  39. package/src/agents/session.ts +108 -0
  40. package/src/agents/worktree.ts +153 -0
  41. package/src/agents/wrfc-config.ts +47 -0
  42. package/src/agents/wrfc-controller.ts +747 -0
  43. package/src/agents/wrfc-gate-runtime.ts +75 -0
  44. package/src/agents/wrfc-reporting.ts +284 -0
  45. package/src/agents/wrfc-runtime-events.ts +150 -0
  46. package/src/agents/wrfc-types.ts +67 -0
  47. package/src/automation/delivery-manager.ts +368 -0
  48. package/src/automation/index.ts +72 -0
  49. package/src/automation/manager-runtime-delivery.ts +139 -0
  50. package/src/automation/manager-runtime-events.ts +131 -0
  51. package/src/automation/manager-runtime-execution.ts +511 -0
  52. package/src/automation/manager-runtime-helpers.ts +433 -0
  53. package/src/automation/manager-runtime-job-mutations.ts +175 -0
  54. package/src/automation/manager-runtime-reconcile.ts +148 -0
  55. package/src/automation/manager-runtime-scheduling.ts +189 -0
  56. package/src/automation/manager-runtime-sync.ts +54 -0
  57. package/src/automation/manager-runtime.ts +721 -0
  58. package/src/automation/manager.ts +10 -0
  59. package/src/automation/service.ts +242 -0
  60. package/src/channels/builtin/account-actions.ts +490 -0
  61. package/src/channels/builtin/accounts.ts +433 -0
  62. package/src/channels/builtin/contracts.ts +405 -0
  63. package/src/channels/builtin/plugins.ts +308 -0
  64. package/src/channels/builtin/rendering.ts +174 -0
  65. package/src/channels/builtin/setup-schema.ts +504 -0
  66. package/src/channels/builtin/shared.ts +96 -0
  67. package/src/channels/builtin/surfaces.ts +57 -0
  68. package/src/channels/builtin/targets.ts +693 -0
  69. package/src/channels/builtin-runtime.ts +443 -0
  70. package/src/channels/delivery/shared.ts +199 -0
  71. package/src/channels/delivery/strategies-bridge.ts +246 -0
  72. package/src/channels/delivery/strategies-core.ts +299 -0
  73. package/src/channels/delivery/strategies-enterprise.ts +178 -0
  74. package/src/channels/delivery/types.ts +59 -0
  75. package/src/channels/delivery-router.ts +127 -0
  76. package/src/channels/index.ts +77 -0
  77. package/src/channels/plugin-registry.ts +551 -0
  78. package/src/channels/provider-runtime.ts +330 -0
  79. package/src/channels/reply-pipeline.ts +522 -0
  80. package/src/channels/route-manager.ts +340 -0
  81. package/src/channels/surface-registry.ts +186 -0
  82. package/src/config/helper-model.ts +233 -0
  83. package/src/config/index.ts +193 -0
  84. package/src/config/manager.ts +404 -0
  85. package/src/config/secrets.ts +547 -0
  86. package/src/config/service-registry.ts +329 -0
  87. package/src/config/subscription-auth.ts +31 -0
  88. package/src/config/subscription-providers.ts +127 -0
  89. package/src/config/tool-llm.ts +110 -0
  90. package/src/control-plane/approval-broker.ts +351 -0
  91. package/src/control-plane/gateway.ts +713 -0
  92. package/src/control-plane/index.ts +54 -0
  93. package/src/control-plane/media-contract-schemas.ts +208 -0
  94. package/src/control-plane/method-catalog-admin.ts +136 -0
  95. package/src/control-plane/method-catalog-channels.ts +591 -0
  96. package/src/control-plane/method-catalog-control-automation.ts +475 -0
  97. package/src/control-plane/method-catalog-control-core.ts +594 -0
  98. package/src/control-plane/method-catalog-control.ts +8 -0
  99. package/src/control-plane/method-catalog-events.ts +74 -0
  100. package/src/control-plane/method-catalog-knowledge.ts +531 -0
  101. package/src/control-plane/method-catalog-media.ts +279 -0
  102. package/src/control-plane/method-catalog-runtime.ts +304 -0
  103. package/src/control-plane/method-catalog-shared.ts +223 -0
  104. package/src/control-plane/method-catalog.ts +242 -0
  105. package/src/control-plane/operator-contract-schemas-admin.ts +639 -0
  106. package/src/control-plane/operator-contract-schemas-channels.ts +375 -0
  107. package/src/control-plane/operator-contract-schemas-control.ts +226 -0
  108. package/src/control-plane/operator-contract-schemas-domains.ts +4 -0
  109. package/src/control-plane/operator-contract-schemas-knowledge.ts +582 -0
  110. package/src/control-plane/operator-contract-schemas-media.ts +297 -0
  111. package/src/control-plane/operator-contract-schemas-permissions.ts +100 -0
  112. package/src/control-plane/operator-contract-schemas-remote.ts +38 -0
  113. package/src/control-plane/operator-contract-schemas-runtime.ts +563 -0
  114. package/src/control-plane/operator-contract-schemas-shared.ts +85 -0
  115. package/src/control-plane/operator-contract-schemas-telemetry.ts +349 -0
  116. package/src/control-plane/operator-contract-schemas.ts +6 -0
  117. package/src/control-plane/operator-contract.ts +163 -0
  118. package/src/control-plane/session-broker.ts +780 -0
  119. package/src/core/compaction-sections.ts +492 -0
  120. package/src/core/compaction-types.ts +147 -0
  121. package/src/core/composer-state.ts +59 -0
  122. package/src/core/context-compaction.ts +542 -0
  123. package/src/core/conversation-compaction.ts +68 -0
  124. package/src/core/conversation-diff.ts +55 -0
  125. package/src/core/conversation-rendering.ts +343 -0
  126. package/src/core/conversation-utils.ts +72 -0
  127. package/src/core/conversation.ts +775 -0
  128. package/src/core/event-replay.ts +287 -0
  129. package/src/core/orchestrator-context-runtime.ts +407 -0
  130. package/src/core/orchestrator-follow-up-runtime.ts +134 -0
  131. package/src/core/orchestrator-runtime.ts +132 -0
  132. package/src/core/orchestrator-tool-runtime.ts +468 -0
  133. package/src/core/orchestrator-turn-helpers.ts +355 -0
  134. package/src/core/orchestrator-turn-loop.ts +443 -0
  135. package/src/core/orchestrator.ts +733 -0
  136. package/src/core/plan-command-handler.ts +169 -0
  137. package/src/core/system-message-router.ts +210 -0
  138. package/src/core/transcript-events/classify.ts +95 -0
  139. package/src/core/transcript-events/index.ts +15 -0
  140. package/src/daemon/cli.ts +88 -0
  141. package/src/daemon/control-plane.ts +522 -0
  142. package/src/daemon/facade-composition.ts +397 -0
  143. package/src/daemon/facade.ts +638 -0
  144. package/src/daemon/helpers.ts +74 -0
  145. package/src/daemon/http/router-route-contexts.ts +370 -0
  146. package/src/daemon/http/router.ts +531 -0
  147. package/src/daemon/http-listener.ts +301 -0
  148. package/src/daemon/index.ts +3 -0
  149. package/src/daemon/server.ts +1 -0
  150. package/src/daemon/service-manager.ts +413 -0
  151. package/src/daemon/surface-actions.ts +183 -0
  152. package/src/daemon/surface-delivery.ts +530 -0
  153. package/src/daemon/surface-policy.ts +60 -0
  154. package/src/daemon/transport-events.ts +110 -0
  155. package/src/daemon/types.ts +191 -0
  156. package/src/export/markdown.ts +213 -0
  157. package/src/export/session-export.ts +633 -0
  158. package/src/git/index.ts +1 -0
  159. package/src/git/service.ts +414 -0
  160. package/src/hooks/chain-engine.ts +414 -0
  161. package/src/hooks/dispatcher.ts +414 -0
  162. package/src/hooks/hook-api.ts +170 -0
  163. package/src/hooks/index.ts +48 -0
  164. package/src/hooks/runners/agent.ts +93 -0
  165. package/src/hooks/runners/prompt.ts +69 -0
  166. package/src/hooks/workbench.ts +360 -0
  167. package/src/input/autocomplete.ts +96 -0
  168. package/src/input/bookmark-modal.ts +115 -0
  169. package/src/input/command-registry.ts +300 -0
  170. package/src/input/commands/branch-runtime.ts +72 -0
  171. package/src/input/commands/config.ts +515 -0
  172. package/src/input/commands/control-room-runtime.ts +255 -0
  173. package/src/input/commands/conversation-runtime.ts +207 -0
  174. package/src/input/commands/diff-runtime.ts +161 -0
  175. package/src/input/commands/discovery-runtime.ts +45 -0
  176. package/src/input/commands/eval.ts +204 -0
  177. package/src/input/commands/experience-runtime.ts +278 -0
  178. package/src/input/commands/git-runtime.ts +81 -0
  179. package/src/input/commands/guidance-runtime.ts +101 -0
  180. package/src/input/commands/health-runtime.ts +434 -0
  181. package/src/input/commands/hooks-runtime.ts +148 -0
  182. package/src/input/commands/incident-runtime.ts +95 -0
  183. package/src/input/commands/integration-runtime.ts +394 -0
  184. package/src/input/commands/intelligence-runtime.ts +223 -0
  185. package/src/input/commands/knowledge.ts +368 -0
  186. package/src/input/commands/local-auth-runtime.ts +105 -0
  187. package/src/input/commands/local-provider-runtime.ts +170 -0
  188. package/src/input/commands/local-runtime.ts +458 -0
  189. package/src/input/commands/local-setup-review.ts +192 -0
  190. package/src/input/commands/local-setup-transfer.ts +134 -0
  191. package/src/input/commands/local-setup.ts +292 -0
  192. package/src/input/commands/managed-runtime.ts +208 -0
  193. package/src/input/commands/marketplace-runtime.ts +290 -0
  194. package/src/input/commands/mcp-runtime.ts +202 -0
  195. package/src/input/commands/memory-product-runtime.ts +111 -0
  196. package/src/input/commands/memory.ts +151 -0
  197. package/src/input/commands/notify-runtime.ts +83 -0
  198. package/src/input/commands/operator-panel-runtime.ts +141 -0
  199. package/src/input/commands/operator-runtime.ts +392 -0
  200. package/src/input/commands/permissions-runtime.ts +104 -0
  201. package/src/input/commands/planning-runtime.ts +97 -0
  202. package/src/input/commands/platform-access-runtime.ts +422 -0
  203. package/src/input/commands/platform-runtime.ts +6 -0
  204. package/src/input/commands/platform-sandbox-qemu.ts +137 -0
  205. package/src/input/commands/platform-sandbox-runtime.ts +406 -0
  206. package/src/input/commands/platform-sandbox-session.ts +128 -0
  207. package/src/input/commands/platform-services-runtime.ts +246 -0
  208. package/src/input/commands/policy-dispatch.ts +339 -0
  209. package/src/input/commands/policy.ts +17 -0
  210. package/src/input/commands/product-runtime.ts +351 -0
  211. package/src/input/commands/profile-sync-runtime.ts +99 -0
  212. package/src/input/commands/provider-accounts-runtime.ts +113 -0
  213. package/src/input/commands/provider.ts +363 -0
  214. package/src/input/commands/quit-shared.ts +162 -0
  215. package/src/input/commands/recall-bundle.ts +132 -0
  216. package/src/input/commands/recall-capture.ts +152 -0
  217. package/src/input/commands/recall-query.ts +229 -0
  218. package/src/input/commands/recall-review.ts +98 -0
  219. package/src/input/commands/recall-shared.ts +22 -0
  220. package/src/input/commands/remote-runtime-pool.ts +106 -0
  221. package/src/input/commands/remote-runtime-setup.ts +199 -0
  222. package/src/input/commands/remote-runtime.ts +531 -0
  223. package/src/input/commands/replay-runtime.ts +18 -0
  224. package/src/input/commands/runtime-services.ts +279 -0
  225. package/src/input/commands/schedule-runtime.ts +332 -0
  226. package/src/input/commands/services-runtime.ts +207 -0
  227. package/src/input/commands/session-content.ts +408 -0
  228. package/src/input/commands/session-workflow.ts +464 -0
  229. package/src/input/commands/session.ts +376 -0
  230. package/src/input/commands/settings-sync-runtime.ts +173 -0
  231. package/src/input/commands/share-runtime.ts +114 -0
  232. package/src/input/commands/shell-core.ts +320 -0
  233. package/src/input/commands/skills-runtime.ts +221 -0
  234. package/src/input/commands/subscription-runtime.ts +434 -0
  235. package/src/input/commands/tasks-runtime.ts +230 -0
  236. package/src/input/commands/teamwork-runtime.ts +374 -0
  237. package/src/input/commands/teleport-runtime.ts +57 -0
  238. package/src/input/commands/worktree-runtime.ts +137 -0
  239. package/src/input/commands.ts +127 -0
  240. package/src/input/file-picker.ts +192 -0
  241. package/src/input/handler-command-route.ts +106 -0
  242. package/src/input/handler-content-actions.ts +465 -0
  243. package/src/input/handler-feed-routes.ts +541 -0
  244. package/src/input/handler-feed.ts +361 -0
  245. package/src/input/handler-modal-routes.ts +335 -0
  246. package/src/input/handler-modal-stack.ts +237 -0
  247. package/src/input/handler-modal-token-routes.ts +272 -0
  248. package/src/input/handler-picker-routes.ts +416 -0
  249. package/src/input/handler-prompt-buffer.ts +320 -0
  250. package/src/input/handler-shortcuts.ts +195 -0
  251. package/src/input/handler-ui-state.ts +294 -0
  252. package/src/input/handler.ts +798 -0
  253. package/src/input/input-history.ts +267 -0
  254. package/src/input/keybindings.ts +256 -0
  255. package/src/input/model-picker.ts +730 -0
  256. package/src/input/panel-integration-actions.ts +77 -0
  257. package/src/input/profile-picker-modal.ts +222 -0
  258. package/src/input/search.ts +100 -0
  259. package/src/input/selection-modal.ts +163 -0
  260. package/src/input/selection.ts +135 -0
  261. package/src/input/session-picker-modal.ts +136 -0
  262. package/src/input/settings-modal.ts +718 -0
  263. package/src/input/submission-intent.ts +18 -0
  264. package/src/input/submission-router.ts +64 -0
  265. package/src/integrations/index.ts +42 -0
  266. package/src/integrations/notifier.ts +206 -0
  267. package/src/integrations/webhooks.ts +177 -0
  268. package/src/knowledge/consolidation.ts +346 -0
  269. package/src/knowledge/graphql.ts +324 -0
  270. package/src/knowledge/index.ts +60 -0
  271. package/src/knowledge/ingest-compile.ts +386 -0
  272. package/src/knowledge/ingest-context.ts +18 -0
  273. package/src/knowledge/ingest-inputs.ts +387 -0
  274. package/src/knowledge/ingest.ts +20 -0
  275. package/src/knowledge/internal.ts +257 -0
  276. package/src/knowledge/knowledge-api.ts +432 -0
  277. package/src/knowledge/lint.ts +121 -0
  278. package/src/knowledge/memory-sync.ts +62 -0
  279. package/src/knowledge/packet.ts +370 -0
  280. package/src/knowledge/scheduling.ts +283 -0
  281. package/src/knowledge/service.ts +715 -0
  282. package/src/main.ts +798 -0
  283. package/src/mcp/client.ts +383 -0
  284. package/src/mcp/index.ts +12 -0
  285. package/src/mcp/mcp-api.ts +90 -0
  286. package/src/mcp/registry.ts +508 -0
  287. package/src/media/builtin-image-understanding.ts +303 -0
  288. package/src/media/builtin-providers.ts +26 -0
  289. package/src/media/index.ts +18 -0
  290. package/src/multimodal/index.ts +13 -0
  291. package/src/multimodal/service.ts +492 -0
  292. package/src/panels/agent-inspector-panel.ts +515 -0
  293. package/src/panels/agent-inspector-shared.ts +94 -0
  294. package/src/panels/agent-logs-panel.ts +539 -0
  295. package/src/panels/agent-logs-shared.ts +129 -0
  296. package/src/panels/approval-panel.ts +169 -0
  297. package/src/panels/automation-control-panel.ts +253 -0
  298. package/src/panels/base-panel.ts +72 -0
  299. package/src/panels/builtin/agent.ts +88 -0
  300. package/src/panels/builtin/development.ts +111 -0
  301. package/src/panels/builtin/knowledge.ts +26 -0
  302. package/src/panels/builtin/operations.ts +385 -0
  303. package/src/panels/builtin/session.ts +61 -0
  304. package/src/panels/builtin/shared.ts +240 -0
  305. package/src/panels/builtin-panels.ts +23 -0
  306. package/src/panels/cockpit-panel.ts +183 -0
  307. package/src/panels/communication-panel.ts +191 -0
  308. package/src/panels/context-visualizer-panel.ts +199 -0
  309. package/src/panels/control-plane-panel.ts +266 -0
  310. package/src/panels/cost-tracker-panel.ts +444 -0
  311. package/src/panels/debug-panel.ts +432 -0
  312. package/src/panels/diff-panel.ts +518 -0
  313. package/src/panels/docs-panel.ts +283 -0
  314. package/src/panels/eval-panel.ts +399 -0
  315. package/src/panels/file-explorer-panel.ts +556 -0
  316. package/src/panels/file-preview-panel.ts +412 -0
  317. package/src/panels/forensics-panel.ts +364 -0
  318. package/src/panels/git-panel.ts +630 -0
  319. package/src/panels/hooks-panel.ts +274 -0
  320. package/src/panels/incident-review-panel.ts +247 -0
  321. package/src/panels/index.ts +48 -0
  322. package/src/panels/intelligence-panel.ts +176 -0
  323. package/src/panels/knowledge-panel.ts +328 -0
  324. package/src/panels/local-auth-panel.ts +146 -0
  325. package/src/panels/marketplace-panel.ts +223 -0
  326. package/src/panels/mcp-panel.ts +260 -0
  327. package/src/panels/memory-panel.ts +293 -0
  328. package/src/panels/ops-control-panel.ts +184 -0
  329. package/src/panels/ops-strategy-panel.ts +235 -0
  330. package/src/panels/orchestration-panel.ts +254 -0
  331. package/src/panels/panel-list-panel.ts +508 -0
  332. package/src/panels/panel-manager.ts +538 -0
  333. package/src/panels/panel-picker.ts +106 -0
  334. package/src/panels/plan-dashboard-panel.ts +272 -0
  335. package/src/panels/plugins-panel.ts +201 -0
  336. package/src/panels/policy-panel.ts +308 -0
  337. package/src/panels/polish.ts +668 -0
  338. package/src/panels/provider-account-snapshot.ts +259 -0
  339. package/src/panels/provider-accounts-panel.ts +221 -0
  340. package/src/panels/provider-health-domains.ts +211 -0
  341. package/src/panels/provider-health-panel.ts +725 -0
  342. package/src/panels/provider-health-tracker.ts +115 -0
  343. package/src/panels/provider-stats-panel.ts +366 -0
  344. package/src/panels/remote-panel.ts +449 -0
  345. package/src/panels/routes-panel.ts +228 -0
  346. package/src/panels/sandbox-panel.ts +289 -0
  347. package/src/panels/schedule-panel.ts +344 -0
  348. package/src/panels/search-focus.ts +32 -0
  349. package/src/panels/security-panel.ts +329 -0
  350. package/src/panels/services-panel.ts +271 -0
  351. package/src/panels/session-browser-panel.ts +399 -0
  352. package/src/panels/session-maintenance.ts +125 -0
  353. package/src/panels/settings-sync-panel.ts +164 -0
  354. package/src/panels/skills-panel.ts +475 -0
  355. package/src/panels/subscription-panel.ts +273 -0
  356. package/src/panels/symbol-outline-panel.ts +486 -0
  357. package/src/panels/system-messages-panel.ts +224 -0
  358. package/src/panels/tasks-panel.ts +448 -0
  359. package/src/panels/thinking-panel.ts +304 -0
  360. package/src/panels/token-budget-panel.ts +469 -0
  361. package/src/panels/tool-inspector-panel.ts +434 -0
  362. package/src/panels/types.ts +44 -0
  363. package/src/panels/watchers-panel.ts +241 -0
  364. package/src/panels/welcome-panel.ts +64 -0
  365. package/src/panels/worktree-panel.ts +180 -0
  366. package/src/panels/wrfc-panel.ts +480 -0
  367. package/src/permissions/briefs/build.ts +88 -0
  368. package/src/permissions/manager.ts +356 -0
  369. package/src/permissions/prompt.ts +184 -0
  370. package/src/plugins/api.ts +383 -0
  371. package/src/plugins/loader.ts +304 -0
  372. package/src/plugins/manager.ts +481 -0
  373. package/src/profiles/shape.ts +58 -0
  374. package/src/providers/amazon-bedrock-mantle.ts +50 -0
  375. package/src/providers/amazon-bedrock.ts +61 -0
  376. package/src/providers/anthropic-compat.ts +373 -0
  377. package/src/providers/anthropic-sdk-provider.ts +230 -0
  378. package/src/providers/anthropic-vertex.ts +59 -0
  379. package/src/providers/anthropic.ts +469 -0
  380. package/src/providers/auto-register.ts +417 -0
  381. package/src/providers/builtin-catalog.ts +326 -0
  382. package/src/providers/builtin-registry.ts +575 -0
  383. package/src/providers/cache-planner.ts +258 -0
  384. package/src/providers/capabilities.ts +601 -0
  385. package/src/providers/custom-loader.ts +425 -0
  386. package/src/providers/discovered-compat.ts +18 -0
  387. package/src/providers/discovered-factory.ts +61 -0
  388. package/src/providers/discovered-traits.ts +138 -0
  389. package/src/providers/gemini.ts +462 -0
  390. package/src/providers/github-copilot.ts +254 -0
  391. package/src/providers/index.ts +47 -0
  392. package/src/providers/interface.ts +185 -0
  393. package/src/providers/llama-cpp.ts +402 -0
  394. package/src/providers/lm-studio-helpers.ts +367 -0
  395. package/src/providers/lm-studio.ts +484 -0
  396. package/src/providers/model-catalog-cache.ts +221 -0
  397. package/src/providers/model-catalog-notifications.ts +97 -0
  398. package/src/providers/model-catalog-synthetic.ts +202 -0
  399. package/src/providers/model-catalog.ts +211 -0
  400. package/src/providers/model-limits.ts +280 -0
  401. package/src/providers/ollama.ts +469 -0
  402. package/src/providers/openai-codex.ts +472 -0
  403. package/src/providers/openai-compat.ts +615 -0
  404. package/src/providers/openai.ts +231 -0
  405. package/src/providers/optimizer.ts +381 -0
  406. package/src/providers/provider-api.ts +553 -0
  407. package/src/providers/registry-helpers.ts +34 -0
  408. package/src/providers/registry-models.ts +77 -0
  409. package/src/providers/registry-types.ts +67 -0
  410. package/src/providers/registry.ts +729 -0
  411. package/src/providers/runtime-metadata.ts +149 -0
  412. package/src/providers/runtime-snapshot.ts +130 -0
  413. package/src/providers/synthetic.ts +561 -0
  414. package/src/providers/tier-prompts.ts +84 -0
  415. package/src/providers/tool-formats.ts +414 -0
  416. package/src/renderer/agent-detail-modal.ts +285 -0
  417. package/src/renderer/autocomplete-overlay.ts +154 -0
  418. package/src/renderer/block-actions.ts +76 -0
  419. package/src/renderer/bookmark-modal.ts +101 -0
  420. package/src/renderer/bottom-bar.ts +58 -0
  421. package/src/renderer/buffer.ts +34 -0
  422. package/src/renderer/code-block.ts +373 -0
  423. package/src/renderer/compositor.ts +261 -0
  424. package/src/renderer/context-inspector.ts +219 -0
  425. package/src/renderer/conversation-layout.ts +67 -0
  426. package/src/renderer/conversation-overlays.ts +123 -0
  427. package/src/renderer/conversation-surface.ts +260 -0
  428. package/src/renderer/diff-view.ts +132 -0
  429. package/src/renderer/diff.ts +122 -0
  430. package/src/renderer/file-picker-overlay.ts +101 -0
  431. package/src/renderer/file-tree.ts +153 -0
  432. package/src/renderer/git-status.ts +89 -0
  433. package/src/renderer/help-overlay.ts +247 -0
  434. package/src/renderer/history-search-overlay.ts +73 -0
  435. package/src/renderer/layout-engine.ts +97 -0
  436. package/src/renderer/layout.ts +32 -0
  437. package/src/renderer/live-tail-modal.ts +156 -0
  438. package/src/renderer/markdown.ts +777 -0
  439. package/src/renderer/modal-factory.ts +467 -0
  440. package/src/renderer/modal-utils.ts +24 -0
  441. package/src/renderer/model-picker-overlay.ts +396 -0
  442. package/src/renderer/overlay-box.ts +165 -0
  443. package/src/renderer/overlay-viewport.ts +104 -0
  444. package/src/renderer/panel-composite.ts +80 -0
  445. package/src/renderer/panel-picker-overlay.ts +202 -0
  446. package/src/renderer/panel-tab-bar.ts +69 -0
  447. package/src/renderer/panel-workspace-bar.ts +38 -0
  448. package/src/renderer/process-indicator.ts +96 -0
  449. package/src/renderer/process-modal.ts +295 -0
  450. package/src/renderer/profile-picker-modal.ts +129 -0
  451. package/src/renderer/progress.ts +98 -0
  452. package/src/renderer/search-overlay.ts +54 -0
  453. package/src/renderer/selection-modal-overlay.ts +214 -0
  454. package/src/renderer/semantic-diff.ts +369 -0
  455. package/src/renderer/session-picker-modal.ts +127 -0
  456. package/src/renderer/settings-modal.ts +701 -0
  457. package/src/renderer/shell-surface.ts +88 -0
  458. package/src/renderer/surface-layout.ts +101 -0
  459. package/src/renderer/syntax-highlighter.ts +542 -0
  460. package/src/renderer/system-message.ts +83 -0
  461. package/src/renderer/tab-strip.ts +108 -0
  462. package/src/renderer/text-layout.ts +31 -0
  463. package/src/renderer/thinking.ts +17 -0
  464. package/src/renderer/tool-call.ts +233 -0
  465. package/src/renderer/ui-factory.ts +524 -0
  466. package/src/renderer/ui-primitives.ts +96 -0
  467. package/src/runtime/auth/inspection.ts +125 -0
  468. package/src/runtime/bootstrap-background.ts +147 -0
  469. package/src/runtime/bootstrap-command-context.ts +265 -0
  470. package/src/runtime/bootstrap-command-parts.ts +357 -0
  471. package/src/runtime/bootstrap-core.ts +375 -0
  472. package/src/runtime/bootstrap-helpers.ts +88 -0
  473. package/src/runtime/bootstrap-hook-bridge.ts +271 -0
  474. package/src/runtime/bootstrap-runtime-events.ts +254 -0
  475. package/src/runtime/bootstrap-services.ts +197 -0
  476. package/src/runtime/bootstrap-shell.ts +262 -0
  477. package/src/runtime/bootstrap.ts +488 -0
  478. package/src/runtime/compaction/index.ts +90 -0
  479. package/src/runtime/compaction/lifecycle.ts +167 -0
  480. package/src/runtime/compaction/manager.ts +474 -0
  481. package/src/runtime/compaction/quality-score.ts +279 -0
  482. package/src/runtime/compaction/resume-repair.ts +183 -0
  483. package/src/runtime/compaction/strategies/autocompact.ts +65 -0
  484. package/src/runtime/compaction/strategies/boundary-commit.ts +106 -0
  485. package/src/runtime/compaction/strategies/collapse.ts +90 -0
  486. package/src/runtime/compaction/strategies/index.ts +23 -0
  487. package/src/runtime/compaction/strategies/microcompact.ts +74 -0
  488. package/src/runtime/compaction/strategies/reactive.ts +89 -0
  489. package/src/runtime/compaction/types.ts +221 -0
  490. package/src/runtime/context.ts +158 -0
  491. package/src/runtime/diagnostics/actions.ts +776 -0
  492. package/src/runtime/diagnostics/index.ts +99 -0
  493. package/src/runtime/diagnostics/panels/agents.ts +252 -0
  494. package/src/runtime/diagnostics/panels/events.ts +188 -0
  495. package/src/runtime/diagnostics/panels/health.ts +242 -0
  496. package/src/runtime/diagnostics/panels/index.ts +24 -0
  497. package/src/runtime/diagnostics/panels/ops.ts +156 -0
  498. package/src/runtime/diagnostics/panels/policy.ts +176 -0
  499. package/src/runtime/diagnostics/panels/tasks.ts +251 -0
  500. package/src/runtime/diagnostics/panels/tool-calls.ts +267 -0
  501. package/src/runtime/diagnostics/provider.ts +262 -0
  502. package/src/runtime/ecosystem/catalog.ts +606 -0
  503. package/src/runtime/ecosystem/recommendations.ts +117 -0
  504. package/src/runtime/emitters/agents.ts +96 -0
  505. package/src/runtime/emitters/automation.ts +112 -0
  506. package/src/runtime/emitters/communication.ts +53 -0
  507. package/src/runtime/emitters/compaction.ts +161 -0
  508. package/src/runtime/emitters/control-plane.ts +65 -0
  509. package/src/runtime/emitters/deliveries.ts +65 -0
  510. package/src/runtime/emitters/forensics.ts +17 -0
  511. package/src/runtime/emitters/index.ts +59 -0
  512. package/src/runtime/emitters/knowledge.ts +129 -0
  513. package/src/runtime/emitters/mcp.ts +95 -0
  514. package/src/runtime/emitters/ops.ts +163 -0
  515. package/src/runtime/emitters/orchestration.ts +87 -0
  516. package/src/runtime/emitters/permissions.ts +98 -0
  517. package/src/runtime/emitters/planner.ts +23 -0
  518. package/src/runtime/emitters/plugins.ts +78 -0
  519. package/src/runtime/emitters/providers.ts +30 -0
  520. package/src/runtime/emitters/routes.ts +57 -0
  521. package/src/runtime/emitters/security.ts +53 -0
  522. package/src/runtime/emitters/session.ts +93 -0
  523. package/src/runtime/emitters/surfaces.ts +57 -0
  524. package/src/runtime/emitters/tasks.ts +69 -0
  525. package/src/runtime/emitters/tools.ts +140 -0
  526. package/src/runtime/emitters/transport.ts +78 -0
  527. package/src/runtime/emitters/turn.ts +155 -0
  528. package/src/runtime/emitters/ui.ts +57 -0
  529. package/src/runtime/emitters/watchers.ts +57 -0
  530. package/src/runtime/emitters/workflows.ts +79 -0
  531. package/src/runtime/eval/index.ts +48 -0
  532. package/src/runtime/eval/runner.ts +163 -0
  533. package/src/runtime/eval/suites.ts +264 -0
  534. package/src/runtime/events/domain-map.ts +148 -0
  535. package/src/runtime/events/index.ts +194 -0
  536. package/src/runtime/events/turn.ts +60 -0
  537. package/src/runtime/events/workflows.ts +17 -0
  538. package/src/runtime/forensics/collector.ts +693 -0
  539. package/src/runtime/forensics/index.ts +23 -0
  540. package/src/runtime/foundation-clients.ts +78 -0
  541. package/src/runtime/foundation-services.ts +96 -0
  542. package/src/runtime/guidance.ts +183 -0
  543. package/src/runtime/health/effect-handlers.ts +189 -0
  544. package/src/runtime/health/index.ts +70 -0
  545. package/src/runtime/health/wiring.ts +115 -0
  546. package/src/runtime/index.ts +174 -0
  547. package/src/runtime/integration/helpers.ts +640 -0
  548. package/src/runtime/lifecycle.ts +107 -0
  549. package/src/runtime/mcp/index.ts +68 -0
  550. package/src/runtime/mcp/manager.ts +513 -0
  551. package/src/runtime/network/inbound.ts +131 -0
  552. package/src/runtime/network/index.ts +30 -0
  553. package/src/runtime/network/outbound.ts +292 -0
  554. package/src/runtime/network/shared.ts +82 -0
  555. package/src/runtime/operator-client.ts +235 -0
  556. package/src/runtime/ops/control-plane.ts +363 -0
  557. package/src/runtime/ops/index.ts +122 -0
  558. package/src/runtime/ops/playbooks/index.ts +10 -0
  559. package/src/runtime/ops/playbooks/session-unrecoverable.ts +196 -0
  560. package/src/runtime/ops/playbooks/stuck-turn.ts +197 -0
  561. package/src/runtime/ops/runtime-context.ts +100 -0
  562. package/src/runtime/ops-api.ts +27 -0
  563. package/src/runtime/orchestration/spawn-policy.ts +83 -0
  564. package/src/runtime/peer-client.ts +404 -0
  565. package/src/runtime/perf/index.ts +57 -0
  566. package/src/runtime/perf/slo-collector.ts +375 -0
  567. package/src/runtime/permissions/index.ts +190 -0
  568. package/src/runtime/permissions/policy-runtime.ts +175 -0
  569. package/src/runtime/permissions/preflight.ts +101 -0
  570. package/src/runtime/permissions/rule-suggestions.ts +36 -0
  571. package/src/runtime/plugins/hot-reload.ts +221 -0
  572. package/src/runtime/plugins/index.ts +84 -0
  573. package/src/runtime/plugins/lifecycle.ts +95 -0
  574. package/src/runtime/plugins/manager.ts +474 -0
  575. package/src/runtime/plugins/manifest.ts +167 -0
  576. package/src/runtime/plugins/quarantine.ts +202 -0
  577. package/src/runtime/plugins/trust.ts +291 -0
  578. package/src/runtime/plugins/types.ts +205 -0
  579. package/src/runtime/provider-accounts/registry.ts +326 -0
  580. package/src/runtime/remote/distributed-runtime-contract-schemas.ts +386 -0
  581. package/src/runtime/remote/index.ts +488 -0
  582. package/src/runtime/remote/runner-registry.ts +438 -0
  583. package/src/runtime/remote/supervisor.ts +70 -0
  584. package/src/runtime/runtime-hook-api.ts +5 -0
  585. package/src/runtime/runtime-knowledge-api.ts +14 -0
  586. package/src/runtime/runtime-mcp-api.ts +5 -0
  587. package/src/runtime/runtime-ops-api.ts +86 -0
  588. package/src/runtime/runtime-provider-api.ts +18 -0
  589. package/src/runtime/sandbox/backend.ts +291 -0
  590. package/src/runtime/sandbox/manager.ts +364 -0
  591. package/src/runtime/sandbox/provisioning.ts +422 -0
  592. package/src/runtime/sandbox/session-registry.ts +289 -0
  593. package/src/runtime/services.ts +541 -0
  594. package/src/runtime/session-maintenance.ts +188 -0
  595. package/src/runtime/session-persistence.ts +288 -0
  596. package/src/runtime/session-return-context.ts +195 -0
  597. package/src/runtime/settings/control-plane-store.ts +258 -0
  598. package/src/runtime/settings/control-plane.ts +599 -0
  599. package/src/runtime/shell-command-extensions.ts +54 -0
  600. package/src/runtime/shell-command-ops.ts +207 -0
  601. package/src/runtime/shell-command-platform.ts +47 -0
  602. package/src/runtime/shell-command-services.ts +143 -0
  603. package/src/runtime/shell-command-workspace.ts +31 -0
  604. package/src/runtime/store/domains/conversation.ts +181 -0
  605. package/src/runtime/store/domains/domain-read-matrix.ts +17 -0
  606. package/src/runtime/store/domains/index.ts +222 -0
  607. package/src/runtime/store/domains/panels.ts +117 -0
  608. package/src/runtime/store/domains/permissions.ts +143 -0
  609. package/src/runtime/store/domains/ui-perf.ts +103 -0
  610. package/src/runtime/store/helpers/reducers/conversation.ts +228 -0
  611. package/src/runtime/store/helpers/reducers/lifecycle.ts +440 -0
  612. package/src/runtime/store/helpers/reducers/shared.ts +60 -0
  613. package/src/runtime/store/helpers/reducers/sync.ts +555 -0
  614. package/src/runtime/store/helpers/reducers.ts +30 -0
  615. package/src/runtime/store/index.ts +304 -0
  616. package/src/runtime/store/selectors/index.ts +354 -0
  617. package/src/runtime/store/state.ts +137 -0
  618. package/src/runtime/tasks/adapters/acp-adapter.ts +211 -0
  619. package/src/runtime/tasks/adapters/agent-adapter.ts +208 -0
  620. package/src/runtime/tasks/adapters/index.ts +16 -0
  621. package/src/runtime/tasks/adapters/process-adapter.ts +214 -0
  622. package/src/runtime/tasks/adapters/scheduler-adapter.ts +193 -0
  623. package/src/runtime/tasks/index.ts +68 -0
  624. package/src/runtime/tasks/manager.ts +415 -0
  625. package/src/runtime/telemetry/api-helpers.ts +517 -0
  626. package/src/runtime/telemetry/api.ts +768 -0
  627. package/src/runtime/telemetry/index.ts +178 -0
  628. package/src/runtime/telemetry/instrumentation/domain-bridge-agent-session.ts +440 -0
  629. package/src/runtime/telemetry/instrumentation/domain-bridge-plugin-mcp.ts +200 -0
  630. package/src/runtime/telemetry/instrumentation/domain-bridge-shared.ts +18 -0
  631. package/src/runtime/telemetry/instrumentation/domain-bridge-transport-task.ts +204 -0
  632. package/src/runtime/telemetry/instrumentation/domain-bridge.ts +125 -0
  633. package/src/runtime/telemetry/instrumentation/index.ts +67 -0
  634. package/src/runtime/tools/context.ts +114 -0
  635. package/src/runtime/tools/index.ts +46 -0
  636. package/src/runtime/tools/phased-executor.ts +448 -0
  637. package/src/runtime/tools/phases/budget.ts +130 -0
  638. package/src/runtime/tools/phases/execute.ts +69 -0
  639. package/src/runtime/tools/phases/index.ts +13 -0
  640. package/src/runtime/tools/phases/map-output.ts +98 -0
  641. package/src/runtime/tools/phases/permission.ts +133 -0
  642. package/src/runtime/tools/phases/posthook.ts +57 -0
  643. package/src/runtime/tools/phases/prehook.ts +68 -0
  644. package/src/runtime/tools/phases/validate.ts +53 -0
  645. package/src/runtime/transports/direct.ts +73 -0
  646. package/src/runtime/transports/http-helpers.ts +218 -0
  647. package/src/runtime/transports/http-types.ts +364 -0
  648. package/src/runtime/transports/http.ts +629 -0
  649. package/src/runtime/transports/realtime.ts +50 -0
  650. package/src/runtime/transports/remote-events.ts +16 -0
  651. package/src/runtime/transports/shared.ts +39 -0
  652. package/src/runtime/transports/ui-runtime-events.ts +35 -0
  653. package/src/runtime/ui/index.ts +39 -0
  654. package/src/runtime/ui/model-picker/data-provider.ts +182 -0
  655. package/src/runtime/ui/model-picker/health-enrichment.ts +228 -0
  656. package/src/runtime/ui/model-picker/index.ts +59 -0
  657. package/src/runtime/ui/model-picker/types.ts +149 -0
  658. package/src/runtime/ui/provider-health/data-provider.ts +244 -0
  659. package/src/runtime/ui/provider-health/fallback-visualizer.ts +69 -0
  660. package/src/runtime/ui/provider-health/index.ts +46 -0
  661. package/src/runtime/ui/provider-health/types.ts +146 -0
  662. package/src/runtime/ui-events.ts +46 -0
  663. package/src/runtime/ui-read-model-helpers.ts +32 -0
  664. package/src/runtime/ui-read-models-core.ts +95 -0
  665. package/src/runtime/ui-read-models-observability-maintenance.ts +81 -0
  666. package/src/runtime/ui-read-models-observability-options.ts +5 -0
  667. package/src/runtime/ui-read-models-observability-remote.ts +73 -0
  668. package/src/runtime/ui-read-models-observability-security.ts +172 -0
  669. package/src/runtime/ui-read-models-observability-system.ts +217 -0
  670. package/src/runtime/ui-read-models-observability.ts +59 -0
  671. package/src/runtime/ui-read-models-operations.ts +203 -0
  672. package/src/runtime/ui-read-models.ts +61 -0
  673. package/src/runtime/ui-service-queries.ts +114 -0
  674. package/src/runtime/ui-services.ts +163 -0
  675. package/src/runtime/worktree/registry.ts +252 -0
  676. package/src/scripts/process-messages.ts +42 -0
  677. package/src/sessions/manager.ts +388 -0
  678. package/src/shell/blocking-input.ts +89 -0
  679. package/src/shell/ui-openers.ts +163 -0
  680. package/src/state/file-watcher.ts +294 -0
  681. package/src/state/index.ts +56 -0
  682. package/src/state/knowledge-injection.ts +214 -0
  683. package/src/state/memory-embedding-http.ts +642 -0
  684. package/src/state/memory-embeddings.ts +312 -0
  685. package/src/state/memory-ingest.ts +132 -0
  686. package/src/state/memory-registry.ts +111 -0
  687. package/src/state/memory-store-helpers.ts +160 -0
  688. package/src/state/memory-store.ts +728 -0
  689. package/src/state/memory-vector-store.ts +418 -0
  690. package/src/templates/manager.ts +187 -0
  691. package/src/tools/agent/index.ts +610 -0
  692. package/src/tools/agent/manager.ts +476 -0
  693. package/src/tools/analyze/git-modes.ts +380 -0
  694. package/src/tools/analyze/index.ts +128 -0
  695. package/src/tools/channel/agent-tools.ts +16 -0
  696. package/src/tools/channel/index.ts +268 -0
  697. package/src/tools/control/index.ts +90 -0
  698. package/src/tools/edit/core.ts +619 -0
  699. package/src/tools/edit/index.ts +4 -0
  700. package/src/tools/edit/phased.ts +33 -0
  701. package/src/tools/fetch/index.ts +3 -0
  702. package/src/tools/fetch/phased.ts +34 -0
  703. package/src/tools/fetch/runtime.ts +499 -0
  704. package/src/tools/index.ts +186 -0
  705. package/src/tools/mcp/index.ts +190 -0
  706. package/src/tools/remote-trigger/index.ts +130 -0
  707. package/src/tools/repl/index.ts +318 -0
  708. package/src/tools/shared/auto-heal.ts +282 -0
  709. package/src/tools/state/index.ts +688 -0
  710. package/src/tools/web-search/index.ts +38 -0
  711. package/src/tools/write/index.ts +604 -0
  712. package/src/tools/write/phased.ts +41 -0
  713. package/src/types/generated/foundation-client-types.ts +22 -0
  714. package/src/types/sql-js.d.ts +15 -0
  715. package/src/utils/splash-lines.ts +46 -0
  716. package/src/version.ts +17 -0
  717. package/src/watchers/index.ts +11 -0
  718. package/src/watchers/registry.ts +517 -0
  719. package/src/web-search/index.ts +26 -0
  720. package/src/web-search/provider-registry.ts +64 -0
  721. package/src/web-search/providers/brave.ts +100 -0
  722. package/src/web-search/providers/duckduckgo.ts +270 -0
  723. package/src/web-search/providers/exa.ts +77 -0
  724. package/src/web-search/providers/firecrawl.ts +90 -0
  725. package/src/web-search/providers/perplexity.ts +86 -0
  726. package/src/web-search/providers/searxng.ts +88 -0
  727. package/src/web-search/providers/shared.ts +249 -0
  728. package/src/web-search/providers/tavily.ts +90 -0
  729. package/src/web-search/service.ts +142 -0
  730. package/src/widget/index.ts +2 -0
  731. package/src/widget/types.ts +9 -0
  732. package/src/widget/widget.ts +8 -0
@@ -0,0 +1,231 @@
1
+ import OpenAI from 'openai';
2
+ import type {
3
+ LLMProvider,
4
+ ChatRequest,
5
+ ChatResponse,
6
+ ProviderEmbeddingRequest,
7
+ ProviderEmbeddingResult,
8
+ ProviderRuntimeMetadata,
9
+ ProviderRuntimeMetadataDeps,
10
+ } from './interface.ts';
11
+ import { ProviderError } from '@pellux/goodvibes-sdk/platform/types/errors';
12
+ import { withRetry } from '@pellux/goodvibes-sdk/platform/utils/retry';
13
+ import {
14
+ toOpenAITools,
15
+ toOpenAIMessages,
16
+ fromOpenAIToolCalls,
17
+ extractTextToolCalls,
18
+ } from './tool-formats.ts';
19
+ import type { OpenAIToolCall } from './tool-formats.ts';
20
+ import type { CacheHitTracker } from '@pellux/goodvibes-sdk/platform/providers/cache-strategy';
21
+ import { extractOpenAIStreamTextDelta } from '@pellux/goodvibes-sdk/platform/providers/openai-stream-delta';
22
+ import { summarizeError, toProviderError } from '@pellux/goodvibes-sdk/platform/utils/error-display';
23
+
24
+ const NOOP_CACHE_HIT_TRACKER: Pick<CacheHitTracker, 'recordTurn'> = {
25
+ recordTurn: () => {},
26
+ };
27
+
28
+ /**
29
+ * OpenAIProvider — wraps the official `openai` npm package.
30
+ * Supports GPT-5 family models with full function/tool calling.
31
+ */
32
+ export class OpenAIProvider implements LLMProvider {
33
+ readonly name = 'openai';
34
+ readonly models: string[] = [];
35
+
36
+ private client: OpenAI;
37
+ private readonly embeddingModel = 'text-embedding-3-small';
38
+ private readonly cacheHitTracker: Pick<CacheHitTracker, 'recordTurn'>;
39
+
40
+ constructor(apiKey: string, cacheHitTracker: Pick<CacheHitTracker, 'recordTurn'> = NOOP_CACHE_HIT_TRACKER) {
41
+ this.client = new OpenAI({ apiKey });
42
+ this.cacheHitTracker = cacheHitTracker;
43
+ }
44
+
45
+ async chat(params: ChatRequest): Promise<ChatResponse> {
46
+ const { messages, tools, model, maxTokens, signal, systemPrompt, onDelta, reasoningEffort: _reasoningEffort } = params;
47
+ // Note: OpenAI GPT-5 does not expose reasoning effort as a configurable API parameter
48
+
49
+ return withRetry(async () => {
50
+ let responseText = '';
51
+ let inputTokens = 0;
52
+ let outputTokens = 0;
53
+ let cacheReadTokens = 0;
54
+ let stopReason: ChatResponse['stopReason'] = 'end';
55
+ let rawToolCalls: OpenAIToolCall[] = [];
56
+
57
+ const openaiMessages = toOpenAIMessages(messages, systemPrompt);
58
+ const openaiTools = tools && tools.length > 0 ? toOpenAITools(tools) : undefined;
59
+
60
+ try {
61
+ const stream = await this.client.chat.completions.create(
62
+ {
63
+ model,
64
+ messages: openaiMessages as Parameters<typeof this.client.chat.completions.create>[0]['messages'],
65
+ ...(openaiTools ? { tools: openaiTools as Parameters<typeof this.client.chat.completions.create>[0]['tools'] } : {}),
66
+ ...(maxTokens ? { max_tokens: maxTokens } : {}),
67
+ stream: true,
68
+ stream_options: { include_usage: true },
69
+ },
70
+ { signal },
71
+ );
72
+
73
+ const accToolCalls: Map<number, { id: string; name: string; args: string }> = new Map();
74
+
75
+ for await (const chunk of stream) {
76
+ const delta = chunk.choices[0]?.delta;
77
+ const textDelta = extractOpenAIStreamTextDelta(chunk);
78
+ for (const contentDelta of textDelta.content) {
79
+ responseText += contentDelta;
80
+ if (onDelta) onDelta({ content: contentDelta });
81
+ }
82
+ for (const reasoningDelta of textDelta.reasoning) {
83
+ if (onDelta) onDelta({ reasoning: reasoningDelta });
84
+ }
85
+
86
+ // Accumulate streaming tool_calls deltas
87
+ if (delta?.tool_calls) {
88
+ for (const tc of delta.tool_calls) {
89
+ const idx = tc.index;
90
+ if (!accToolCalls.has(idx)) {
91
+ accToolCalls.set(idx, { id: tc.id ?? '', name: tc.function?.name ?? '', args: '' });
92
+ }
93
+ const entry = accToolCalls.get(idx)!;
94
+ if (tc.id) entry.id = tc.id;
95
+ if (tc.function?.name) entry.name = tc.function.name;
96
+ if (tc.function?.arguments) entry.args += tc.function.arguments;
97
+ if (onDelta) {
98
+ onDelta({ toolCalls: [{ index: idx, id: tc.id, name: tc.function?.name, arguments: tc.function?.arguments }] });
99
+ }
100
+ }
101
+ }
102
+
103
+ const finishReason = chunk.choices[0]?.finish_reason;
104
+ if (finishReason === 'tool_calls') stopReason = 'tool_use';
105
+ else if (finishReason === 'length') stopReason = 'max_tokens';
106
+
107
+ const usage = (chunk as { usage?: { prompt_tokens?: number; completion_tokens?: number; prompt_tokens_details?: { cached_tokens?: number } } }).usage;
108
+ if (usage) {
109
+ inputTokens = usage.prompt_tokens ?? 0;
110
+ outputTokens = usage.completion_tokens ?? 0;
111
+ cacheReadTokens = usage.prompt_tokens_details?.cached_tokens ?? cacheReadTokens;
112
+ }
113
+ }
114
+
115
+ // Finalise accumulated tool calls
116
+ for (const [, tc] of [...accToolCalls.entries()].sort(([a], [b]) => a - b)) {
117
+ rawToolCalls.push({
118
+ id: tc.id,
119
+ type: 'function',
120
+ function: { name: tc.name, arguments: tc.args },
121
+ });
122
+ }
123
+ } catch (err: unknown) {
124
+ const { hasStatus } = await import('@pellux/goodvibes-sdk/platform/utils/retry');
125
+ const status = hasStatus(err) ? err.status : undefined;
126
+ throw toProviderError(err, {
127
+ ...(status !== undefined ? { statusCode: status } : {}),
128
+ provider: this.name,
129
+ operation: 'chat',
130
+ phase: 'stream',
131
+ });
132
+ }
133
+
134
+ // Some models may emit tool calls as raw text tokens instead of the
135
+ // OpenAI function-calling wire format. Fall back to text extraction.
136
+ let toolCalls = rawToolCalls.length > 0 ? fromOpenAIToolCalls(rawToolCalls) : [];
137
+ if (toolCalls.length === 0 && (responseText.includes('<|toolcallbegin|>') || responseText.includes('<|tool_call_begin|>'))) {
138
+ const extracted = extractTextToolCalls(responseText);
139
+ if (extracted.toolCalls.length > 0) {
140
+ toolCalls = extracted.toolCalls;
141
+ responseText = extracted.cleanedContent;
142
+ stopReason = 'tool_use';
143
+ }
144
+ }
145
+
146
+ this.cacheHitTracker.recordTurn({
147
+ inputTokens,
148
+ cacheReadTokens,
149
+ });
150
+
151
+ return {
152
+ content: responseText,
153
+ toolCalls,
154
+ usage: {
155
+ inputTokens,
156
+ outputTokens,
157
+ ...(cacheReadTokens > 0 ? { cacheReadTokens } : {}),
158
+ },
159
+ stopReason,
160
+ };
161
+ });
162
+ }
163
+
164
+ async embed(request: ProviderEmbeddingRequest): Promise<ProviderEmbeddingResult> {
165
+ let response;
166
+ try {
167
+ response = await this.client.embeddings.create(
168
+ {
169
+ model: request.model ?? this.embeddingModel,
170
+ input: request.text,
171
+ ...(request.dimensions ? { dimensions: request.dimensions } : {}),
172
+ },
173
+ request.signal ? { signal: request.signal } : undefined,
174
+ );
175
+ } catch (error: unknown) {
176
+ throw toProviderError(error, {
177
+ provider: this.name,
178
+ operation: 'embed',
179
+ phase: 'request',
180
+ });
181
+ }
182
+ const embedding = response.data[0]?.embedding ?? [];
183
+ return {
184
+ vector: Float32Array.from(embedding),
185
+ dimensions: embedding.length,
186
+ modelId: response.model,
187
+ metadata: {
188
+ usage: request.usage,
189
+ provider: this.name,
190
+ },
191
+ };
192
+ }
193
+
194
+ async describeRuntime(deps: ProviderRuntimeMetadataDeps): Promise<ProviderRuntimeMetadata> {
195
+ const configured = Boolean(process.env.OPENAI_API_KEY || process.env.OPENAI_KEY);
196
+ const { buildStandardProviderAuthRoutes } = await import('./runtime-metadata.ts');
197
+ const authRoutes = await buildStandardProviderAuthRoutes({
198
+ providerId: 'openai',
199
+ apiKeyEnvVars: ['OPENAI_API_KEY', 'OPENAI_KEY'],
200
+ serviceNames: ['openai'],
201
+ subscriptionProviderId: 'openai',
202
+ }, deps);
203
+ return {
204
+ auth: {
205
+ mode: 'api-key',
206
+ configured,
207
+ detail: configured ? 'OpenAI API key available' : 'OPENAI_API_KEY or OPENAI_KEY not set',
208
+ envVars: ['OPENAI_API_KEY', 'OPENAI_KEY'],
209
+ routes: authRoutes,
210
+ },
211
+ models: {
212
+ models: this.models,
213
+ embeddingModel: this.embeddingModel,
214
+ embeddingDimensions: 384,
215
+ },
216
+ usage: {
217
+ streaming: true,
218
+ toolCalling: true,
219
+ parallelTools: true,
220
+ notes: ['Embeddings use the OpenAI embeddings API.'],
221
+ },
222
+ policy: {
223
+ local: false,
224
+ streamProtocol: 'openai-chat-completions',
225
+ reasoningMode: 'provider-default',
226
+ cacheStrategy: 'implicit-openai-cache-observation',
227
+ notes: ['OpenAI embedding usage is subject to OpenAI API terms.'],
228
+ },
229
+ };
230
+ }
231
+ }
@@ -0,0 +1,381 @@
1
+ /**
2
+ * Provider Optimizer
3
+ *
4
+ * Lives above provider implementations. Routes requests based on capability
5
+ * contracts from ProviderCapabilityRegistry. Supports auto/manual/pinned
6
+ * routing modes with deterministic, fully-explainable decisions.
7
+ *
8
+ * Optimizer off → zero behavior change (selectRoute returns null).
9
+ * Optimizer on → deterministic route explanation for every request profile.
10
+ */
11
+
12
+ import {
13
+ ProviderCapabilityRegistry,
14
+ type RequestProfile,
15
+ type RouteExplanation,
16
+ } from './capabilities.ts';
17
+ import type { ModelDefinition, ProviderRegistry } from './registry.ts';
18
+ import type { ProviderHealthRecord } from '@pellux/goodvibes-sdk/platform/runtime/store/domains/provider-health';
19
+
20
+ // ---------------------------------------------------------------------------
21
+ // Types
22
+ // ---------------------------------------------------------------------------
23
+
24
+ /** Optimizer routing mode. */
25
+ export type OptimizerMode = 'auto' | 'manual' | 'pinned';
26
+
27
+ /** A single fallback transition log entry. */
28
+ export interface FallbackTransition {
29
+ /** Epoch ms when the transition occurred. */
30
+ readonly ts: number;
31
+ /** Provider/model that failed or was skipped. */
32
+ readonly from: string;
33
+ /** Provider/model selected as fallback. */
34
+ readonly to: string;
35
+ /** Human-readable reason for the transition. */
36
+ readonly reason: string;
37
+ }
38
+
39
+ /** Result of a route selection decision. */
40
+ export interface RouteDecision {
41
+ /** Provider ID selected. */
42
+ readonly providerId: string;
43
+ /** Model ID selected. */
44
+ readonly modelId: string;
45
+ /** Full route explanation from the capability registry. */
46
+ readonly explanation: RouteExplanation;
47
+ /** All candidates considered (accepted and rejected). */
48
+ readonly allCandidates: readonly RouteExplanation[];
49
+ /** Epoch ms when this decision was made. */
50
+ readonly decidedAt: number;
51
+ /** Whether this decision was constrained by a pin. */
52
+ readonly pinned: boolean;
53
+ }
54
+
55
+ /** Result of a fallback chain test. */
56
+ export interface FallbackTestResult {
57
+ /** Ordered nodes in the simulated fallback chain. */
58
+ readonly chain: ReadonlyArray<{
59
+ readonly position: number;
60
+ readonly providerId: string;
61
+ readonly modelId: string;
62
+ readonly capable: boolean;
63
+ readonly explanation: RouteExplanation;
64
+ }>;
65
+ /** Number of nodes that satisfy the empty request profile. */
66
+ readonly viableCount: number;
67
+ /** Total nodes tested. */
68
+ readonly totalCount: number;
69
+ /** Epoch ms when the test was run. */
70
+ readonly testedAt: number;
71
+ }
72
+
73
+ // ---------------------------------------------------------------------------
74
+ // ProviderOptimizer
75
+ // ---------------------------------------------------------------------------
76
+
77
+ /**
78
+ * Optimizer that selects the best provider/model for a given request profile.
79
+ *
80
+ * When disabled (`enabled = false`) every method returns null/empty — the
81
+ * optimizer has zero effect on normal request flow.
82
+ *
83
+ * When enabled, routing decisions are driven entirely by `ProviderCapabilityRegistry`
84
+ * capability contracts. The selection algorithm is deterministic: candidates are
85
+ * evaluated in registry order (custom → synthetic → catalog → discovered), and
86
+ * the first capable model wins. Ties are never broken by opaque scoring.
87
+ */
88
+ export class ProviderOptimizer {
89
+ private _mode: OptimizerMode = 'manual';
90
+ private _enabled: boolean;
91
+ private _pinnedProvider: string | null = null;
92
+ private _pinnedModel: string | null = null;
93
+ private readonly _fallbackLog: FallbackTransition[] = [];
94
+ private static readonly MAX_LOG_ENTRIES = 200;
95
+ private readonly _clock: () => number;
96
+ private readonly registry: Pick<ProviderRegistry, 'getCurrentModel' | 'getSelectableModels' | 'explainRoute'>;
97
+ private readonly capabilityRegistry: ProviderCapabilityRegistry;
98
+
99
+ constructor(
100
+ registry: Pick<ProviderRegistry, 'getCurrentModel' | 'getSelectableModels' | 'explainRoute'>,
101
+ capabilityRegistry: ProviderCapabilityRegistry,
102
+ enabled = false,
103
+ clock: () => number = Date.now,
104
+ ) {
105
+ this.registry = registry;
106
+ this.capabilityRegistry = capabilityRegistry;
107
+ this._enabled = enabled;
108
+ this._clock = clock;
109
+ }
110
+
111
+ // -------------------------------------------------------------------------
112
+ // Mode control
113
+ // -------------------------------------------------------------------------
114
+
115
+ /** Current routing mode. */
116
+ get mode(): OptimizerMode {
117
+ return this._mode;
118
+ }
119
+
120
+ /** Whether the optimizer is active. When false, selectRoute always returns null. */
121
+ get enabled(): boolean {
122
+ return this._enabled;
123
+ }
124
+
125
+ /** Enable or disable the optimizer. */
126
+ setEnabled(enabled: boolean): void {
127
+ this._enabled = enabled;
128
+ }
129
+
130
+ /**
131
+ * Set the routing mode.
132
+ * - `auto` — optimizer selects the best capable provider for each request profile.
133
+ * - `manual` — optimizer is advisory only; caller drives provider selection.
134
+ * - `pinned` — optimizer always returns the pinned provider/model (if capable).
135
+ */
136
+ setMode(mode: OptimizerMode): void {
137
+ this._mode = mode;
138
+ if (mode !== 'pinned') {
139
+ this._pinnedProvider = null;
140
+ this._pinnedModel = null;
141
+ }
142
+ }
143
+
144
+ // -------------------------------------------------------------------------
145
+ // Pinning
146
+ // -------------------------------------------------------------------------
147
+
148
+ /**
149
+ * Pin routing to a specific provider and model.
150
+ * Automatically switches mode to `pinned`.
151
+ *
152
+ * @param providerId - Provider name (e.g. `'anthropic'`).
153
+ * @param modelId - Model ID (e.g. `'claude-opus-4-5'`).
154
+ */
155
+ pin(providerId: string, modelId: string): void {
156
+ this._pinnedProvider = providerId;
157
+ this._pinnedModel = modelId;
158
+ this._mode = 'pinned';
159
+ }
160
+
161
+ /** Remove the current pin and return to `manual` mode. */
162
+ unpin(): void {
163
+ this._pinnedProvider = null;
164
+ this._pinnedModel = null;
165
+ this._mode = 'manual';
166
+ }
167
+
168
+ /** Current pin target, or null if not pinned. */
169
+ get pinnedTarget(): { providerId: string; modelId: string } | null {
170
+ if (this._pinnedProvider && this._pinnedModel) {
171
+ return { providerId: this._pinnedProvider, modelId: this._pinnedModel };
172
+ }
173
+ return null;
174
+ }
175
+
176
+ // -------------------------------------------------------------------------
177
+ // Route selection
178
+ // -------------------------------------------------------------------------
179
+
180
+ /**
181
+ * Select the best route for the given request profile.
182
+ *
183
+ * Returns `null` when the optimizer is disabled — callers must handle null
184
+ * and fall through to their own provider selection logic.
185
+ *
186
+ * @param profile - Capability requirements for the request.
187
+ * @param healthSnapshot - Optional map of provider health records for filtering
188
+ * unhealthy providers in `auto` mode.
189
+ * @returns A `RouteDecision` or `null` when optimizer is off.
190
+ *
191
+ * @remarks
192
+ * `selectRoute` is wired by the orchestrator when the `provider-optimizer`
193
+ * feature flag is enabled. This follows the same deferred-integration pattern
194
+ * as session emitters — the method is fully functional but called externally
195
+ * only when the feature is active. Until then it is a no-op (returns `null`).
196
+ */
197
+ selectRoute(
198
+ profile: RequestProfile,
199
+ healthSnapshot?: ReadonlyMap<string, ProviderHealthRecord>,
200
+ ): RouteDecision | null {
201
+ if (!this._enabled) return null;
202
+
203
+ const candidates = this.registry.getSelectableModels();
204
+ const allCandidates: RouteExplanation[] = [];
205
+
206
+ // Pinned mode — evaluate only the pinned target
207
+ if (this._mode === 'pinned' && this._pinnedProvider && this._pinnedModel) {
208
+ const explanation = this.capabilityRegistry.getRouteExplanation(
209
+ this._pinnedProvider,
210
+ this._pinnedModel,
211
+ profile,
212
+ );
213
+ allCandidates.push(explanation);
214
+ return {
215
+ providerId: this._pinnedProvider,
216
+ modelId: this._pinnedModel,
217
+ explanation,
218
+ allCandidates,
219
+ decidedAt: this._clock(),
220
+ pinned: true,
221
+ };
222
+ }
223
+
224
+ // Auto mode — evaluate all selectable models; pick first capable
225
+ // Manual mode — same evaluation but result is advisory (caller may ignore)
226
+ let selected: ModelDefinition | null = null;
227
+ let selectedExplanation: RouteExplanation | null = null;
228
+
229
+ for (const model of candidates) {
230
+ // Skip unhealthy providers in auto mode when health data is available
231
+ if (this._mode === 'auto' && healthSnapshot) {
232
+ const health = healthSnapshot.get(model.provider);
233
+ if (health && (health.status === 'unavailable' || health.status === 'auth_error')) {
234
+ continue;
235
+ }
236
+ }
237
+
238
+ const explanation = this.capabilityRegistry.getRouteExplanation(
239
+ model.provider,
240
+ model.id,
241
+ profile,
242
+ );
243
+ allCandidates.push(explanation);
244
+
245
+ if (explanation.accepted && !selected) {
246
+ selected = model;
247
+ selectedExplanation = explanation;
248
+ }
249
+ }
250
+
251
+ if (!selected || !selectedExplanation) {
252
+ // No capable provider found — return first candidate's explanation as the decision
253
+ // so callers get a fully-populated rejection explanation
254
+ const fallbackExpl = allCandidates[0] ?? this._emptyExplanation();
255
+ return {
256
+ providerId: fallbackExpl.providerId,
257
+ modelId: fallbackExpl.modelId,
258
+ explanation: fallbackExpl,
259
+ allCandidates,
260
+ decidedAt: this._clock(),
261
+ pinned: false,
262
+ };
263
+ }
264
+
265
+ return {
266
+ providerId: selected.provider,
267
+ modelId: selected.id,
268
+ explanation: selectedExplanation,
269
+ allCandidates,
270
+ decidedAt: this._clock(),
271
+ pinned: false,
272
+ };
273
+ }
274
+
275
+ /**
276
+ * Explain the current routing decision for the active model without changing it.
277
+ * Always returns a full explanation even when the optimizer is in manual mode.
278
+ *
279
+ * @param profile - Optional request profile; defaults to empty (no requirements).
280
+ */
281
+ explainCurrentRoute(profile: RequestProfile = {}): RouteExplanation {
282
+ const current = this.registry.getCurrentModel();
283
+ return this.registry.explainRoute(current.registryKey ?? `${current.provider}:${current.id}`, profile);
284
+ }
285
+
286
+ // -------------------------------------------------------------------------
287
+ // Private helpers
288
+ // -------------------------------------------------------------------------
289
+
290
+ /** Returns a fully-typed rejection explanation when no candidates are available. */
291
+ private _emptyExplanation() {
292
+ return {
293
+ accepted: false as const,
294
+ providerId: 'none',
295
+ modelId: 'none',
296
+ summary: 'No selectable models available in registry.',
297
+ rejections: [] as import('./capabilities.ts').RouteRejectionDetail[],
298
+ capability: this.capabilityRegistry.getCapability('unknown', 'unknown'),
299
+ };
300
+ }
301
+
302
+ // -------------------------------------------------------------------------
303
+ // Fallback test
304
+ // -------------------------------------------------------------------------
305
+
306
+ /**
307
+ * Simulate the fallback chain by evaluating all selectable models against
308
+ * the given profile. Returns an ordered list of results (capable first,
309
+ * then incapable) so operators can visualize the full fallback topology.
310
+ *
311
+ * @param profile - Capability requirements to test against.
312
+ */
313
+ testFallback(profile: RequestProfile = {}): FallbackTestResult {
314
+ const candidates = this.registry.getSelectableModels();
315
+
316
+ const chain: Array<{
317
+ position: number;
318
+ providerId: string;
319
+ modelId: string;
320
+ capable: boolean;
321
+ explanation: RouteExplanation;
322
+ }> = [];
323
+
324
+ let position = 0;
325
+ for (const model of candidates) {
326
+ const explanation = this.capabilityRegistry.getRouteExplanation(model.provider, model.id, profile);
327
+ chain.push({
328
+ position,
329
+ providerId: model.provider,
330
+ modelId: model.id,
331
+ capable: explanation.accepted,
332
+ explanation,
333
+ });
334
+ position++;
335
+ }
336
+
337
+ const viableCount = chain.filter((n) => n.capable).length;
338
+
339
+ return {
340
+ chain,
341
+ viableCount,
342
+ totalCount: chain.length,
343
+ testedAt: this._clock(),
344
+ };
345
+ }
346
+
347
+ // -------------------------------------------------------------------------
348
+ // Fallback transition log
349
+ // -------------------------------------------------------------------------
350
+
351
+ /**
352
+ * Record a fallback transition. Called by orchestration layers when a
353
+ * provider fails and routing switches to a fallback.
354
+ *
355
+ * Transitions are always recorded regardless of optimizer enabled state
356
+ * so that manual fallbacks are also visible in the log.
357
+ */
358
+ recordFallbackTransition(from: string, to: string, reason: string): void {
359
+ const entry: FallbackTransition = {
360
+ ts: this._clock(),
361
+ from,
362
+ to,
363
+ reason,
364
+ };
365
+ this._fallbackLog.push(entry);
366
+ // Trim to bounded size
367
+ if (this._fallbackLog.length > ProviderOptimizer.MAX_LOG_ENTRIES) {
368
+ this._fallbackLog.splice(0, this._fallbackLog.length - ProviderOptimizer.MAX_LOG_ENTRIES);
369
+ }
370
+ }
371
+
372
+ /** All recorded fallback transitions (oldest first). */
373
+ get fallbackLog(): readonly FallbackTransition[] {
374
+ return this._fallbackLog;
375
+ }
376
+
377
+ /** Clear the fallback transition log. */
378
+ clearFallbackLog(): void {
379
+ this._fallbackLog.splice(0);
380
+ }
381
+ }