{"record":{"id":"b88e0eba12561acf","repo":"NousResearch/hermes-agent","slug":"non-ascii-lsp-header-line-r","errorCode":null,"errorMessage":"non-ASCII LSP header: {line!r}","messagePattern":"non-ASCII LSP header: (.+?)","errorType":"exception","errorClass":"LSPProtocolError","httpStatus":null,"severity":"error","filePath":"agent/lsp/protocol.py","lineNumber":102,"sourceCode":"                return None\n            raise LSPProtocolError(\n                f\"unexpected EOF while reading LSP headers (partial={e.partial!r})\"\n            ) from e\n        # Defensive cap against a server streaming headers without ever\n        # emitting CRLF-CRLF.  Caps total header bytes at 8 KiB — a\n        # well-behaved server fits in well under 200 bytes.\n        header_bytes += len(line)\n        if header_bytes > 8192:\n            raise LSPProtocolError(\n                \"LSP header block exceeded 8 KiB without terminator\"\n            )\n        line = line[:-2]  # strip CRLF\n        if not line:\n            break  # blank line ends header block\n        try:\n            key, _, value = line.decode(\"ascii\").partition(\":\")\n        except UnicodeDecodeError as e:\n            raise LSPProtocolError(f\"non-ASCII LSP header: {line!r}\") from e\n        if not key:\n            raise LSPProtocolError(f\"malformed LSP header line: {line!r}\")\n        headers[key.strip().lower()] = value.strip()\n\n    cl = headers.get(\"content-length\")\n    if cl is None:\n        raise LSPProtocolError(f\"LSP message missing Content-Length: {headers!r}\")\n    try:\n        n = int(cl)\n    except ValueError as e:\n        raise LSPProtocolError(f\"non-integer Content-Length: {cl!r}\") from e\n    if n < 0 or n > 64 * 1024 * 1024:  # 64 MiB sanity cap\n        raise LSPProtocolError(f\"unreasonable Content-Length: {n}\")\n\n    try:\n        body = await reader.readexactly(n)\n    except asyncio.IncompleteReadError as e:\n        raise LSPProtocolError(","sourceCodeStart":84,"sourceCodeEnd":120,"githubUrl":"https://github.com/NousResearch/hermes-agent/blob/c896c09c42910c584c4c7d2325b58c14713ea42c/agent/lsp/protocol.py#L84-L120","documentation":"LSPProtocolError raised when a header line cannot be decoded as ASCII — the LSP base protocol requires ASCII headers (UTF-8 is only allowed in the JSON body). Non-ASCII bytes in the header region mean the stream is not LSP framing at all or the framing has desynced.","triggerScenarios":"The parser is reading where it expects headers but finds UTF-8 body or diagnostics text: desynced framing after a wrong Content-Length, a server printing localized/non-ASCII messages (e.g. a stack trace with accents or CJK) to stdout, or binary garbage after a crash.","commonSituations":"Server with a non-English locale printing errors to stdout; framing desync caused by an earlier message whose declared Content-Length did not match actual bytes written.","solutions":["Force an English/UTF-8-safe environment for the server (LC_ALL=C.UTF-8) and ensure all diagnostics go to stderr.","Update the server — Content-Length mismatches (the root cause of desync) are known bugs in several servers and get fixed.","If you control the server, double-check that byte length, not character length, is used for Content-Length."],"exampleFix":"# before\nenv = {\"PATH\": ...}  # inherits locale that makes server print localized output to stdout\n\n# after\nenv = {**os.environ, \"LC_ALL\": \"C.UTF-8\"}\nLSPClient(cmd=[server, \"--stdio\"], env=env, ...)","handlingStrategy":"fallback","validationCode":null,"typeGuard":null,"tryCatchPattern":"try:\n    msg = await read_message(reader)\nexcept LSPProtocolError as e:\n    if \"non-ASCII\" in str(e) or \"malformed\" in str(e):\n        restart_with_clean_env_and_stderr_only_logging()\n    else:\n        raise","preventionTips":["Set LC_ALL=C.UTF-8 for server subprocesses so no localized output hits stdout.","Keep server stdout reserved strictly for LSP framing; all logs to stderr.","When framing desyncs once, restart the session — the stream rarely re-aligns."],"tags":["lsp","protocol","encoding"],"backgroundTag":null,"analyzedSha":"c896c09c42910c584c4c7d2325b58c14713ea42c","analyzedAt":"2026-08-14T17:18:01.089Z","schemaVersion":2},"datasetVersion":"2026-08-15T22:17:37.221Z"}