305 lines · 9.0 KB · TypeScript
RawDownload
import { ProviderDriverKind, ProviderInstanceId, type ServerProvider } from "@t3tools/contracts";import { DEFAULT_UNIFIED_SETTINGS, type UnifiedSettings } from "@t3tools/contracts/settings";import { describe, expect, it } from "vite-plus/test";import { deriveProviderInstanceEntries } from "./providerInstances";import {  getAppModelOptionsForInstance,  resolveAppModelSelectionForInstance,  resolveAppModelSelectionState,} from "./modelSelection"; function provider(input: {  provider?: ProviderDriverKind;  instanceId: string;  models?: ReadonlyArray<string>;}): ServerProvider {  const driver =    input.provider ??    (input.instanceId.startsWith("claude_")      ? ProviderDriverKind.make("claudeAgent")      : ProviderDriverKind.make("codex"));  return {    instanceId: ProviderInstanceId.make(input.instanceId),    driver,    enabled: true,    installed: true,    version: null,    status: "ready",    auth: { status: "authenticated" },    checkedAt: "2026-01-01T00:00:00.000Z",    models: (input.models ?? []).map((slug) => ({      slug,      name: slug,      isCustom: false,      capabilities: {},    })),    slashCommands: [],    skills: [],  };} function settingsWithProviderInstances(): UnifiedSettings {  return {    ...DEFAULT_UNIFIED_SETTINGS,    providerInstances: {      [ProviderInstanceId.make("claudeAgent")]: {        driver: ProviderDriverKind.make("claudeAgent"),        config: { customModels: [] },      },      [ProviderInstanceId.make("claude_openrouter")]: {        driver: ProviderDriverKind.make("claudeAgent"),        config: { customModels: ["openai/gpt-5.5"] },      },    },  };} describe("instance-scoped model selection", () => {  it("keeps custom models on the provider instance that declared them", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-sonnet-4-6"],      }),      provider({        instanceId: "claude_openrouter",        models: ["claude-sonnet-4-6"],      }),    ];    const entries = deriveProviderInstanceEntries(providers);    const stock = entries.find((entry) => entry.instanceId === "claudeAgent")!;    const openrouter = entries.find((entry) => entry.instanceId === "claude_openrouter")!;     expect(      getAppModelOptionsForInstance(settingsWithProviderInstances(), stock).map(        (option) => option.slug,      ),    ).not.toContain("openai/gpt-5.5");    expect(      getAppModelOptionsForInstance(settingsWithProviderInstances(), openrouter).map(        (option) => option.slug,      ),    ).toContain("openai/gpt-5.5");  });   it("resolves a custom slug against the selected custom instance", () => {    const providers = [      provider({ provider: ProviderDriverKind.make("claudeAgent"), instanceId: "claudeAgent" }),      provider({        provider: ProviderDriverKind.make("claudeAgent"),        instanceId: "claude_openrouter",      }),    ];     expect(      resolveAppModelSelectionForInstance(        ProviderInstanceId.make("claude_openrouter"),        settingsWithProviderInstances(),        providers,        "openai/gpt-5.5",      ),    ).toBe("openai/gpt-5.5");  });   it("preserves a custom slug that collides with a provider alias", () => {    const providers = [      provider({        provider: ProviderDriverKind.make("claudeAgent"),        instanceId: "claude_openrouter",        models: ["claude-opus-4-8"],      }),    ];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      providerInstances: {        ...settingsWithProviderInstances().providerInstances,        [ProviderInstanceId.make("claude_openrouter")]: {          driver: ProviderDriverKind.make("claudeAgent"),          config: { customModels: ["opus"] },        },      },    };    const openrouter = deriveProviderInstanceEntries(providers)[0]!;     expect(      getAppModelOptionsForInstance(settings, openrouter).map((option) => option.slug),    ).toEqual(["claude-opus-4-8", "opus"]);    expect(      resolveAppModelSelectionForInstance(        ProviderInstanceId.make("claude_openrouter"),        settings,        providers,        "opus",      ),    ).toBe("opus");  });   it("includes Grok custom models from the selected provider instance", () => {    const providers = [provider({ provider: ProviderDriverKind.make("grok"), instanceId: "grok" })];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      providerInstances: {        ...settingsWithProviderInstances().providerInstances,        [ProviderInstanceId.make("grok")]: {          driver: ProviderDriverKind.make("grok"),          config: { customModels: ["grok-test-custom-model"] },        },      },    };    const grok = deriveProviderInstanceEntries(providers).find(      (entry) => entry.instanceId === "grok",    )!;     expect(getAppModelOptionsForInstance(settings, grok).map((option) => option.slug)).toContain(      "grok-test-custom-model",    );  });   it("does not inject an unknown selected slug into the stock instance list", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-sonnet-4-6"],      }),      provider({        instanceId: "claude_openrouter",        models: ["claude-sonnet-4-6"],      }),    ];    const stock = deriveProviderInstanceEntries(providers).find(      (entry) => entry.instanceId === "claudeAgent",    )!;     expect(      getAppModelOptionsForInstance(settingsWithProviderInstances(), stock).map(        (option) => option.slug,      ),    ).not.toContain("openai/gpt-5.5");  });   it("hides server models from the instance option list", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-opus-4-6", "claude-sonnet-4-6"],      }),    ];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      providerModelPreferences: {        [ProviderInstanceId.make("claudeAgent")]: {          hiddenModels: ["claude-opus-4-6"],          modelOrder: [],        },      },    };    const stock = deriveProviderInstanceEntries(providers).find(      (entry) => entry.instanceId === "claudeAgent",    )!;     expect(getAppModelOptionsForInstance(settings, stock).map((option) => option.slug)).toEqual([      "claude-sonnet-4-6",    ]);  });   it("applies persisted per-instance model ordering", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-opus-4-6", "claude-sonnet-4-6", "claude-haiku-4-5"],      }),    ];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      providerModelPreferences: {        [ProviderInstanceId.make("claudeAgent")]: {          hiddenModels: [],          modelOrder: ["claude-haiku-4-5", "claude-opus-4-6"],        },      },    };    const stock = deriveProviderInstanceEntries(providers).find(      (entry) => entry.instanceId === "claudeAgent",    )!;     expect(getAppModelOptionsForInstance(settings, stock).map((option) => option.slug)).toEqual([      "claude-haiku-4-5",      "claude-opus-4-6",      "claude-sonnet-4-6",    ]);  });   it("falls back when the selected model is hidden", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-opus-4-6", "claude-sonnet-4-6"],      }),    ];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      providerModelPreferences: {        [ProviderInstanceId.make("claudeAgent")]: {          hiddenModels: ["claude-opus-4-6"],          modelOrder: [],        },      },    };     expect(      resolveAppModelSelectionForInstance(        ProviderInstanceId.make("claudeAgent"),        settings,        providers,        "claude-opus-4-6",      ),    ).toBe("claude-sonnet-4-6");  });   it("falls back instead of resolving a custom slug against the wrong instance", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-sonnet-4-6"],      }),      provider({        instanceId: "claude_openrouter",        models: ["claude-sonnet-4-6"],      }),    ];     expect(      resolveAppModelSelectionForInstance(        ProviderInstanceId.make("claudeAgent"),        settingsWithProviderInstances(),        providers,        "openai/gpt-5.5",      ),    ).toBe("claude-sonnet-4-6");  });   it("preserves custom provider instances in settings model selection", () => {    const providers = [      provider({        instanceId: "claudeAgent",        models: ["claude-sonnet-4-6"],      }),      provider({        instanceId: "claude_openrouter",        models: ["claude-sonnet-4-6"],      }),    ];    const settings: UnifiedSettings = {      ...settingsWithProviderInstances(),      textGenerationModelSelection: {        instanceId: ProviderInstanceId.make("claude_openrouter"),        model: "openai/gpt-5.5",      },    };     expect(resolveAppModelSelectionState(settings, providers)).toEqual({      instanceId: ProviderInstanceId.make("claude_openrouter"),      model: "openai/gpt-5.5",    });  });});