From 0a1f1d42ee312b72f8ae7dbbde70e6ea5b64da62 Mon Sep 17 00:00:00 2001 From: Markus Hartung Date: Thu, 20 Aug 2026 20:27:26 -0300 Subject: [PATCH] fix(open-sse): declare Ollama Cloud reasoning models' supportedThinkingEfforts (#10788) glm-5.1, glm-5.2, deepseek-v4-pro and deepseek-v4-flash declared supportsReasoning:true but no supportedThinkingEfforts, so the catalog's appendSyncedEffortVariants() pass (which only synthesizes -low/-high/-max ids from an already-populated capabilities.effort_tiers) never exposed a selectable effort tier for them, unlike gpt-oss:20b/120b. Add the documented low/medium/high/max vocabulary (see supportsMaxEffortForProvider's isOllamaCloud comment in reasoningEffort.ts). --- .../fixes/10788-ollama-cloud-effort-tiers.md | 1 + .../providers/registry/ollama-cloud/index.ts | 22 +++++++++- ...cloud-reasoning-effort-tiers-10788.test.ts | 40 +++++++++++++++++++ 3 files changed, 61 insertions(+), 2 deletions(-) create mode 100644 changelog.d/fixes/10788-ollama-cloud-effort-tiers.md create mode 100644 tests/unit/ollama-cloud-reasoning-effort-tiers-10788.test.ts diff --git a/changelog.d/fixes/10788-ollama-cloud-effort-tiers.md b/changelog.d/fixes/10788-ollama-cloud-effort-tiers.md new file mode 100644 index 0000000000..0437576d38 --- /dev/null +++ b/changelog.d/fixes/10788-ollama-cloud-effort-tiers.md @@ -0,0 +1 @@ +- **fix(open-sse):** declare `supportedThinkingEfforts` (`low`/`medium`/`high`/`max`) on Ollama Cloud's `glm-5.1`, `glm-5.2`, `deepseek-v4-pro` and `deepseek-v4-flash` registry entries so the catalog's `appendSyncedEffortVariants()` pass — which only synthesizes selectable `-low`/`-high`/`-max` model ids from an already-populated `capabilities.effort_tiers` — can expose an effort selector for these reasoning-capable models, matching what `gpt-oss:20b`/`gpt-oss:120b` already had (#10788) diff --git a/open-sse/config/providers/registry/ollama-cloud/index.ts b/open-sse/config/providers/registry/ollama-cloud/index.ts index 05b28df65f..4cf020263a 100644 --- a/open-sse/config/providers/registry/ollama-cloud/index.ts +++ b/open-sse/config/providers/registry/ollama-cloud/index.ts @@ -24,8 +24,24 @@ export const ollama_cloudProvider: RegistryEntry = { supportsReasoning: true, supportedThinkingEfforts: ["low", "medium", "high"], }, - { id: "deepseek-v4-pro", name: "DeepSeek V4 Pro", supportsReasoning: true }, - { id: "deepseek-v4-flash", name: "DeepSeek V4 Flash", supportsReasoning: true }, + // #10788: Ollama Cloud accepts low|medium|high|max|none uniformly across + // its reasoning-capable models (see supportsMaxEffortForProvider's + // isOllamaCloud comment in open-sse/executors/base/reasoningEffort.ts) — + // declare supportedThinkingEfforts so appendSyncedEffortVariants() (which + // runs before static-model capability enrichment) can synthesize the + // catalog's selectable -low/-high/-max variant ids for these models. + { + id: "deepseek-v4-pro", + name: "DeepSeek V4 Pro", + supportsReasoning: true, + supportedThinkingEfforts: ["low", "medium", "high", "max"], + }, + { + id: "deepseek-v4-flash", + name: "DeepSeek V4 Flash", + supportsReasoning: true, + supportedThinkingEfforts: ["low", "medium", "high", "max"], + }, { id: "kimi-k2.6", name: "Kimi K2.6" }, // Ollama Cloud accepts low|medium|high|max|none and rejects xhigh, so the // explicit supportsXHighEffort:false makes the sanitizer map xhigh → max. @@ -34,12 +50,14 @@ export const ollama_cloudProvider: RegistryEntry = { name: "GLM 5.1", supportsReasoning: true, supportsXHighEffort: false, + supportedThinkingEfforts: ["low", "medium", "high", "max"], }, { id: "glm-5.2", name: "GLM 5.2", supportsReasoning: true, supportsXHighEffort: false, + supportedThinkingEfforts: ["low", "medium", "high", "max"], }, // #3110: MiniMax M3 via Ollama { id: "minimax-m3", name: "MiniMax M3", contextLength: 1048576, supportsVision: true }, diff --git a/tests/unit/ollama-cloud-reasoning-effort-tiers-10788.test.ts b/tests/unit/ollama-cloud-reasoning-effort-tiers-10788.test.ts new file mode 100644 index 0000000000..ae7506cbf1 --- /dev/null +++ b/tests/unit/ollama-cloud-reasoning-effort-tiers-10788.test.ts @@ -0,0 +1,40 @@ +import { test } from "node:test"; +import assert from "node:assert/strict"; +import { ollama_cloudProvider } from "../../open-sse/config/providers/registry/ollama-cloud/index.ts"; + +// #10788: ollama-cloud declared supportsReasoning:true on several models +// (glm-5.1/5.2, deepseek-v4-pro/flash) but never declared +// supportedThinkingEfforts. appendSyncedEffortVariants() (open-sse/utils/ +// syncedEffortVariants.ts) only synthesizes catalog `-` ids from +// an already-populated capabilities.effort_tiers, and for static registry +// models that population only happens from a non-empty +// supportedThinkingEfforts — so these models never got a selectable +// -low/-high/-max catalog id. gpt-oss:20b/120b already declared it as the +// control case. +test("#10788: ollama-cloud reasoning-capable models declare supportedThinkingEfforts", () => { + const byId = new Map(ollama_cloudProvider.models.map((m) => [m.id, m])); + + const control = byId.get("gpt-oss:20b"); + assert.ok( + Array.isArray(control?.supportedThinkingEfforts) && control.supportedThinkingEfforts.length > 0, + "control: gpt-oss:20b should already declare supportedThinkingEfforts" + ); + + const reasoningModelIds = ["glm-5.1", "glm-5.2", "deepseek-v4-pro", "deepseek-v4-flash"]; + for (const id of reasoningModelIds) { + const model = byId.get(id); + assert.ok(model?.supportsReasoning, `${id} should be flagged as a reasoning model`); + assert.ok( + Array.isArray(model?.supportedThinkingEfforts) && model.supportedThinkingEfforts.length > 0, + `${id} supports reasoning but declares no supportedThinkingEfforts` + ); + // Ollama Cloud's documented vocabulary (see supportsMaxEffortForProvider's + // isOllamaCloud comment in open-sse/executors/base/reasoningEffort.ts): + // low|medium|high|max|none — xhigh is rejected and mapped to max. + assert.deepEqual( + [...(model?.supportedThinkingEfforts ?? [])], + ["low", "medium", "high", "max"], + `${id} should declare Ollama Cloud's documented low/medium/high/max vocabulary` + ); + } +});