BerriAI/litellm · error · LangGraphError

Error processing response

Error message

Error processing response: {e}

What it means

LangGraphConfig.transform_response wraps the whole response conversion in try/except; any exception inside (most often raw_response.json() failing on a non-JSON body, or an unexpected response shape) is re-raised as LangGraphError "Error processing response: {e}" with the HTTP status of the original response. The {e} part names the real underlying failure, so read it first.

Solutions

  1. Look at the {e} suffix — a JSONDecodeError means non-JSON body, anything else points at the shape
  2. Enable verbose logging and dump raw_response.text to see exactly what the server returned
  3. Point api_base at the LangGraph API root (no UI path, no trailing /runs)
  4. Confirm auth is accepted (JSON error beats an HTML login page)
  5. Reproduce with curl to {api_base}/runs/wait to inspect the raw body

Example fix

# before: api_base points at the UI -> HTML body -> 'Error processing response: ...'
litellm.completion(model="langgraph/agent", api_base="https://host/ui/", messages=[...])

# after
import litellm
litellm.verbose_logger.setLevel("DEBUG")  # log raw response for diagnosis
litellm.completion(model="langgraph/agent", api_base="https://host", messages=[...])
Defensive patterns

Strategy: try-catch

Validate before calling

import httpx

def langgraph_serves_json(base: str) -> None:
    r = httpx.post(
        f"{base.rstrip('/')}/runs/wait",
        json={"assistant_id": "agent", "input": {"messages": []}},
        timeout=10,
    )
    if "json" not in r.headers.get("content-type", ""):
        raise RuntimeError(f"{base} is not a LangGraph API endpoint (content-type={r.headers.get('content-type')!r})")

Try / catch

try:
    resp = litellm.completion(model="langgraph/agent", messages=msgs, api_base=base)
except Exception as e:
    if "Error processing response" in str(getattr(e, "message", "")):
        log.error("LangGraph returned an unparseable body (HTTP %s); dumping base URL config", getattr(e, "status_code", None))
    raise

Prevention

When it happens

Trigger: The /runs/wait (or streamed final) response body is HTML/plain-text (auth page, gateway error) so .json() throws; the JSON parses but is not the expected dict shape; a truncated or wrongly-encoded body from an intermediary proxy.

Common situations: api_base pointing at the LangGraph UI page instead of the API; an ingress returning an HTML error page under load; a version of LangGraph server whose response envelope differs from what the extractor expects.

Related errors


AI-assisted analysis of BerriAI/litellm@77b7c6c40c (2026-08-18). Data as JSON: /api/errors/44e27d9c139088fc. Report an issue: GitHub.

Appendix: source

Thrown at litellm/llms/langgraph/chat/transformation.py:460

                prompt_tokens: Final = token_counter(model="gpt-3.5-turbo", messages=messages)
                completion_tokens = token_counter(model="gpt-3.5-turbo", text=content, count_response_tokens=True)
                total_tokens: Final = prompt_tokens + completion_tokens

                usage: Final = Usage(
                    prompt_tokens=prompt_tokens,
                    completion_tokens=completion_tokens,
                    total_tokens=total_tokens,
                )
                setattr(model_response, "usage", usage)
            except Exception as e:
                verbose_logger.warning("Failed to calculate token usage: %s", e)

            return model_response

        except Exception as e:
            verbose_logger.error("Error processing LangGraph response: %s", e)
            raise LangGraphError(
                message=f"Error processing response: {e}",
                status_code=raw_response.status_code,
            )

    def validate_environment(
        self,
        headers: dict,
        model: str,
        messages: list[AllMessageValues],
        optional_params: dict,
        litellm_params: dict,
        api_key: str | None = None,
        api_base: str | None = None,
    ) -> dict:
        """
        Validate and set up environment for LangGraph requests.
        """
        headers["Content-Type"] = "application/json"

View on GitHub (pinned to 77b7c6c40c)