[GH-ISSUE #21927] UX: 'Network connection lost' when built-in tool call has malformed/incomplete arguments — needs graceful error handling #90358

Closed
opened 2026-05-15 15:36:09 -05:00 by GiteaMirror · 0 comments
Owner

Originally created by @sewasti on GitHub (Feb 27, 2026).
Original GitHub issue: https://github.com/open-webui/open-webui/issues/21927

Summary

When a model generates incomplete or malformed JSON for a built-in tool call (e.g., missing required parameters like content in replace_note_content), OWUI's response_handler in utils/middleware.py fails to parse the arguments and terminates the SSE stream. The browser shows "Network connection lost" — leaving the user with no actionable information and no way to understand what went wrong.

Environment

  • Open WebUI v0.8.5
  • LLM: anthropic/claude-sonnet-4.6 via OpenRouter (with extended thinking / reasoning_effort: high)
  • Built-in Notes tools (search_notes, view_note, replace_note_content)

Steps to Reproduce

  1. Enable built-in Notes tools for a model with extended thinking (e.g., Claude Sonnet 4.6)
  2. Ask the model to edit a note using replace_note_content
  3. If the model generates an incomplete tool call (e.g., generates note_id and title but the stream is cut before the large content field is emitted)
  4. → OWUI logs ERROR and terminates the SSE stream
  5. → Browser shows "Network connection lost"

Log Evidence

ERROR | open_webui.utils.middleware:response_handler:4059 - Error parsing tool call arguments: {"note_id": "9af73036-6a51-4840-98d6-b348d4e26595", "title": "AI-Richtlinie"
WARNING | open_webui.utils.middleware:response_handler:4532 - Task was cancelled!

The JSON is truncated — json.loads() and ast.literal_eval() both fail. The handler currently silently drops the connection.

Code Path (v0.8.5)

In open_webui/utils/middleware.py, response_handler around line 4059:

try:
    tool_function_params = ast.literal_eval(tool_args)
except Exception as e:
    log.debug(e)
    try:
        tool_function_params = json.loads(tool_args)
    except Exception as e:
        log.error(f"Error parsing tool call arguments: {tool_args}")
        # ← After this, tool_function_params = {} and the stream terminates
        # ← User sees "Network connection lost" with zero context

Expected Behavior

When tool argument parsing fails, OWUI should:

  1. Stream a clear error message to the user instead of terminating the connection:

    ⚠️ Tool call failed (replace_note_content): arguments could not be parsed. Please try again.

  2. Continue the conversation turn — do not cancel the SSE stream
  3. (Bonus) Validate tool call args against the tool's JSON Schema required fields before executing — reject calls with missing required params with a clear message instead of a Python exception downstream

Proposed Fix (sketch)

except Exception as e:
    log.error(f"Error parsing tool call arguments: {tool_args}")
    # Gracefully inform the user instead of crashing the stream
    await event_emitter({
        "type": "message",
        "data": {
            "content": f"\n\n⚠️ Tool call failed: could not parse arguments for `{tool_function_name}`. Please try again."
        }
    })
    continue  # skip this tool call, keep the handler alive

Impact

  • Users see a cryptic "Network connection lost" instead of a clear retry prompt
  • The note is not saved; the user has to manually retry without knowing why it failed
  • Extended thinking models (which occasionally misformat tool call JSON) are disproportionately affected

Additional Context

This was observed with replace_note_content (built-in Notes tool) where the content parameter — which contains the full note markdown — is the last and largest JSON field. On first attempt the model omitted it; on retry (with longer thinking time) it succeeded. Better error surfacing would make this a minor UX annoyance rather than a confusing hard failure.

Originally created by @sewasti on GitHub (Feb 27, 2026). Original GitHub issue: https://github.com/open-webui/open-webui/issues/21927 ## Summary When a model generates incomplete or malformed JSON for a built-in tool call (e.g., missing required parameters like `content` in `replace_note_content`), OWUI's `response_handler` in `utils/middleware.py` fails to parse the arguments and **terminates the SSE stream**. The browser shows "Network connection lost" — leaving the user with no actionable information and no way to understand what went wrong. ## Environment - Open WebUI **v0.8.5** - LLM: `anthropic/claude-sonnet-4.6` via OpenRouter (with extended thinking / `reasoning_effort: high`) - Built-in Notes tools (`search_notes`, `view_note`, `replace_note_content`) ## Steps to Reproduce 1. Enable built-in Notes tools for a model with extended thinking (e.g., Claude Sonnet 4.6) 2. Ask the model to edit a note using `replace_note_content` 3. If the model generates an incomplete tool call (e.g., generates `note_id` and `title` but the stream is cut before the large `content` field is emitted) 4. → OWUI logs `ERROR` and terminates the SSE stream 5. → Browser shows "Network connection lost" ## Log Evidence ``` ERROR | open_webui.utils.middleware:response_handler:4059 - Error parsing tool call arguments: {"note_id": "9af73036-6a51-4840-98d6-b348d4e26595", "title": "AI-Richtlinie" WARNING | open_webui.utils.middleware:response_handler:4532 - Task was cancelled! ``` The JSON is truncated — `json.loads()` and `ast.literal_eval()` both fail. The handler currently silently drops the connection. ## Code Path (v0.8.5) In `open_webui/utils/middleware.py`, `response_handler` around line 4059: ```python try: tool_function_params = ast.literal_eval(tool_args) except Exception as e: log.debug(e) try: tool_function_params = json.loads(tool_args) except Exception as e: log.error(f"Error parsing tool call arguments: {tool_args}") # ← After this, tool_function_params = {} and the stream terminates # ← User sees "Network connection lost" with zero context ``` ## Expected Behavior When tool argument parsing fails, OWUI should: 1. **Stream a clear error message** to the user instead of terminating the connection: > ⚠️ Tool call failed (`replace_note_content`): arguments could not be parsed. Please try again. 2. **Continue the conversation turn** — do not cancel the SSE stream 3. **(Bonus)** Validate tool call args against the tool's JSON Schema `required` fields **before** executing — reject calls with missing required params with a clear message instead of a Python exception downstream ## Proposed Fix (sketch) ```python except Exception as e: log.error(f"Error parsing tool call arguments: {tool_args}") # Gracefully inform the user instead of crashing the stream await event_emitter({ "type": "message", "data": { "content": f"\n\n⚠️ Tool call failed: could not parse arguments for `{tool_function_name}`. Please try again." } }) continue # skip this tool call, keep the handler alive ``` ## Impact - Users see a cryptic "Network connection lost" instead of a clear retry prompt - The note is not saved; the user has to manually retry without knowing why it failed - Extended thinking models (which occasionally misformat tool call JSON) are disproportionately affected ## Additional Context This was observed with `replace_note_content` (built-in Notes tool) where the `content` parameter — which contains the full note markdown — is the last and largest JSON field. On first attempt the model omitted it; on retry (with longer thinking time) it succeeded. Better error surfacing would make this a minor UX annoyance rather than a confusing hard failure.
Sign in to join this conversation.
1 Participants
Notifications
Due Date
No due date set.
Dependencies

No dependencies set.

Reference: github-starred/open-webui#90358