cartethyia 2.8.0 → 2.8.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.env.example +3 -3
- package/dist/dashboard/assets/{BannedPage-Cc0vKpMG.js → BannedPage-Dq530awD.js} +1 -1
- package/dist/dashboard/assets/BannedPage-Dq530awD.js.gz +0 -0
- package/dist/dashboard/assets/{CliToolDetailPage-Bqj2aa1T.js → CliToolDetailPage-DZzaS-7S.js} +1 -1
- package/dist/dashboard/assets/CliToolDetailPage-DZzaS-7S.js.gz +0 -0
- package/dist/dashboard/assets/{CliToolsPage-CXsaOAO2.js → CliToolsPage-DaZZ3cqP.js} +1 -1
- package/dist/dashboard/assets/CliToolsPage-DaZZ3cqP.js.gz +0 -0
- package/dist/dashboard/assets/{CombosPage-BeLpJ4ma.js → CombosPage-BlC_xdkX.js} +1 -1
- package/dist/dashboard/assets/CombosPage-BlC_xdkX.js.gz +0 -0
- package/dist/dashboard/assets/{ConsoleLogPage-DnV0uZ3m.js → ConsoleLogPage-D-rqeVtG.js} +1 -1
- package/dist/dashboard/assets/ConsoleLogPage-D-rqeVtG.js.gz +0 -0
- package/dist/dashboard/assets/{CustomizationPage-CBxAjo63.js → CustomizationPage-7xT5yg2E.js} +1 -1
- package/dist/dashboard/assets/CustomizationPage-7xT5yg2E.js.gz +0 -0
- package/dist/dashboard/assets/{HealthEventsModal-B5yEE0k6.js → HealthEventsModal-Clq8E9cW.js} +1 -1
- package/dist/dashboard/assets/HealthEventsModal-Clq8E9cW.js.gz +0 -0
- package/dist/dashboard/assets/{InjectSystemPromptPanel-BWFLECmz.js → InjectSystemPromptPanel-6Teoq9Se.js} +1 -1
- package/dist/dashboard/assets/InjectSystemPromptPanel-6Teoq9Se.js.gz +0 -0
- package/dist/dashboard/assets/{LoginPage-CgoPc5B9.js → LoginPage-CZuI0MAR.js} +1 -1
- package/dist/dashboard/assets/LoginPage-CZuI0MAR.js.gz +0 -0
- package/dist/dashboard/assets/{ModelPicker-D9bFQern.js → ModelPicker-C1hNTlkr.js} +1 -1
- package/dist/dashboard/assets/ModelPicker-C1hNTlkr.js.gz +0 -0
- package/dist/dashboard/assets/{OverviewPage-B_p4tL8k.js → OverviewPage-0yfhSI1C.js} +1 -1
- package/dist/dashboard/assets/OverviewPage-0yfhSI1C.js.gz +0 -0
- package/dist/dashboard/assets/ProviderDetailPage-xqTxdQ4c.js +8 -0
- package/dist/dashboard/assets/ProviderDetailPage-xqTxdQ4c.js.gz +0 -0
- package/dist/dashboard/assets/{ProviderIcon-D_0PiZtg.js → ProviderIcon-Ddhm1InL.js} +1 -1
- package/dist/dashboard/assets/ProviderIcon-Ddhm1InL.js.gz +0 -0
- package/dist/dashboard/assets/{ProvidersPage-CLI2bJTK.js → ProvidersPage-C3fYuu6i.js} +1 -1
- package/dist/dashboard/assets/ProvidersPage-C3fYuu6i.js.gz +0 -0
- package/dist/dashboard/assets/ProxyPage-CHtJtZ3u.js +9 -0
- package/dist/dashboard/assets/ProxyPage-CHtJtZ3u.js.gz +0 -0
- package/dist/dashboard/assets/{QuotaPage-DA-a1iSN.js → QuotaPage-D1RV_2BX.js} +1 -1
- package/dist/dashboard/assets/QuotaPage-D1RV_2BX.js.gz +0 -0
- package/dist/dashboard/assets/{SettingsPage-CctTga2C.js → SettingsPage-BzZAvYSX.js} +1 -1
- package/dist/dashboard/assets/SettingsPage-BzZAvYSX.js.gz +0 -0
- package/dist/dashboard/assets/{SetupPage-febLU4r1.js → SetupPage--s-EfEIL.js} +1 -1
- package/dist/dashboard/assets/SetupPage--s-EfEIL.js.gz +0 -0
- package/dist/dashboard/assets/{StudioPage-M6fvR5Wz.js → StudioPage-BjXFGSK4.js} +1 -1
- package/dist/dashboard/assets/StudioPage-BjXFGSK4.js.gz +0 -0
- package/dist/dashboard/assets/{UsagePage-nyeuRqz9.js → UsagePage-CP8F8BN7.js} +1 -1
- package/dist/dashboard/assets/UsagePage-CP8F8BN7.js.gz +0 -0
- package/dist/dashboard/assets/{api-keys-BFOlvrJC.js → api-keys-2hc12Uz2.js} +1 -1
- package/dist/dashboard/assets/api-keys-2hc12Uz2.js.gz +0 -0
- package/dist/dashboard/assets/app-DGXbNfAR.css +2 -0
- package/dist/dashboard/assets/app-DGXbNfAR.css.gz +0 -0
- package/dist/dashboard/assets/{assert-CqTLw5e7.js → assert-BMcj1xZE.js} +1 -1
- package/dist/dashboard/assets/assert-BMcj1xZE.js.gz +0 -0
- package/dist/dashboard/assets/{badge-C83EqLB0.js → badge-DkRUuVfz.js} +1 -1
- package/dist/dashboard/assets/badge-DkRUuVfz.js.gz +0 -0
- package/dist/dashboard/assets/{banner-D1xn7pIe.js → banner-CDjW841Q.js} +1 -1
- package/dist/dashboard/assets/banner-CDjW841Q.js.gz +0 -0
- package/dist/dashboard/assets/{card-DU3Lq5Lm.js → card-Bto5UlL9.js} +1 -1
- package/dist/dashboard/assets/card-Bto5UlL9.js.gz +0 -0
- package/dist/dashboard/assets/{cli-tools-Dw1U_drK.js → cli-tools-DaH6g9hL.js} +1 -1
- package/dist/dashboard/assets/cli-tools-DaH6g9hL.js.gz +0 -0
- package/dist/dashboard/assets/{clipboard-button-CEL5Sg_J.js → clipboard-button-BYKBCzjk.js} +1 -1
- package/dist/dashboard/assets/clipboard-button-BYKBCzjk.js.gz +0 -0
- package/dist/dashboard/assets/{dialog-BjFR5UHy.js → dialog-DL0Zftwv.js} +1 -1
- package/dist/dashboard/assets/dialog-DL0Zftwv.js.gz +0 -0
- package/dist/dashboard/assets/{drawer-HvBW0AjI.js → drawer-Dpx_UXaS.js} +1 -1
- package/dist/dashboard/assets/drawer-Dpx_UXaS.js.gz +0 -0
- package/dist/dashboard/assets/{entry-CECVELyy.js → entry-BV7-1NoM.js} +1 -1
- package/dist/dashboard/assets/entry-BV7-1NoM.js.gz +0 -0
- package/dist/dashboard/assets/{entry-DYYofQ7W.js → entry-CGvdNU6r.js} +1 -1
- package/dist/dashboard/assets/entry-CGvdNU6r.js.gz +0 -0
- package/dist/dashboard/assets/{entry-BSu3gFlt.js → entry-DScKYvZj.js} +3 -3
- package/dist/dashboard/assets/entry-DScKYvZj.js.gz +0 -0
- package/dist/dashboard/assets/{formatters-DLW4i8zK.js → formatters-BS3DZlZj.js} +1 -1
- package/dist/dashboard/assets/formatters-BS3DZlZj.js.gz +0 -0
- package/dist/dashboard/assets/{index-1-fCqe64.js → index-SQnvvTWX.js} +2 -2
- package/dist/dashboard/assets/index-SQnvvTWX.js.gz +0 -0
- package/dist/dashboard/assets/{inline-DGvU2oLK.js → inline-Dl-cuLK0.js} +1 -1
- package/dist/dashboard/assets/inline-Dl-cuLK0.js.gz +0 -0
- package/dist/dashboard/assets/{input-iNnO1X2K.js → input-Bfx0EzRc.js} +1 -1
- package/dist/dashboard/assets/input-Bfx0EzRc.js.gz +0 -0
- package/dist/dashboard/assets/{layout-0q8UGypb.js → layout-BxhbQ_JS.js} +1 -1
- package/dist/dashboard/assets/layout-BxhbQ_JS.js.gz +0 -0
- package/dist/dashboard/assets/{list-row-C0w2bQjJ.js → list-row-D49Y4ptn.js} +1 -1
- package/dist/dashboard/assets/list-row-D49Y4ptn.js.gz +0 -0
- package/dist/dashboard/assets/{live-M5aJ_xCa.js → live-CbVTdX9V.js} +1 -1
- package/dist/dashboard/assets/live-CbVTdX9V.js.gz +0 -0
- package/dist/dashboard/assets/{network-BKeQGT3K.js → network-JGvDveof.js} +1 -1
- package/dist/dashboard/assets/network-JGvDveof.js.gz +0 -0
- package/dist/dashboard/assets/{numbers-CivAk3da.js → numbers-Dw6kiew-.js} +1 -1
- package/dist/dashboard/assets/numbers-Dw6kiew-.js.gz +0 -0
- package/dist/dashboard/assets/{pagination-CpzvI5ep.js → pagination-iUoI8GeE.js} +1 -1
- package/dist/dashboard/assets/pagination-iUoI8GeE.js.gz +0 -0
- package/dist/dashboard/assets/providers/sensenova-intl.png +0 -0
- package/dist/dashboard/assets/providers/sensenova.png +0 -0
- package/dist/dashboard/assets/{routing-BFQX2VBc.js → routing-8jZr-3WE.js} +1 -1
- package/dist/dashboard/assets/routing-8jZr-3WE.js.gz +0 -0
- package/dist/dashboard/assets/{select-CXbck0jG.js → select-oO1FxMVb.js} +1 -1
- package/dist/dashboard/assets/select-oO1FxMVb.js.gz +0 -0
- package/dist/dashboard/assets/{settings-C_XvMHh9.js → settings-CLr3kdIx.js} +1 -1
- package/dist/dashboard/assets/settings-CLr3kdIx.js.gz +0 -0
- package/dist/dashboard/assets/{stack-DggRiCxE.js → stack-Y3pDteZr.js} +1 -1
- package/dist/dashboard/assets/stack-Y3pDteZr.js.gz +0 -0
- package/dist/dashboard/assets/{state-ClFzfbYp.js → state-CArX_Iak.js} +1 -1
- package/dist/dashboard/assets/state-CArX_Iak.js.gz +0 -0
- package/dist/dashboard/assets/{switch-CTIFxKqS.js → switch-DwlwmDO-.js} +1 -1
- package/dist/dashboard/assets/switch-DwlwmDO-.js.gz +0 -0
- package/dist/dashboard/assets/{useMutation-BClG3yWj.js → useMutation-DJ9GYEgf.js} +1 -1
- package/dist/dashboard/assets/useMutation-DJ9GYEgf.js.gz +0 -0
- package/dist/dashboard/index.html +2 -2
- package/dist/dashboard/index.html.gz +0 -0
- package/dist/dashboard/precompressed-assets.json +51 -51
- package/migrations/full-postgres/0047_add_provider_device_flow_proxy.sql +17 -0
- package/migrations/lite-sqlite3/0047_add_provider_device_flow_proxy.sql +19 -0
- package/package.json +1 -1
- package/src/boot/app.ts +1 -1
- package/src/boot/dependencies.ts +4 -6
- package/src/config/providers.ts +6 -5
- package/src/config/spec.ts +8 -8
- package/src/console/backup/nine-router.ts +71 -10
- package/src/console/backup/service.ts +8 -1
- package/src/console/console-router.ts +1 -1
- package/src/console/domain-registration.ts +7 -2
- package/src/console/inferhub/client.ts +1 -1
- package/src/console/observability/live.ts +2 -2
- package/src/console/providers/catalog/contracts.ts +9 -3
- package/src/console/providers/catalog/model-operations.ts +2 -3
- package/src/console/providers/catalog/provider-operations.ts +1 -1
- package/src/console/providers/catalog/routes.ts +2 -2
- package/src/console/providers/catalog/store.ts +1914 -1907
- package/src/console/providers/detail/routes.ts +1 -0
- package/src/console/providers/detail/store.ts +4 -0
- package/src/console/providers/oauth/callback-listener.ts +30 -11
- package/src/console/providers/oauth/device-egress.ts +123 -0
- package/src/console/providers/oauth/routes.ts +123 -16
- package/src/console/quota/account-quota-tenant.ts +5 -5
- package/src/console/quota/account-test-egress.ts +2 -2
- package/src/console/quota/daily-growth-job.ts +1 -1
- package/src/console/routing/pools/contracts.ts +1 -1
- package/src/console/routing/pools/operations.ts +1 -1
- package/src/console/routing/pools/probe-verdict.ts +2 -2
- package/src/console/routing/pools/relay-deploy.ts +1 -1
- package/src/console/routing/pools/store.ts +4 -4
- package/src/network/client.ts +67 -0
- package/src/network/egress/bidi-session.ts +322 -0
- package/src/network/egress/dial.ts +201 -0
- package/src/network/egress/factory.ts +191 -0
- package/src/network/{outbound-fetch.ts → egress/fetch.ts} +195 -29
- package/src/network/egress/tls-profile.ts +123 -0
- package/src/network/egress/ws.ts +175 -0
- package/src/network/{types.ts → pool/agent-config.ts} +1 -1
- package/src/network/pool/agent.ts +2 -2
- package/src/network/{pool-cooldown-store.ts → pool/cooldown-store.ts} +7 -7
- package/src/network/{pool-health-machine.ts → pool/health.ts} +205 -6
- package/src/network/pool/resolver.ts +10 -849
- package/src/network/pool/selector.ts +2 -2
- package/src/network/ssrf.ts +1 -1
- package/src/network/{retry.ts → util/retry.ts} +1 -1
- package/src/observability/telemetry-buffer.ts +1 -1
- package/src/persistence/schema.ts +9 -0
- package/src/persistence/ttl-cache.ts +1 -1
- package/src/protocol/codecs.ts +58 -1
- package/src/protocol/request/messages.ts +31 -18
- package/src/protocol/response/messages.ts +34 -7
- package/src/protocol/translation/quirks.ts +15 -0
- package/src/protocol/upstream/send-claude-messages.ts +2 -2
- package/src/providers/adapters/compatible-adapter.ts +5 -0
- package/src/providers/authentication/oauth-client.ts +40 -6
- package/src/providers/authentication/oauth-device-flow.ts +7 -3
- package/src/providers/authentication/oauth-flow-store.ts +82 -1
- package/src/providers/authentication/oauth-refresh-service.ts +766 -739
- package/src/providers/default-registry.ts +76 -0
- package/src/providers/discovery/discovery-types.ts +7 -0
- package/src/providers/discovery/probe-phases.ts +6 -2
- package/src/providers/discovery/probing-service.ts +7 -0
- package/src/providers/integrations/antigravity/antigravity-protocol.ts +11 -0
- package/src/providers/integrations/buddy/account.ts +969 -0
- package/src/providers/integrations/buddy/capabilities.ts +10 -10
- package/src/providers/integrations/buddy/{buddy-catalog-shared.ts → catalog.ts} +198 -136
- package/src/providers/integrations/buddy/{buddy-chat-shared.ts → chat.ts} +5 -5
- package/src/providers/integrations/buddy/codebuddy/index.ts +429 -0
- package/src/providers/integrations/buddy/codebuddy/shared.ts +4 -4
- package/src/providers/integrations/buddy/{buddy-identity.ts → headers.ts} +138 -140
- package/src/providers/integrations/buddy/lifecycle.ts +1018 -0
- package/src/providers/integrations/buddy/{buddy-media.ts → media.ts} +1 -1
- package/src/providers/integrations/cline/cline-oauth.ts +10 -5
- package/src/providers/integrations/cline/cline.ts +3 -4
- package/src/providers/integrations/clixad/clixad-oauth.ts +98 -0
- package/src/providers/integrations/clixad/clixad-quota.ts +132 -0
- package/src/providers/integrations/clixad/provider.ts +145 -0
- package/src/providers/integrations/codex/codex-oauth.ts +8 -5
- package/src/providers/integrations/cursor/cursor-auth.ts +1 -1
- package/src/providers/integrations/cursor/cursor-hardening.ts +279 -0
- package/src/providers/integrations/cursor/cursor-http2.ts +605 -6
- package/src/providers/integrations/cursor/cursor-shared.ts +1 -1
- package/src/providers/integrations/cursor/cursor.ts +485 -70
- package/src/providers/integrations/deepai/deepai-catalog.ts +149 -0
- package/src/providers/integrations/deepai/deepai-common.ts +145 -0
- package/src/providers/integrations/deepai/deepai-oauth.ts +129 -0
- package/src/providers/integrations/deepai/deepai-quota.ts +97 -0
- package/src/providers/integrations/deepai/provider.ts +42 -0
- package/src/providers/integrations/devin/devin-auth.ts +7 -0
- package/src/providers/integrations/factory/factory-oauth.ts +16 -7
- package/src/providers/integrations/freebuff/freebuff.ts +2 -2
- package/src/providers/integrations/freepi/freepi-catalog.ts +5 -0
- package/src/providers/integrations/freepi/freepi-discovery.ts +2 -2
- package/src/providers/integrations/freepi/freepi-headers.ts +2 -2
- package/src/providers/integrations/freepi/freepi-protocol.ts +11 -2
- package/src/providers/integrations/freepi/freepi-realm.ts +0 -3
- package/src/providers/integrations/freepi/freepi-session.ts +158 -0
- package/src/providers/integrations/freepi/freepi.ts +80 -54
- package/src/providers/integrations/github/github-discovery.ts +30 -13
- package/src/providers/integrations/github/github-oauth.ts +217 -44
- package/src/providers/integrations/github/github-quota.ts +22 -5
- package/src/providers/integrations/github/github.ts +40 -32
- package/src/providers/integrations/grok/grok-oauth.ts +4 -4
- package/src/providers/integrations/hermes/hermes-oauth.ts +3 -3
- package/src/providers/integrations/hermes/hermes.ts +34 -5
- package/src/providers/integrations/kilo/kilo-oauth.ts +4 -4
- package/src/providers/integrations/kilo/kilo.ts +1 -1
- package/src/providers/integrations/kimi/kimi-oauth.ts +3 -3
- package/src/providers/integrations/kiro/kiro-oauth.ts +2 -2
- package/src/providers/integrations/muse/muse-oauth.ts +5 -5
- package/src/providers/integrations/opencode/fingerprint.ts +1 -1
- package/src/providers/integrations/openrouter/provider.ts +1 -1
- package/src/providers/integrations/perch/perch-protocol.ts +0 -3
- package/src/providers/integrations/perch/perch.ts +3 -3
- package/src/providers/integrations/qoder/claim-qoder-credits.ts +1 -1
- package/src/providers/integrations/qoder/qoder-adapter.ts +19 -113
- package/src/providers/integrations/qoder/qoder-auth.ts +8 -1
- package/src/providers/integrations/qoder/qoder-catalog.ts +1 -1
- package/src/providers/integrations/qoder/qoder-chat.ts +25 -8
- package/src/providers/integrations/qoder/qoder-checkin.ts +1 -1
- package/src/providers/integrations/qoder/qoder-cosy.ts +37 -9
- package/src/providers/integrations/qoder/qoder-oauth.ts +9 -2
- package/src/providers/integrations/qoder/qoder-realm.ts +13 -36
- package/src/providers/integrations/qoder/qoder-sse.ts +447 -68
- package/src/providers/integrations/qoder/qoder-types.ts +9 -0
- package/src/providers/integrations/qoder/qoder.ts +3 -25
- package/src/providers/integrations/sensenova/provider.ts +144 -0
- package/src/providers/integrations/trae/trae-quota.ts +15 -1
- package/src/providers/integrations/vercel/provider.ts +117 -0
- package/src/providers/integrations/vercel/vercel-quota.ts +96 -0
- package/src/providers/integrations/xai/xai-oauth.ts +5 -5
- package/src/providers/integrations/zcode-start-plan/gifts.ts +1 -1
- package/src/providers/integrations/zcode-start-plan/oauth.ts +3 -3
- package/src/providers/integrations/zro/zro.ts +2 -1
- package/src/providers/operations/account-refresh-status.ts +14 -0
- package/src/providers/operations/client-versions.ts +95 -30
- package/src/providers/operations/oauth-refresh-lead.ts +46 -22
- package/src/providers/operations/provider-caches.ts +1 -1
- package/src/providers/operations/provider-credential-service.ts +22 -25
- package/src/providers/operations/session-resolution.ts +17 -1
- package/src/providers/provider-contracts.ts +2 -2
- package/src/providers/provider-metadata.ts +30 -0
- package/src/providers/quota/quota-contracts.ts +2 -0
- package/src/providers/quota/refresh.ts +25 -3
- package/src/security/ip-boundary.ts +1 -1
- package/src/transport/dispatch/attempt-finalize.ts +1 -1
- package/src/transport/dispatch/attempt-loop.ts +3 -3
- package/src/transport/dispatch/handler-deps.ts +1 -1
- package/src/transport/dispatch/leases.ts +1 -1
- package/src/transport/dispatch/retry-policy.ts +1 -1
- package/src/transport/dispatch/streaming/finalize.ts +2 -2
- package/src/transport/dispatch/streaming/stream.ts +1 -1
- package/src/transport/dispatch/upstream.ts +1 -1
- package/src/transport/shutdown-notice.ts +1 -1
- package/src/workers/buddy-growth-tasks.ts +8 -8
- package/src/workers/daily-checkin.ts +4 -4
- package/src/workers/quota-refresh-sweep.ts +1 -1
- package/src/workers/zcode-gift-claim.ts +1 -1
- package/dist/dashboard/assets/BannedPage-Cc0vKpMG.js.gz +0 -0
- package/dist/dashboard/assets/CliToolDetailPage-Bqj2aa1T.js.gz +0 -0
- package/dist/dashboard/assets/CliToolsPage-CXsaOAO2.js.gz +0 -0
- package/dist/dashboard/assets/CombosPage-BeLpJ4ma.js.gz +0 -0
- package/dist/dashboard/assets/ConsoleLogPage-DnV0uZ3m.js.gz +0 -0
- package/dist/dashboard/assets/CustomizationPage-CBxAjo63.js.gz +0 -0
- package/dist/dashboard/assets/HealthEventsModal-B5yEE0k6.js.gz +0 -0
- package/dist/dashboard/assets/InjectSystemPromptPanel-BWFLECmz.js.gz +0 -0
- package/dist/dashboard/assets/LoginPage-CgoPc5B9.js.gz +0 -0
- package/dist/dashboard/assets/ModelPicker-D9bFQern.js.gz +0 -0
- package/dist/dashboard/assets/OverviewPage-B_p4tL8k.js.gz +0 -0
- package/dist/dashboard/assets/ProviderDetailPage-rs5E2rxv.js +0 -8
- package/dist/dashboard/assets/ProviderDetailPage-rs5E2rxv.js.gz +0 -0
- package/dist/dashboard/assets/ProviderIcon-D_0PiZtg.js.gz +0 -0
- package/dist/dashboard/assets/ProvidersPage-CLI2bJTK.js.gz +0 -0
- package/dist/dashboard/assets/ProxyPage-BwNC_-Cx.js +0 -9
- package/dist/dashboard/assets/ProxyPage-BwNC_-Cx.js.gz +0 -0
- package/dist/dashboard/assets/QuotaPage-DA-a1iSN.js.gz +0 -0
- package/dist/dashboard/assets/SettingsPage-CctTga2C.js.gz +0 -0
- package/dist/dashboard/assets/SetupPage-febLU4r1.js.gz +0 -0
- package/dist/dashboard/assets/StudioPage-M6fvR5Wz.js.gz +0 -0
- package/dist/dashboard/assets/UsagePage-nyeuRqz9.js.gz +0 -0
- package/dist/dashboard/assets/api-keys-BFOlvrJC.js.gz +0 -0
- package/dist/dashboard/assets/app-Dx2QgsNj.css +0 -2
- package/dist/dashboard/assets/app-Dx2QgsNj.css.gz +0 -0
- package/dist/dashboard/assets/assert-CqTLw5e7.js.gz +0 -0
- package/dist/dashboard/assets/badge-C83EqLB0.js.gz +0 -0
- package/dist/dashboard/assets/banner-D1xn7pIe.js.gz +0 -0
- package/dist/dashboard/assets/card-DU3Lq5Lm.js.gz +0 -0
- package/dist/dashboard/assets/cli-tools-Dw1U_drK.js.gz +0 -0
- package/dist/dashboard/assets/clipboard-button-CEL5Sg_J.js.gz +0 -0
- package/dist/dashboard/assets/dialog-BjFR5UHy.js.gz +0 -0
- package/dist/dashboard/assets/drawer-HvBW0AjI.js.gz +0 -0
- package/dist/dashboard/assets/entry-BSu3gFlt.js.gz +0 -0
- package/dist/dashboard/assets/entry-CECVELyy.js.gz +0 -0
- package/dist/dashboard/assets/entry-DYYofQ7W.js.gz +0 -0
- package/dist/dashboard/assets/formatters-DLW4i8zK.js.gz +0 -0
- package/dist/dashboard/assets/index-1-fCqe64.js.gz +0 -0
- package/dist/dashboard/assets/inline-DGvU2oLK.js.gz +0 -0
- package/dist/dashboard/assets/input-iNnO1X2K.js.gz +0 -0
- package/dist/dashboard/assets/layout-0q8UGypb.js.gz +0 -0
- package/dist/dashboard/assets/list-row-C0w2bQjJ.js.gz +0 -0
- package/dist/dashboard/assets/live-M5aJ_xCa.js.gz +0 -0
- package/dist/dashboard/assets/network-BKeQGT3K.js.gz +0 -0
- package/dist/dashboard/assets/numbers-CivAk3da.js.gz +0 -0
- package/dist/dashboard/assets/pagination-CpzvI5ep.js.gz +0 -0
- package/dist/dashboard/assets/routing-BFQX2VBc.js.gz +0 -0
- package/dist/dashboard/assets/select-CXbck0jG.js.gz +0 -0
- package/dist/dashboard/assets/settings-C_XvMHh9.js.gz +0 -0
- package/dist/dashboard/assets/stack-DggRiCxE.js.gz +0 -0
- package/dist/dashboard/assets/state-ClFzfbYp.js.gz +0 -0
- package/dist/dashboard/assets/switch-CTIFxKqS.js.gz +0 -0
- package/dist/dashboard/assets/useMutation-BClG3yWj.js.gz +0 -0
- package/src/console/providers/catalog/discover-constants.ts +0 -6
- package/src/network/pool-health.ts +0 -198
- package/src/providers/integrations/buddy/buddy-checkin.ts +0 -521
- package/src/providers/integrations/buddy/buddy-cli-headers.ts +0 -76
- package/src/providers/integrations/buddy/buddy-conversation-headers.ts +0 -130
- package/src/providers/integrations/buddy/buddy-discovery-shared.ts +0 -234
- package/src/providers/integrations/buddy/buddy-growth-shared.ts +0 -496
- package/src/providers/integrations/buddy/buddy-oauth-shared.ts +0 -341
- package/src/providers/integrations/buddy/buddy-quota-shared.ts +0 -417
- package/src/providers/integrations/buddy/buddy-server-tools.ts +0 -240
- package/src/providers/integrations/buddy/buddy-usage-shared.ts +0 -221
- package/src/providers/integrations/buddy/buddy-usage-store.ts +0 -181
- package/src/providers/integrations/buddy/codebuddy/cn-catalog.ts +0 -37
- package/src/providers/integrations/buddy/codebuddy/cn-provider.ts +0 -188
- package/src/providers/integrations/buddy/codebuddy/oauth.ts +0 -47
- package/src/providers/integrations/buddy/codebuddy/provider.ts +0 -179
- package/src/providers/integrations/buddy/codebuddy/quota.ts +0 -154
- package/src/providers/integrations/qoder/chat-proto.ts +0 -328
- package/src/providers/integrations/qoder/qoder-grpc.ts +0 -870
- package/src/providers/integrations/qoder/qoder-ide.ts +0 -481
- /package/dist/dashboard/assets/{app-DIXLjojg.js → app-C0gTXEoN.js} +0 -0
- /package/dist/dashboard/assets/{app-DIXLjojg.js.gz → app-C0gTXEoN.js.gz} +0 -0
- /package/src/network/{http2-bidi.ts → bidi.ts} +0 -0
- /package/src/network/pool/{byte-accounting.ts → accounting.ts} +0 -0
- /package/src/network/pool/{pool-scripts.ts → scripts.ts} +0 -0
- /package/src/network/pool/{pool-state.ts → state.ts} +0 -0
- /package/src/network/{backoff.ts → util/backoff.ts} +0 -0
- /package/src/network/{deduplication.ts → util/dedupe.ts} +0 -0
- /package/src/network/{ip-utils.ts → util/ip.ts} +0 -0
- /package/src/network/{rate-limit-verdict.ts → verdict.ts} +0 -0
|
@@ -12,38 +12,38 @@ type BuddyProviderId = "cb" | "cbcn";
|
|
|
12
12
|
*/
|
|
13
13
|
export const BUDDY_PROVIDER_CAPABILITIES = {
|
|
14
14
|
cb: {
|
|
15
|
-
loadAdapter: async () => (await import("./codebuddy/
|
|
16
|
-
loadModels: async () => (await import("./codebuddy/
|
|
15
|
+
loadAdapter: async () => (await import("./codebuddy/index")).createCodeBuddyAdapter(),
|
|
16
|
+
loadModels: async () => (await import("./codebuddy/index")).CODEBUDDY_MODELS,
|
|
17
17
|
loadModelDiscovery: async () => async ({ credential, fetcher }) =>
|
|
18
|
-
(await import("./codebuddy/
|
|
18
|
+
(await import("./codebuddy/index")).discoverCodeBuddyModels({
|
|
19
19
|
credential,
|
|
20
20
|
...(fetcher === undefined ? {} : { fetcher }),
|
|
21
21
|
}),
|
|
22
22
|
loadAuthentication: oauthCapability(
|
|
23
|
-
() => import("./codebuddy/
|
|
23
|
+
() => import("./codebuddy/index"),
|
|
24
24
|
"codeBuddyOAuthClient",
|
|
25
25
|
{ withRefresher: true },
|
|
26
26
|
),
|
|
27
27
|
loadQuotaCollector: quotaCapability(
|
|
28
|
-
() => import("./codebuddy/
|
|
28
|
+
() => import("./codebuddy/index"),
|
|
29
29
|
"fetchCodeBuddyIntlQuota",
|
|
30
30
|
),
|
|
31
31
|
},
|
|
32
32
|
cbcn: {
|
|
33
|
-
loadAdapter: async () => (await import("./codebuddy/
|
|
34
|
-
loadModels: async () => (await import("./codebuddy/
|
|
33
|
+
loadAdapter: async () => (await import("./codebuddy/index")).createCodeBuddyCnAdapter(),
|
|
34
|
+
loadModels: async () => (await import("./codebuddy/index")).CODEBUDDY_CN_MODELS,
|
|
35
35
|
loadModelDiscovery: async () => async ({ credential, fetcher }) =>
|
|
36
|
-
(await import("./codebuddy/
|
|
36
|
+
(await import("./codebuddy/index")).discoverCodeBuddyCnModels({
|
|
37
37
|
credential,
|
|
38
38
|
...(fetcher === undefined ? {} : { fetcher }),
|
|
39
39
|
}),
|
|
40
40
|
loadAuthentication: oauthCapability(
|
|
41
|
-
() => import("./codebuddy/
|
|
41
|
+
() => import("./codebuddy/index"),
|
|
42
42
|
"codeBuddyCnOAuthClient",
|
|
43
43
|
{ withRefresher: true },
|
|
44
44
|
),
|
|
45
45
|
loadQuotaCollector: quotaCapability(
|
|
46
|
-
() => import("./codebuddy/
|
|
46
|
+
() => import("./codebuddy/index"),
|
|
47
47
|
"fetchCodeBuddyCnQuota",
|
|
48
48
|
),
|
|
49
49
|
},
|
|
@@ -1,22 +1,11 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* The buddy-family static catalog row.
|
|
3
|
-
*
|
|
4
|
-
* CodeBuddy (intl + CN) and WorkBuddy describe their static fallback catalogs
|
|
5
|
-
* with the same seven-field tuple and build each row the same way, differing
|
|
6
|
-
* only in the wire endpoint the row targets. Both had their own copy of the
|
|
7
|
-
* tuple type and the builder, so a new column meant editing two identical
|
|
8
|
-
* declarations.
|
|
9
|
-
*
|
|
10
|
-
* Only the row shape and the builder are shared. Identity headers are not:
|
|
11
|
-
* `codebuddyHeaders` sends genuinely different bytes per realm
|
|
12
|
-
* (`X-Product`/`X-IDE-Type`/`X-Domain` versus the CN CLI profile), and those
|
|
13
|
-
* stay with the provider.
|
|
14
|
-
*/
|
|
15
1
|
import { GatewayError } from "../../../protocol/gateway-error";
|
|
16
2
|
import { defineModel } from "../../provider-model-definition";
|
|
17
3
|
import type { ModelDefinition } from "../../provider-model-definition";
|
|
4
|
+
import { asNumber as sharedAsNumber, asRecord } from "../../../shared/coerce";
|
|
5
|
+
import { buddyAccountUid } from "./account";
|
|
6
|
+
|
|
7
|
+
// ── buddy-catalog-shared ──────────────────────────────────────────
|
|
18
8
|
|
|
19
|
-
/** One static catalog row: id, display name, flags, limits, optional tool override. */
|
|
20
9
|
export type BuddyRawEntry = readonly [
|
|
21
10
|
string,
|
|
22
11
|
string,
|
|
@@ -28,14 +17,6 @@ export type BuddyRawEntry = readonly [
|
|
|
28
17
|
boolean?,
|
|
29
18
|
];
|
|
30
19
|
|
|
31
|
-
/**
|
|
32
|
-
* Realm-specific effort ladders.
|
|
33
|
-
*
|
|
34
|
-
* International DeepSeek Flash accepts only `high`; sending CN's `low`/`max`
|
|
35
|
-
* is a 400. A model absent from its realm's table is not clamped. Lives here,
|
|
36
|
-
* next to the catalog rows, so a row can carry its ladder as
|
|
37
|
-
* `reasoningEfforts` without the catalog importing the chat hook.
|
|
38
|
-
*/
|
|
39
20
|
export const BUDDY_INTL_EFFORTS: Readonly<Record<string, readonly string[]>> = {
|
|
40
21
|
"deepseek-v4.1-flash": ["high"],
|
|
41
22
|
"glm-5.2": ["high", "xhigh"],
|
|
@@ -44,6 +25,7 @@ export const BUDDY_INTL_EFFORTS: Readonly<Record<string, readonly string[]>> = {
|
|
|
44
25
|
hy4: ["high"],
|
|
45
26
|
hy4free: ["high"],
|
|
46
27
|
};
|
|
28
|
+
|
|
47
29
|
export const BUDDY_CN_EFFORTS: Readonly<Record<string, readonly string[]>> = {
|
|
48
30
|
"deepseek-v4-flash": ["low", "high", "max"],
|
|
49
31
|
"deepseek-v4-pro": ["low", "high", "xhigh"],
|
|
@@ -57,7 +39,6 @@ export const BUDDY_CN_EFFORTS: Readonly<Record<string, readonly string[]>> = {
|
|
|
57
39
|
hy4free: ["high"],
|
|
58
40
|
};
|
|
59
41
|
|
|
60
|
-
/** The image-generation ids the international buddy providers serve. */
|
|
61
42
|
const BUDDY_IMAGE_MODEL_IDS: readonly { id: string; endpoint: string; ctx: number; out: number }[] = [
|
|
62
43
|
{ id: "gemini-2.5-flash-image", endpoint: "/chat/completions", ctx: 1_000_000, out: 64_000 },
|
|
63
44
|
{ id: "gemini-3.0-pro-image", endpoint: "/chat/completions", ctx: 1_000_000, out: 64_000 },
|
|
@@ -70,16 +51,6 @@ const BUDDY_IMAGE_MODEL_IDS: readonly { id: string; endpoint: string; ctx: numbe
|
|
|
70
51
|
{ id: "hy-image-3.5", endpoint: "/chat/completions", ctx: 1_000_000, out: 64_000 },
|
|
71
52
|
];
|
|
72
53
|
|
|
73
|
-
/**
|
|
74
|
-
* The video-generation ids the international buddy providers serve.
|
|
75
|
-
*
|
|
76
|
-
* `seedance-2.5` is the text-to-video model the buddy facade exposes. It is a
|
|
77
|
-
* distinct service kind (`videoGeneration`), not a chat or image row, so it is
|
|
78
|
-
* built by {@link makeBuddyVideoModels} and reached through
|
|
79
|
-
* `/videos/generations` (relative to each variant's own base) rather than a
|
|
80
|
-
* chat wire. CodeBuddy CN is deliberately absent — it publishes a different
|
|
81
|
-
* roster.
|
|
82
|
-
*/
|
|
83
54
|
const BUDDY_VIDEO_MODEL_IDS: readonly { id: string; endpoint: string; ctx: number; out: number }[] = [
|
|
84
55
|
{ id: "seedance-2.5", endpoint: "/videos/generations", ctx: 1_000_000, out: 128_000 },
|
|
85
56
|
// Published by /v3/config only, tagged `text-to-video` + `image-to-video`.
|
|
@@ -89,42 +60,19 @@ const BUDDY_VIDEO_MODEL_IDS: readonly { id: string; endpoint: string; ctx: numbe
|
|
|
89
60
|
{ id: "kling-video-v3", endpoint: "/videos/generations", ctx: 1_000_000, out: 128_000 },
|
|
90
61
|
];
|
|
91
62
|
|
|
92
|
-
/**
|
|
93
|
-
* Ids that belong to the image-generation rows rather than the chat roster.
|
|
94
|
-
*
|
|
95
|
-
* A caller mapping `BUDDY_SHARED_RAW` through {@link makeBuddyModel} must skip
|
|
96
|
-
* these, or the same model id lands in the catalog twice under two service
|
|
97
|
-
* kinds and becomes ambiguous to resolve.
|
|
98
|
-
*/
|
|
99
63
|
export const BUDDY_IMAGE_MODEL_ID_SET: ReadonlySet<string> = new Set(
|
|
100
64
|
BUDDY_IMAGE_MODEL_IDS.map((entry) => entry.id),
|
|
101
65
|
);
|
|
102
66
|
|
|
103
|
-
/**
|
|
104
|
-
* The CN realm's image-generation ids.
|
|
105
|
-
*
|
|
106
|
-
* Separate from {@link BUDDY_IMAGE_MODEL_IDS} because the realms do not share
|
|
107
|
-
* a roster: `hunyuan-image-alpha` (text-to-image) and
|
|
108
|
-
* `hunyuan-image-alpha-edit` (image-to-image) are published by the CN
|
|
109
|
-
* `/v3/config` only, and the intl image ids are not served there. Sharing one
|
|
110
|
-
* list would either leak CN-only ids onto the international catalogs or force
|
|
111
|
-
* a realm check into every consumer.
|
|
112
|
-
*/
|
|
113
67
|
const BUDDY_CN_IMAGE_MODEL_IDS: readonly { id: string; ctx: number; out: number }[] = [
|
|
114
68
|
{ id: "hunyuan-image-alpha", ctx: 1_000_000, out: 64_000 },
|
|
115
69
|
{ id: "hunyuan-image-alpha-edit", ctx: 1_000_000, out: 64_000 },
|
|
116
70
|
];
|
|
117
71
|
|
|
118
|
-
/** The CN analogue of {@link BUDDY_IMAGE_MODEL_ID_SET}. */
|
|
119
72
|
export const BUDDY_CN_IMAGE_MODEL_ID_SET: ReadonlySet<string> = new Set(
|
|
120
73
|
BUDDY_CN_IMAGE_MODEL_IDS.map((entry) => entry.id),
|
|
121
74
|
);
|
|
122
75
|
|
|
123
|
-
/**
|
|
124
|
-
* Builds the CN image-generation rows for one buddy CN provider.
|
|
125
|
-
*
|
|
126
|
-
* Same shape as {@link makeBuddyImageModels}, scoped to the CN roster.
|
|
127
|
-
*/
|
|
128
76
|
export function makeBuddyCnImageModels(
|
|
129
77
|
providerId: string,
|
|
130
78
|
endpoint: string,
|
|
@@ -145,30 +93,15 @@ export function makeBuddyCnImageModels(
|
|
|
145
93
|
);
|
|
146
94
|
}
|
|
147
95
|
|
|
148
|
-
/**
|
|
149
|
-
* The CN realm's video-generation ids.
|
|
150
|
-
*
|
|
151
|
-
* `kling-video-v3` (text-to-video + image-to-video) and
|
|
152
|
-
* `minimax-video-h3` (text-to-video) are published by the CN `/v3/config`,
|
|
153
|
-
* sharing the async task surface the intl video rows use.
|
|
154
|
-
*/
|
|
155
96
|
const BUDDY_CN_VIDEO_MODEL_IDS: readonly { id: string; ctx: number; out: number }[] = [
|
|
156
97
|
{ id: "kling-video-v3", ctx: 1_000_000, out: 128_000 },
|
|
157
98
|
{ id: "minimax-video-h3", ctx: 1_000_000, out: 128_000 },
|
|
158
99
|
];
|
|
159
100
|
|
|
160
|
-
/** The CN analogue of {@link BUDDY_VIDEO_MODEL_ID_SET}. */
|
|
161
101
|
export const BUDDY_CN_VIDEO_MODEL_ID_SET: ReadonlySet<string> = new Set(
|
|
162
102
|
BUDDY_CN_VIDEO_MODEL_IDS.map((entry) => entry.id),
|
|
163
103
|
);
|
|
164
104
|
|
|
165
|
-
/**
|
|
166
|
-
* Builds the CN video-generation rows for one buddy CN provider.
|
|
167
|
-
*
|
|
168
|
-
* Same shape as {@link makeBuddyVideoModels}, scoped to the CN roster: a video
|
|
169
|
-
* row produces `["video"]` on the `videoGeneration` surface and is reached
|
|
170
|
-
* through the native video route, not a chat wire.
|
|
171
|
-
*/
|
|
172
105
|
export function makeBuddyCnVideoModels(
|
|
173
106
|
providerId: string,
|
|
174
107
|
endpoint: string,
|
|
@@ -189,23 +122,6 @@ export function makeBuddyCnVideoModels(
|
|
|
189
122
|
);
|
|
190
123
|
}
|
|
191
124
|
|
|
192
|
-
/**
|
|
193
|
-
* Ids the buddy facade refuses on a free plan.
|
|
194
|
-
*
|
|
195
|
-
* The international CodeBuddy catalog shares this roster and
|
|
196
|
-
* the same Pro-tier model classification.
|
|
197
|
-
*
|
|
198
|
-
* Nothing in the console directory predicts it. `credits` does not — `kimi-k3`
|
|
199
|
-
* bills `x1.62` and is served while `gpt-5.6-luna` bills `x0.14` and is
|
|
200
|
-
* refused — and `vendor` does not either. Only the refusal itself is a signal,
|
|
201
|
-
* which is why this is a list and not a rule.
|
|
202
|
-
*
|
|
203
|
-
* Hardcoded deliberately: it is one account's tier, so it is a fact about that
|
|
204
|
-
* plan rather than about the model. A pro account serves all six. The pill is
|
|
205
|
-
* therefore a hint about a free account, and a dispatch is what settles it.
|
|
206
|
-
*
|
|
207
|
-
* @see `documentation/research/codebuddy/2026-10-19-codebuddy-chat-dispatch-headers.md`
|
|
208
|
-
*/
|
|
209
125
|
export const BUDDY_PRO_ONLY_MODEL_IDS: ReadonlySet<string> = new Set([
|
|
210
126
|
"primary-model",
|
|
211
127
|
"gpt-5.6-terra",
|
|
@@ -227,18 +143,6 @@ export const BUDDY_PRO_ONLY_MODEL_IDS: ReadonlySet<string> = new Set([
|
|
|
227
143
|
"claude-opus-4.7-1m",
|
|
228
144
|
]);
|
|
229
145
|
|
|
230
|
-
/**
|
|
231
|
-
* Builds the image-generation rows for one buddy provider.
|
|
232
|
-
*
|
|
233
|
-
* Shared rather than copied per provider: cb serves the same image
|
|
234
|
-
* models from the same facade, so the roster and the declared capabilities are
|
|
235
|
-
* one decision instead of two that drift. CodeBuddy CN is deliberately absent —
|
|
236
|
-
* it publishes a different roster.
|
|
237
|
-
*
|
|
238
|
-
* `endpoint` is explicit because the realms disagree about the path their
|
|
239
|
-
* base URL expects, and a bare `defineModel` would infer the generic default
|
|
240
|
-
* and produce a URL the upstream rejects.
|
|
241
|
-
*/
|
|
242
146
|
export function makeBuddyImageModels(
|
|
243
147
|
providerId: string,
|
|
244
148
|
endpoint: string,
|
|
@@ -260,15 +164,6 @@ export function makeBuddyImageModels(
|
|
|
260
164
|
);
|
|
261
165
|
}
|
|
262
166
|
|
|
263
|
-
/**
|
|
264
|
-
* Builds the video-generation rows for one buddy provider.
|
|
265
|
-
*
|
|
266
|
-
* Shared for the same reason as {@link makeBuddyImageModels}: the roster is one
|
|
267
|
-
* decision, not one per provider that drifts. A video row produces `["video"]`
|
|
268
|
-
* on the `videoGeneration` surface and is reached through the native video
|
|
269
|
-
* route, not a chat wire, so `endpoint` names the upstream generation path
|
|
270
|
-
* rather than a chat-completions path.
|
|
271
|
-
*/
|
|
272
167
|
export function makeBuddyVideoModels(
|
|
273
168
|
providerId: string,
|
|
274
169
|
endpoint: string,
|
|
@@ -289,25 +184,10 @@ export function makeBuddyVideoModels(
|
|
|
289
184
|
);
|
|
290
185
|
}
|
|
291
186
|
|
|
292
|
-
/**
|
|
293
|
-
* Ids that belong to the video-generation rows rather than the chat roster.
|
|
294
|
-
*
|
|
295
|
-
* The video analogue of {@link BUDDY_IMAGE_MODEL_ID_SET}: a caller mapping the
|
|
296
|
-
* shared chat tuple must skip these so `seedance-2.5` never lands in the
|
|
297
|
-
* catalog twice under two service kinds.
|
|
298
|
-
*/
|
|
299
187
|
export const BUDDY_VIDEO_MODEL_ID_SET: ReadonlySet<string> = new Set(
|
|
300
188
|
BUDDY_VIDEO_MODEL_IDS.map((entry) => entry.id),
|
|
301
189
|
);
|
|
302
190
|
|
|
303
|
-
/**
|
|
304
|
-
* Builds one buddy catalog row.
|
|
305
|
-
*
|
|
306
|
-
* `endpoint` is explicit rather than left to the generic `/chat/completions`
|
|
307
|
-
* default because the family's CN base URL differs from the intl one; callers
|
|
308
|
-
* pass the endpoint their base URL actually serves, and `undefined` for the
|
|
309
|
-
* default.
|
|
310
|
-
*/
|
|
311
191
|
export function makeBuddyModel(
|
|
312
192
|
entry: BuddyRawEntry,
|
|
313
193
|
providerId: string,
|
|
@@ -337,17 +217,6 @@ export function makeBuddyModel(
|
|
|
337
217
|
});
|
|
338
218
|
}
|
|
339
219
|
|
|
340
|
-
/**
|
|
341
|
-
* The shared model roster for the international buddy site.
|
|
342
|
-
*
|
|
343
|
-
* CodeBuddy intl serves the model set from the same console directory shape, so
|
|
344
|
-
* the catalog is one hand-written list as the single source of truth, mapped
|
|
345
|
-
* with the provider's own endpoint (`codebuddy.ts` takes the family default).
|
|
346
|
-
*
|
|
347
|
-
* CodeBuddy CN is deliberately NOT on this list: its console publishes a
|
|
348
|
-
* different roster (its own `glm-5v-turbo` / `kimi-k3-1` ids and CN-specific
|
|
349
|
-
* output ceilings), so it keeps its own table.
|
|
350
|
-
*/
|
|
351
220
|
export const BUDDY_SHARED_RAW: readonly BuddyRawEntry[] = [
|
|
352
221
|
["auto", "Auto", false, true, 176_000, 24_000],
|
|
353
222
|
// The three named tiers and `gpt-6-astra` are published by /v3/config and sit
|
|
@@ -400,3 +269,196 @@ export const BUDDY_SHARED_RAW: readonly BuddyRawEntry[] = [
|
|
|
400
269
|
["minimax-m3.1-flash", "MiniMax-M3.1 Flash", true, true, 1_000_000, 128_000],
|
|
401
270
|
["step-5-preview", "Step-5-Preview", true, true, 1_000_000, 64_000, true],
|
|
402
271
|
];
|
|
272
|
+
|
|
273
|
+
// ── buddy-discovery-shared ──────────────────────────────────────────
|
|
274
|
+
|
|
275
|
+
export const BUDDY_CN_MODELS_PATH = "/console/enterprises/personal/models" as const;
|
|
276
|
+
|
|
277
|
+
export const BUDDY_INTL_MODELS_PATH = "/v2/enterprises/personal/models" as const;
|
|
278
|
+
|
|
279
|
+
export const BUDDY_CONFIG_PATH = "/v3/config" as const;
|
|
280
|
+
|
|
281
|
+
const BUDDY_OK_CODE = 0;
|
|
282
|
+
|
|
283
|
+
interface BuddyDirectoryRow {
|
|
284
|
+
readonly id?: unknown;
|
|
285
|
+
readonly name?: unknown;
|
|
286
|
+
readonly disabled?: unknown;
|
|
287
|
+
readonly maxInputTokens?: unknown;
|
|
288
|
+
readonly maxOutputTokens?: unknown;
|
|
289
|
+
readonly supportsImages?: unknown;
|
|
290
|
+
readonly supportsToolCall?: unknown;
|
|
291
|
+
readonly supportsReasoning?: unknown;
|
|
292
|
+
readonly tags?: unknown;
|
|
293
|
+
}
|
|
294
|
+
|
|
295
|
+
function siteOrigin(baseUrl: string): string {
|
|
296
|
+
return baseUrl.replace(/\/+$/, "").replace(/\/v\d+$/, "");
|
|
297
|
+
}
|
|
298
|
+
|
|
299
|
+
function asNumber(value: unknown): number | null {
|
|
300
|
+
return sharedAsNumber(value) ?? null;
|
|
301
|
+
}
|
|
302
|
+
|
|
303
|
+
export async function fetchBuddyDirectoryModels(args: {
|
|
304
|
+
readonly siteUrl: string;
|
|
305
|
+
readonly providerId: string;
|
|
306
|
+
readonly credential: string;
|
|
307
|
+
readonly modelsPath: string;
|
|
308
|
+
readonly endpoint: string | undefined;
|
|
309
|
+
readonly signal?: AbortSignal | undefined;
|
|
310
|
+
readonly fetcher?: typeof fetch | undefined;
|
|
311
|
+
}): Promise<readonly ModelDefinition[] | null> {
|
|
312
|
+
const fetcher = args.fetcher ?? globalThis.fetch;
|
|
313
|
+
// Fetch both catalog scopes and merge them. `/v3/config` is ranked higher and
|
|
314
|
+
// is the primary source (matches the reference gateways), but the personal
|
|
315
|
+
// models path carries models the v3 response does not always publish — so a
|
|
316
|
+
// single-source read can silently miss models that are callable. Merging with
|
|
317
|
+
// dedupe by model id gives the union, mirroring the upstream codebuddy2api
|
|
318
|
+
// catalog aggregation. Each failure falls through to the other source, so a
|
|
319
|
+
// host that answers only one behaves exactly as it does today.
|
|
320
|
+
const v3 = await fetchBuddyDirectoryOnce(args, fetcher, BUDDY_CONFIG_PATH);
|
|
321
|
+
const personal = await fetchBuddyDirectoryOnce(args, fetcher, args.modelsPath);
|
|
322
|
+
if (v3 !== null && personal !== null) return mergeBuddyDirectories(v3, personal);
|
|
323
|
+
return v3 ?? personal;
|
|
324
|
+
}
|
|
325
|
+
|
|
326
|
+
function mergeBuddyDirectories(
|
|
327
|
+
primary: readonly ModelDefinition[],
|
|
328
|
+
supplemental: readonly ModelDefinition[],
|
|
329
|
+
): readonly ModelDefinition[] {
|
|
330
|
+
const seen = new Set<string>();
|
|
331
|
+
const merged: ModelDefinition[] = [];
|
|
332
|
+
for (const model of primary) {
|
|
333
|
+
if (seen.has(model.modelId)) continue;
|
|
334
|
+
seen.add(model.modelId);
|
|
335
|
+
merged.push(model);
|
|
336
|
+
}
|
|
337
|
+
for (const model of supplemental) {
|
|
338
|
+
if (seen.has(model.modelId)) continue;
|
|
339
|
+
seen.add(model.modelId);
|
|
340
|
+
merged.push(model);
|
|
341
|
+
}
|
|
342
|
+
return merged;
|
|
343
|
+
}
|
|
344
|
+
|
|
345
|
+
async function fetchBuddyDirectoryOnce(
|
|
346
|
+
args: {
|
|
347
|
+
readonly siteUrl: string;
|
|
348
|
+
readonly providerId: string;
|
|
349
|
+
readonly credential: string;
|
|
350
|
+
readonly endpoint: string | undefined;
|
|
351
|
+
readonly signal?: AbortSignal | undefined;
|
|
352
|
+
},
|
|
353
|
+
fetcher: typeof fetch,
|
|
354
|
+
path: string,
|
|
355
|
+
): Promise<readonly ModelDefinition[] | null> {
|
|
356
|
+
// The directory scores by account: an access token's `sub` is the uid. An
|
|
357
|
+
// opaque API key carries no identity, and the endpoint still answers for it,
|
|
358
|
+
// so the header is declared absent rather than guessed.
|
|
359
|
+
const uid = buddyAccountUid(args.credential);
|
|
360
|
+
let response: Response;
|
|
361
|
+
try {
|
|
362
|
+
response = await fetcher(`${siteOrigin(args.siteUrl)}${path}`, {
|
|
363
|
+
method: "GET",
|
|
364
|
+
headers: {
|
|
365
|
+
accept: "application/json",
|
|
366
|
+
authorization: `Bearer ${args.credential}`,
|
|
367
|
+
"x-product": "SaaS",
|
|
368
|
+
...(uid === undefined ? { "x-no-user-id": "1" } : { "x-user-id": uid }),
|
|
369
|
+
"x-no-enterprise-id": "1",
|
|
370
|
+
"x-no-department-info": "1",
|
|
371
|
+
},
|
|
372
|
+
...(args.signal === undefined ? {} : { signal: args.signal }),
|
|
373
|
+
});
|
|
374
|
+
} catch {
|
|
375
|
+
return null;
|
|
376
|
+
}
|
|
377
|
+
if (!response.ok) return null;
|
|
378
|
+
let body: unknown;
|
|
379
|
+
try {
|
|
380
|
+
body = await response.json();
|
|
381
|
+
} catch {
|
|
382
|
+
return null;
|
|
383
|
+
}
|
|
384
|
+
const envelope = asRecord(body);
|
|
385
|
+
if (envelope === undefined || envelope["code"] !== BUDDY_OK_CODE) return null;
|
|
386
|
+
const data = asRecord(envelope["data"]);
|
|
387
|
+
const rawModels = data?.["models"];
|
|
388
|
+
if (!Array.isArray(rawModels)) return null;
|
|
389
|
+
|
|
390
|
+
// The CLI agent's roster, when published, is the callable subset.
|
|
391
|
+
const agents = data?.["agents"];
|
|
392
|
+
let cliRoster: Set<string> | undefined;
|
|
393
|
+
if (Array.isArray(agents)) {
|
|
394
|
+
for (const entry of agents) {
|
|
395
|
+
const agent = asRecord(entry);
|
|
396
|
+
if (agent?.["name"] !== "cli") continue;
|
|
397
|
+
const listed = agent["models"];
|
|
398
|
+
if (Array.isArray(listed) && listed.length > 0) {
|
|
399
|
+
cliRoster = new Set(listed.filter((id): id is string => typeof id === "string"));
|
|
400
|
+
}
|
|
401
|
+
break;
|
|
402
|
+
}
|
|
403
|
+
}
|
|
404
|
+
|
|
405
|
+
const entries: BuddyRawEntry[] = [];
|
|
406
|
+
const seen = new Set<string>();
|
|
407
|
+
for (const entry of rawModels) {
|
|
408
|
+
const model = asRecord(entry) as BuddyDirectoryRow | undefined;
|
|
409
|
+
const id = model?.id;
|
|
410
|
+
if (typeof id !== "string" || id.length === 0 || seen.has(id)) continue;
|
|
411
|
+
if (model?.disabled === true) continue;
|
|
412
|
+
// Completion, NES, and codewise rows are not chat models. Listing them
|
|
413
|
+
// offers a route that 400s on a chat request. A declared output of 256 or
|
|
414
|
+
// less is the same signal: a completion model published with a chat-sized
|
|
415
|
+
// name. `text-to-image` is an image row, served by the image roster.
|
|
416
|
+
const lowerId = id.toLowerCase();
|
|
417
|
+
if (lowerId.startsWith("nes-") || lowerId.startsWith("completion-") || lowerId.startsWith("codewise-")) continue;
|
|
418
|
+
const output = asNumber(model?.maxOutputTokens);
|
|
419
|
+
if (output !== null && output <= 256) continue;
|
|
420
|
+
const tags = model?.tags;
|
|
421
|
+
if (Array.isArray(tags) && tags.some((tag) => typeof tag === "string" && tag.toLowerCase() === "text-to-image")) continue;
|
|
422
|
+
if (cliRoster !== undefined && !cliRoster.has(id)) continue;
|
|
423
|
+
seen.add(id);
|
|
424
|
+
entries.push([
|
|
425
|
+
id,
|
|
426
|
+
typeof model?.name === "string" && model.name.length > 0 ? model.name : id,
|
|
427
|
+
model?.supportsReasoning === true,
|
|
428
|
+
model?.supportsImages === true,
|
|
429
|
+
asNumber(model?.maxInputTokens),
|
|
430
|
+
asNumber(model?.maxOutputTokens),
|
|
431
|
+
model?.supportsToolCall === true,
|
|
432
|
+
]);
|
|
433
|
+
}
|
|
434
|
+
if (entries.length === 0) return null;
|
|
435
|
+
return entries.map((entry) => makeBuddyModel(entry, args.providerId, args.endpoint));
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
// ── codebuddy/cn-catalog ──────────────────────────────────────────
|
|
439
|
+
|
|
440
|
+
export const CODEBUDDY_CN_RAW: readonly BuddyRawEntry[] = [
|
|
441
|
+
["glm-5.1", "GLM 5.1", true, true, 200_000, 48_000],
|
|
442
|
+
["glm-5.2", "GLM 5.2", true, true, 1_000_000, 64_000],
|
|
443
|
+
["glm-5.3", "GLM 5.3", true, true, 1_000_000, 64_000],
|
|
444
|
+
["glm-5.3-flash", "GLM 5.3 Flash", true, true, 1_000_000, 131_072],
|
|
445
|
+
["glm-5v-turbo", "GLM 5v Turbo", true, true, 200_000, 64_000],
|
|
446
|
+
["minimax-m3", "MiniMax M3", true, true, 512_000, 64_000],
|
|
447
|
+
// 1M context, reasoning always on (upstream states both); vision inherited
|
|
448
|
+
// from the M3 row, which is the same family.
|
|
449
|
+
["minimax-m3.1-flash", "MiniMax M3.1 Flash", true, true, 1_000_000, 128_000],
|
|
450
|
+
["mimo-v2.6-pro", "MiMo V2.6 Pro", true, true, 1_000_000, 128_000],
|
|
451
|
+
["kimi-k2.8-preview", "Kimi K2.8 Preview", true, true, 1_000_000, 64_000],
|
|
452
|
+
["kimi-k3.1-pro", "Kimi K3.1 Pro", true, true, 1_000_000, 32_000],
|
|
453
|
+
["hy3", "Hy3", true, true, 192_000, 64_000],
|
|
454
|
+
["hy4", "Hy4", true, true, 960_000, 64_000],
|
|
455
|
+
["hy4free", "Hy4 Free", true, true, 960_000, 64_000],
|
|
456
|
+
["space-bunny", "Space Bunny", true, true, 1_000_000, 128_000],
|
|
457
|
+
["step-5-preview", "Step 5 Preview", true, true, 1_000_000, 64_000],
|
|
458
|
+
["deepseek-v4-pro", "DeepSeek V4 Pro", true, true, 1_000_000, 128_000],
|
|
459
|
+
["deepseek-v4.1-flash", "DeepSeek V4.1 Flash", true, true, 1_000_000, 128_000],
|
|
460
|
+
// Live on the CN roster but absent here, so a request for it resolved to
|
|
461
|
+
// nothing. Limits as published by /v3/config.
|
|
462
|
+
["kimi-k3-1", "Kimi K3-1", true, true, 1_000_000, 32_000],
|
|
463
|
+
["minimax-m2.7", "MiniMax M2.7", true, true, 200_000, 48_000],
|
|
464
|
+
];
|
|
@@ -23,14 +23,14 @@ import type { CanonicalRequest } from "../../../protocol/canonical-model";
|
|
|
23
23
|
import { isRecord } from "../../../protocol/codecs";
|
|
24
24
|
import { GatewayError } from "../../../protocol/gateway-error";
|
|
25
25
|
import { applyDeepSeekReasoning, applyOpenAIReasoning, backfillDeepSeekReasoningContent, clampedEffortOutputFloor, ensureChatReasoningReplayPresence } from "../../../protocol/reasoning";
|
|
26
|
-
import { BUDDY_CN_EFFORTS, BUDDY_INTL_EFFORTS, BUDDY_SHARED_RAW } from "./
|
|
26
|
+
import { BUDDY_CN_EFFORTS, BUDDY_INTL_EFFORTS, BUDDY_SHARED_RAW } from "./catalog";
|
|
27
27
|
// Imported for the CN roster only: a CN-only id has no row in the shared
|
|
28
28
|
// table, and without one `raiseOutputForRaisedEffort` silently no-ops, so a
|
|
29
29
|
// raised effort still answers inside a budget sized for the lower one. It is
|
|
30
30
|
// read inside the function below — never at module init — so the cycle with
|
|
31
31
|
// cn-provider (which imports this module) resolves before any call.
|
|
32
|
-
import { CODEBUDDY_CN_RAW } from "./
|
|
33
|
-
import { buddyAccountUid } from "./
|
|
32
|
+
import { CODEBUDDY_CN_RAW } from "./catalog";
|
|
33
|
+
import { buddyAccountUid } from "./account";
|
|
34
34
|
import { SYSTEM_PROMPT_WRAPPER_PREFIX, SYSTEM_PROMPT_WRAPPER_SUFFIX } from "../../../console/system-prompt/contracts";
|
|
35
35
|
import type { ProviderDispatchContext } from "../../provider-contracts";
|
|
36
36
|
|
|
@@ -226,7 +226,7 @@ export function normalizeBuddyToolNames(payload: Record<string, unknown>): void
|
|
|
226
226
|
name,
|
|
227
227
|
...(fn["parameters"] === undefined ? {} : { parameters: completeRequiredSchema(fn["parameters"]) }),
|
|
228
228
|
};
|
|
229
|
-
return normalizeRe2Declaration(fnOut);
|
|
229
|
+
return { ...rawTool, function: normalizeRe2Declaration(fnOut) };
|
|
230
230
|
}
|
|
231
231
|
if (custom !== undefined) {
|
|
232
232
|
const customOut = {
|
|
@@ -241,7 +241,7 @@ export function normalizeBuddyToolNames(payload: Record<string, unknown>): void
|
|
|
241
241
|
name,
|
|
242
242
|
...(rawTool["parameters"] === undefined ? {} : { parameters: completeRequiredSchema(rawTool["parameters"]) }),
|
|
243
243
|
};
|
|
244
|
-
return normalizeRe2Declaration(bareOut);
|
|
244
|
+
return { ...bareOut, ...normalizeRe2Declaration(bareOut) };
|
|
245
245
|
});
|
|
246
246
|
const messages = payload["messages"];
|
|
247
247
|
if (Array.isArray(messages)) {
|