Repository navigation
feat(providers): add Ollama System One handler and decision-model discovery - #15410
Draft
yourspraveen wants to merge 4 commits into
Draft
yourspraveen wants to merge 4 commits into
yourspraveen wants to merge 4 commits into
Conversation
…covery Ollama 0.35 ships a local System One API (POST /v1/systemone) that answers typed choice / noul / score questions with calibrated probabilities, using the same request/response format as TypeSafe Jev. This adds the Ollama-specific pieces so `ollama-local/<model>` can serve that API once the shared /v1/systemone route lands (coordination on diegosouzapw#13987). - Map Ollama's `decision` capability (Nimble, Tev models) to a new `systemone` supported-endpoint value, same spelling as diegosouzapw#14498. - A decision-only model no longer falls through to the images apiFormat. - open-sse/handlers/ollamaSystemOne.ts: validation mirroring Ollama's own limits (400 / 413 for >64 KiB), forwards only known fields with the provider prefix stripped, 60s default timeout for cold model loads, echoes the caller's model id, logs usage at $0 cost. - Failure mapping: 404 missing model -> model lockout; 400 "not supported by System One" -> returned as-is; 5xx / unreachable / timeout -> connection cooldown; client abort -> nothing marked. Errors go through errorResponse() sanitization. Validated live against Ollama 0.35.0 with nimble and tev1:4b: tev1:4b 200 (1.5s), nimble 200 (2.2s), unpulled model 404 + lockout, gemma3:4b 400 with the connection untouched. Refs diegosouzapw#13987
…Flash Ollama 0.35.1 adds Clef (27B) and Clef Flash (9B), System One models tagged `vision` + `decision`. The System One API takes base64 `images` shared by all questions (URLs and data URLs are not supported) and accepts bodies up to 32 MiB when images are present, versus 64 KiB without. The handler dropped `images` as an unknown field and capped every body at 64 KiB, so a Clef request could not use its vision weights and any real image was refused with 413. `images` is now validated (non-empty raw base64, URLs/data URLs rejected with 400) and forwarded, and the 32 MiB limit applies when images are present. Decision-model discovery already maps Clef's `vision` + `decision` to the systemone endpoint with supportsVision; a test now pins that. Refs diegosouzapw#13987
… path Ollama reports Clef / Clef Flash as `["vision", "decision"]` with no `completion`, and discovery stores that as supportedEndpoints ["systemone"]. Such a row reached /v1/models with no `type`, so agents and the OpenCode plugins listed it as a chat model, and a chat call went upstream only to come back as a 400. - modelEndpointPolicy: a `decision` kind for systemone-only rows (chatSelectable false); a model that also serves chat stays chat. - classifyModelSupportedEndpoints: systemone-only rows are tagged `type: "decision"` in /v1/models, alongside embedding/rerank/image. - decisionOnlyChatRejection, called from getModelInfoOrRetirementResponse (the resolver behind resolveModelOrError, used by direct chat calls and every combo target): refuses a decision-only model with a clear 400 before any credential is picked, so nothing is marked on the connection. The message reads as a model-scoped 400, so a combo advances to its next target. Only System One-capable providers (ollama-local) pay the lookup. Refs diegosouzapw#13987
…mplexity gates handleOllamaSystemOne (complexity 33, cognitive 19) is split into buildUpstreamBody / buildUpstreamHeaders / resolveUpstreamUrl / classifyFetchFailure / parseJsonText / readAnswersPayload / clearRecoveredConnection / buildSuccessResponse, and the decision-only test in classifyModelSupportedEndpoints moves to isDecisionOnly, so no touched function exceeds the complexity ratchets. Behaviour unchanged (28 tests). tests/unit/ollama-systemone.test.ts covers open-sse/services/accountFallback.ts, a mutated module, so it joins stryker.conf.json tap.testFiles.
yourspraveen
force-pushed
the
feat/ollama-systemone
branch
from
October 3, 2026 14:06
ea59d6c to
fcb67f7
Compare
1 of 6 tasks
This branch has not been deployed
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What
Ollama ships a local System One API (
POST /v1/systemone, docs). It uses the same request/response format as TypeSafe Jev (choice/noul/scorequestions with calibrated probabilities). This PR adds the Ollama-specific pieces soollama-local/<model>can serve it alongside the TypeSafe / OpenRouter backends proposed upstream. Models covered:vision+decision(Ollama ≥ 0.35.1)1. Discovery
decisioncapability maps to asystemonesupported endpoint, spelled the same as feat(typesafe): add Jev System One API support #14498.imagesapiFormat.2. Handler (
open-sse/handlers/ollamaSystemOne.ts)imagesare present.imagessupport for Clef / Clef Flash: base64 only. URLs and data URLs are rejected with a 400, as Ollama does.errorResponse()sanitization3. Decision-only guard: keeping System One models out of the chat path
Ollama reports Clef as
["vision","decision"]with nocompletion. Before this guard, such a row looked like a chat model:/v1/modelsgave it notype, and a chat call went upstream only to come back as a 400.modelEndpointPolicy: adecisionkind for systemone-only rows (chatSelectable: false). Nimble and Tev also advertise chat, so they stay chat./v1/modelstags systemone-only rowstype: "decision", alongsideembedding/rerank/image.decisionOnlyChatRejectionruns ingetModelInfoOrRetirementResponse, the resolver behindresolveModelOrError, which handles both direct chat calls and every combo target. It refuses such a model with a clear 400 before any credential is picked, so nothing is marked on the connection. The message reads as a model-scoped 400, so a combo advances to its next target (comboTargetDecision→advance). Only System One-capable providers (ollama-local) pay the stored-model lookup.Related
jevcombo strategy that uses one System Onechoicecall to order chat targets. That is the routing use described in feat(providers): add TypeSafe AI (Jev) as a provider + optional auto-routing classifier #13987 Part 2. Once the route lands, routing that judge call through/v1/systemonewith a decision combo would let it use local Ollama models (Clef Flash / Nimble) with cloud fallback, not only TypeSafe. I proposed this on feat(providers): add TypeSafe AI (Jev) as a provider + optional auto-routing classifier #13987.type: "decision"is a natural thing for those presets to filter out of the chat picker.Testing
tests/unit/ollama-systemone.test.ts(23):vision+decisiontests/unit/ollama-systemone-decision-guard.test.ts(5):/v1/modelstyperesolveModelOrErrorrefusing the modeltev1:4b→ 200 (1.5s)nimble→ 200 (2.2s)gemma3:4b→ 400, connection left untouchedLocal quality gates
I ran the
quality.ymlfast-gate set locally againstrelease/v3.8.52. The branch is rebased onto the current tip (23a1148486).--max-warnings 0on the changed files. The first run caught two problems:handleOllamaSystemOnewas at complexity 33. It's now split into small helpers with no behaviour change.stryker.conf.json. It's added now.workflows, which needsactionlintandzizmor. This PR doesn't touch workflows.Remaining before ready
/v1/systemonebase PR and connect the handler to the routedocs/openapi.yaml,API_REFERENCE.md,LOCAL_OLLAMA_DOCKER.mdchangelog.d/features/15410-ollama-systemone.mdRefs #13987