mirror of
https://github.com/diegosouzapw/OmniRoute.git
synced 2026-09-13 18:32:12 +03:00
Landed with the design call resolved per the owner's pick — **option 1**: the synced store is now endpoint-agnostic (persistDiscoveredModels and managedModelImport no longer drop non-chat models at write time), and chat selectability moved to read time (auto-pool expansion in autoStrategy applies filterChatSelectableModels; the models-route projection already had its chatOnly filter). Your discovery test now passes end-to-end (3/3): /api/show capabilities persist per connection and image/embedding requests route through the advertising host. Reconciliation notes: conflicted areas merged onto the current tip (adobe discovery import, requestedModel preflight signature, resolvedProvider fast-path coexists with the synced-route override — explicit resolution wins); carried base-red drains (#10055 memoization, #11071 test variants) dropped as already-landed; the managed-model-import exclusion test was propagated to the new contract (image/video models persist; the read filter still hides them from chat pickers — pinned by a new assertion). Full battery: 205/206 focused (the one red is a confirmed periodic-timer timing flake on the loaded devbox — 20/20 isolated), autoCombo vitest 30/30, combo suites 46/46, gates + typecheck clean. Thank you @yourspraveen — the capability probe + routing design was right; it just needed the store contract opened up. Fixes #11087.
74 lines
3.4 KiB
TypeScript
74 lines
3.4 KiB
TypeScript
import test from "node:test";
|
|
import assert from "node:assert/strict";
|
|
|
|
const { qualifyPlaygroundModel } =
|
|
await import("../../src/app/(dashboard)/dashboard/media-providers/components/LlmChatCard.tsx");
|
|
|
|
// #3050 — vendor-namespaced model ids already contain a "/", so the old
|
|
// `.includes("/")` heuristic skipped the provider prefix and the request was
|
|
// rejected with "Ambiguous model 'moonshotai/kimi-k2.6'".
|
|
test("qualifyPlaygroundModel prefixes a vendor-namespaced model with providerId (#3050)", () => {
|
|
assert.equal(qualifyPlaygroundModel("moonshotai/kimi-k2.6", "nim"), "nim/moonshotai/kimi-k2.6");
|
|
assert.equal(
|
|
qualifyPlaygroundModel("nvidia/zyphra/zamba2-7b-instruct", "nim"),
|
|
"nim/nvidia/zyphra/zamba2-7b-instruct"
|
|
);
|
|
});
|
|
|
|
test("qualifyPlaygroundModel prefixes a bare model", () => {
|
|
assert.equal(qualifyPlaygroundModel("gpt-4o", "openai"), "openai/gpt-4o");
|
|
});
|
|
|
|
test("qualifyPlaygroundModel does not double-prefix an already-qualified model", () => {
|
|
assert.equal(
|
|
qualifyPlaygroundModel("nim/moonshotai/kimi-k2.6", "nim"),
|
|
"nim/moonshotai/kimi-k2.6"
|
|
);
|
|
assert.equal(qualifyPlaygroundModel("nim", "nim"), "nim");
|
|
});
|
|
|
|
test("qualifyPlaygroundModel returns the model unchanged without a providerId", () => {
|
|
assert.equal(qualifyPlaygroundModel("moonshotai/kimi-k2.6", ""), "moonshotai/kimi-k2.6");
|
|
assert.equal(qualifyPlaygroundModel("", "nim"), "");
|
|
});
|
|
|
|
test("OpenCode Free playground uses its routing alias instead of the reserved provider id", async () => {
|
|
const { getProviderAlias } = await import("../../src/shared/constants/providers.ts");
|
|
assert.equal(getProviderAlias("opencode"), "oc");
|
|
assert.equal(qualifyPlaygroundModel("big-pickle", getProviderAlias("opencode")), "oc/big-pickle");
|
|
});
|
|
|
|
test("qualifyPlaygroundModel inserts the provider after the no-think prefix, not before it", () => {
|
|
assert.equal(
|
|
qualifyPlaygroundModel("no-think/claude-sonnet-5", "vertex"),
|
|
"no-think/vertex/claude-sonnet-5"
|
|
);
|
|
});
|
|
|
|
test("qualifyPlaygroundModel does not double-qualify an already-qualified no-think id", () => {
|
|
assert.equal(
|
|
qualifyPlaygroundModel("no-think/vertex/claude-sonnet-5", "vertex"),
|
|
"no-think/vertex/claude-sonnet-5"
|
|
);
|
|
});
|
|
|
|
test("qualifyPlaygroundModel does not mistake a provider-name-prefix collision for already-qualified", () => {
|
|
// routingPrefix "vertex" must not match "vertex-eu/..." as already-qualified just because
|
|
// it starts with the same characters — the check requires an exact "vertex/" segment
|
|
// boundary. A naive `inner.startsWith(routingPrefix)` (no slash) would wrongly skip
|
|
// qualification here and leave the provider segment un-inserted.
|
|
assert.equal(
|
|
qualifyPlaygroundModel("no-think/vertex-eu/claude-sonnet-5", "vertex"),
|
|
"no-think/vertex/vertex-eu/claude-sonnet-5"
|
|
);
|
|
});
|
|
|
|
test("LlmChatCard's local NO_THINKING_PREFIX literal matches the canonical constant", async () => {
|
|
// Drift guard: LlmChatCard.tsx deliberately hardcodes "no-think/" as a literal instead
|
|
// of importing NO_THINKING_PREFIX from open-sse/utils/noThinkingAlias.ts (avoids pulling
|
|
// server-side catalog modules into the client bundle — see Step 1). This test file is not
|
|
// client-bundled, so it can safely import the real constant and assert they never drift.
|
|
const { NO_THINKING_PREFIX } = await import("../../open-sse/utils/noThinkingAlias.ts");
|
|
assert.equal(NO_THINKING_PREFIX, "no-think/");
|
|
});
|