From ca4287409863c0b44a9cf9700d083d9f2ba9d452 Mon Sep 17 00:00:00 2001 From: diegosouzapw Date: Tue, 19 May 2026 04:04:26 -0300 Subject: [PATCH] fix(providers): skip CLI runtime check for kilocode OAuth-based provider (#2404) The kilocode provider uses OAuth device flow + direct HTTPS to api.kilo.ai and never depends on the local kilocode CLI binary at runtime. The connection test was hard-failing with "Local CLI runtime is not installed" even when the OAuth token itself was perfectly valid, blocking all kilocode setups on hosts where the CLI binary was not also installed. Removed kilocode from CLI_RUNTIME_PROVIDER_MAP and extracted the constant to a dedicated module so unit tests can pin the contract without dragging the full Next.js route + DB initialization into the test runtime. CLI Tools integration (/api/cli-tools/kilo-settings, used to configure the Kilo VSCode extension to point at OmniRoute) keeps its own runtime check since it actually does need the CLI binary to be present. --- .../[id]/test/cliRuntimeProviderMap.ts | 11 +++++++++ src/app/api/providers/[id]/test/route.ts | 6 +---- .../unit/providers-test-route-cli-map.test.ts | 24 +++++++++++++++++++ 3 files changed, 36 insertions(+), 5 deletions(-) create mode 100644 src/app/api/providers/[id]/test/cliRuntimeProviderMap.ts create mode 100644 tests/unit/providers-test-route-cli-map.test.ts diff --git a/src/app/api/providers/[id]/test/cliRuntimeProviderMap.ts b/src/app/api/providers/[id]/test/cliRuntimeProviderMap.ts new file mode 100644 index 0000000000..dc3f547f68 --- /dev/null +++ b/src/app/api/providers/[id]/test/cliRuntimeProviderMap.ts @@ -0,0 +1,11 @@ +// Maps a provider id to the CLI tool id whose local runtime must be present +// for the connection-test path to authenticate against a local CLI auth file. +// kilocode is intentionally absent: the provider uses OAuth device flow + direct +// HTTPS to api.kilo.ai and never depends on the kilocode CLI binary at runtime +// (#2404). CLI-tools integration for Kilo (configuring the VSCode extension to +// point at OmniRoute) lives in /api/cli-tools/kilo-settings and keeps its own +// runtime check there. +export const CLI_RUNTIME_PROVIDER_MAP: Record = { + cline: "cline", + qoder: "qoder", +}; diff --git a/src/app/api/providers/[id]/test/route.ts b/src/app/api/providers/[id]/test/route.ts index 2bbf28b039..b82cd00532 100644 --- a/src/app/api/providers/[id]/test/route.ts +++ b/src/app/api/providers/[id]/test/route.ts @@ -102,11 +102,7 @@ const OAUTH_TEST_CONFIG = { }, }; -const CLI_RUNTIME_PROVIDER_MAP = { - cline: "cline", - kilocode: "kilo", - qoder: "qoder", -}; +import { CLI_RUNTIME_PROVIDER_MAP } from "./cliRuntimeProviderMap"; /** POST body is optional; when present, only known fields are validated. */ const providerConnectionTestBodySchema = z.object({ diff --git a/tests/unit/providers-test-route-cli-map.test.ts b/tests/unit/providers-test-route-cli-map.test.ts new file mode 100644 index 0000000000..b433967f55 --- /dev/null +++ b/tests/unit/providers-test-route-cli-map.test.ts @@ -0,0 +1,24 @@ +import test from "node:test"; +import assert from "node:assert/strict"; + +import { CLI_RUNTIME_PROVIDER_MAP } from "../../src/app/api/providers/[id]/test/cliRuntimeProviderMap"; + +// #2404 — Before this fix, the kilocode provider (OAuth device flow + direct HTTPS +// to api.kilo.ai) was gated on the local `kilocode` CLI binary being installed, +// which made the connection test hard-fail with "Local CLI runtime is not installed" +// even when the OAuth token itself was perfectly valid. The CLI binary is only +// relevant for the dashboard's CLI-tools integration, not for the provider itself. +test("CLI_RUNTIME_PROVIDER_MAP must not gate kilocode on a local CLI binary (#2404)", () => { + assert.equal( + CLI_RUNTIME_PROVIDER_MAP.kilocode, + undefined, + "kilocode is an OAuth+HTTPS provider; it must not require the local CLI binary at test time" + ); +}); + +test("CLI_RUNTIME_PROVIDER_MAP still gates providers that actually need a local CLI", () => { + // cline and qoder both read credentials from a local CLI auth file when used + // in their CLI-flavored auth mode, so the runtime check stays meaningful. + assert.equal(CLI_RUNTIME_PROVIDER_MAP.cline, "cline"); + assert.equal(CLI_RUNTIME_PROVIDER_MAP.qoder, "qoder"); +});