feat(agent): let users choose model route

This commit is contained in:
ginnoir
2026-07-08 19:50:46 -05:00
parent b279f16ba0
commit ec3f96dab1
13 changed files with 235 additions and 45 deletions
+9 -1
View File
@@ -26,7 +26,15 @@ test("assistant chat smoke after opt-in", async ({ page }) => {
await page.goto("/");
await page.getByRole("button", { name: "Open assistant" }).click();
await expect(page.getByRole("dialog", { name: "Assistant" })).toBeVisible();
const modelSelector = page.getByRole("combobox", { name: "Assistant model" });
const routeSelector = page.getByRole("combobox", { name: "Assistant model route" });
await expect(routeSelector).toBeVisible();
await routeSelector.selectOption("auto");
await expect(routeSelector).toHaveValue("auto");
await expect(routeSelector).toBeEnabled();
await routeSelector.selectOption("uncensored");
await expect(routeSelector).toHaveValue("uncensored");
await expect(routeSelector).toBeEnabled();
const modelSelector = page.getByRole("combobox", { name: "Assistant model", exact: true });
await expect(modelSelector).toBeVisible();
const refreshModels = page.getByRole("button", { name: "Refresh assistant models" });
await expect(refreshModels).toBeVisible();
+40 -2
View File
@@ -1,6 +1,7 @@
import assert from "node:assert/strict";
import { describe, it } from "node:test";
import {
isValidAssistantModelRoute,
isValidLlmModelId,
listLlmModels,
normalizeLlmModelsPayload,
@@ -56,6 +57,18 @@ describe("isValidLlmModelId", () => {
});
});
describe("isValidAssistantModelRoute", () => {
it("accepts the supported route families", () => {
assert.equal(isValidAssistantModelRoute("auto"), true);
assert.equal(isValidAssistantModelRoute("uncensored"), true);
});
it("rejects unsupported or padded route families", () => {
assert.equal(isValidAssistantModelRoute("bogus"), false);
assert.equal(isValidAssistantModelRoute(" uncensored "), false);
});
});
describe("listLlmModels", () => {
it("fetches provider models with API key auth when the fallback is advertised", async () => {
const requests: Request[] = [];
@@ -88,10 +101,11 @@ describe("listLlmModels", () => {
assert.equal(result.degraded, true);
});
it("fetches the typed uncensored catalog when uncensored is the fallback route", async () => {
it("fetches the typed uncensored catalog when uncensored is the selected route", async () => {
const requests: Request[] = [];
const result = await listLlmModels({
config: { ...openAiConfig, model: "uncensored" },
config: { ...openAiConfig, model: "auto" },
route: "uncensored",
fetchImpl: async (input, init) => {
requests.push(new Request(input, init));
return Response.json({
@@ -111,6 +125,30 @@ describe("listLlmModels", () => {
{ id: "uncensored", label: "uncensored" },
]);
assert.equal(result.fallbackModel, "uncensored");
assert.equal(result.route, "uncensored");
assert.equal(result.degraded, false);
});
it("fetches the default catalog when auto is selected over an uncensored deployment default", async () => {
const requests: Request[] = [];
const result = await listLlmModels({
config: { ...openAiConfig, model: "uncensored" },
route: "auto",
fetchImpl: async (input, init) => {
requests.push(new Request(input, init));
return Response.json({
data: [{ id: "auto" }, { id: "qwen3:8b" }],
});
},
});
assert.equal(requests[0]?.url, "https://llm.example.test/v1/models");
assert.deepEqual(result.models, [
{ id: "auto", label: "auto" },
{ id: "qwen3:8b", label: "qwen3:8b" },
]);
assert.equal(result.fallbackModel, "auto");
assert.equal(result.route, "auto");
assert.equal(result.degraded, false);
});