project-nomad/admin/tests
Jake Turner 5c97bf605a fix(AI): stop <think> output leaking into titles, chips, and the RAG query (#1254)
ThinkTagSplitter was wired into both streaming paths but neither
non-streaming one, and every ancillary call goes through non-streaming
chat(). So a reasoning tasks model put its reasoning transcript into the
sidebar title, into the suggestion chips, and — worst — into the string
that gets embedded and sent to Qdrant, silently corrupting retrieval for
the rest of the conversation. splitThinkTags() already existed and was
already unit tested; it just had no production callers.

Fixed in three layers:

1. Strip at the transport. New normalizeNonStreamed() in think_stream.ts
   merges structured reasoning (native `thinking`, /v1 `reasoning`) with
   anything the splitter pulls out of inline tags, and both _chatNative
   and _chatCompat now return through it. That covers every caller at
   once, including the legacy controller path and the eval harness.

2. Suppress at the source. _chatNative and _chatStreamNative forwarded
   `think` only when truthy, so `think: false` was never sent and Ollama
   left reasoning on for capable models. Guard is now definedness. This
   also fixes the ai.autoThinking=off setting, which had no effect on
   the native streaming transport.

3. Guard the call sites. Title, suggestions, and query rewrite now pass
   think:false plus thinkingCapable (from the memoized capability check,
   so no extra round-trip), and handle an empty-after-strip result. The
   rewrite matters most: QUERY_REWRITE_MAX_TOKENS caps it at 120, which
   a reasoning model burns entirely on thinking, so stripping alone
   would have turned a corrupt query into an empty one. It now falls
   back to the raw user message instead of embedding "".

Verified: think_stream.spec.ts 17/17 (6 new cases, including the
truncated-mid-thought case that drives the fallback), typecheck clean,
full test:unit failures byte-identical to the pre-change baseline.
2026-09-29 15:54:41 -07:00
..
eval feat(AI): budget the prompt and actually set the context window (#1253) 2026-09-29 15:54:41 -07:00
functional feat: auto-generating OpenAPI docs with Scalar UI (#1128) 2026-08-04 03:38:33 +00:00
standalone refactor(drug-reference): make collections JSON the single source for curated data (#1130) 2026-08-04 03:38:35 +00:00
unit fix(AI): stop <think> output leaking into titles, chips, and the RAG query (#1254) 2026-09-29 15:54:41 -07:00
bootstrap.ts feat: initial commit 2025-06-29 15:51:08 -07:00