fix: buffer split reasoning wrapper deltas
maintainer edit: native reasoning streams can split <thinking> wrapper tags across chunks. Buffer the stream and emit only cleaned incremental reasoning so raw partial tags do not reach WebUI.
This commit is contained in:
@@ -771,18 +771,24 @@ class AgentRunner:
|
||||
await live_file_edits.update(delta)
|
||||
|
||||
if wants_streaming:
|
||||
thinking_buf = ""
|
||||
|
||||
async def _stream(delta: str) -> None:
|
||||
if delta:
|
||||
context.streamed_content = True
|
||||
await hook.on_stream(context, delta)
|
||||
|
||||
async def _thinking(delta: str) -> None:
|
||||
nonlocal thinking_buf
|
||||
if not delta:
|
||||
return
|
||||
delta = strip_reasoning_tags(delta)
|
||||
if delta:
|
||||
prev_clean = strip_reasoning_tags(thinking_buf)
|
||||
thinking_buf += delta
|
||||
new_clean = strip_reasoning_tags(thinking_buf)
|
||||
incremental = new_clean[len(prev_clean):]
|
||||
if incremental:
|
||||
context.streamed_reasoning = True
|
||||
await hook.emit_reasoning(delta)
|
||||
await hook.emit_reasoning(incremental)
|
||||
|
||||
async def _stream_recover() -> None:
|
||||
await hook.on_stream_end(context, resuming=True)
|
||||
|
||||
@@ -134,10 +134,15 @@ def strip_reasoning_tags(text: object) -> str:
|
||||
"""Remove wrapper tags from text that is already known to be reasoning."""
|
||||
if not isinstance(text, str):
|
||||
return ""
|
||||
partial_reasoning_tag = (
|
||||
r"</?(?:t|th|thi|thin|think|thinki|thinkin|thinking|tho|thou|thoug|though|thought)>?"
|
||||
)
|
||||
text = re.sub(rf"^\s*(?:{partial_reasoning_tag})$", "", text)
|
||||
text = re.sub(r"^\s*<(?:think|thinking|thought)/>\s*", "", text)
|
||||
text = re.sub(r"\s*<(?:think|thinking|thought)/>\s*$", "", text)
|
||||
text = re.sub(r"^\s*<(?:think|thinking|thought)>\s*", "", text)
|
||||
text = re.sub(r"\s*</(?:think|thinking|thought)>\s*$", "", text)
|
||||
text = re.sub(rf"\s*(?:{partial_reasoning_tag})$", "", text)
|
||||
return text.strip()
|
||||
|
||||
|
||||
|
||||
@@ -381,8 +381,8 @@ async def test_runner_strips_thinking_tags_from_native_thinking_deltas():
|
||||
*, on_content_delta=None, on_thinking_delta=None, **kwargs
|
||||
):
|
||||
if on_thinking_delta:
|
||||
await on_thinking_delta("<thinking>")
|
||||
await on_thinking_delta("Preparing final response")
|
||||
await on_thinking_delta("<thinking")
|
||||
await on_thinking_delta(">Preparing final response")
|
||||
await on_thinking_delta("</thinking>")
|
||||
if on_content_delta:
|
||||
await on_content_delta("done")
|
||||
|
||||
Reference in New Issue
Block a user