{"record":{"id":"26ea86c5e6ae4210","repo":"aio-libs/aiohttp","slug":"wsclosecode-message-too-big","errorCode":"WSCloseCode.MESSAGE_TOO_BIG","errorMessage":"Decompressed message exceeds size limit {self._max_msg_size}","messagePattern":"Decompressed message exceeds size limit (.+?)","errorType":"exception","errorClass":"WebSocketError","httpStatus":null,"severity":"error","filePath":"aiohttp/_websocket/reader_py.py","lineNumber":257,"sourceCode":"            # received.\n            if compressed:\n                if not self._decompressobj:\n                    self._decompressobj = ZLibDecompressor(suppress_deflate_header=True)\n                # XXX: It's possible that the zlib backend (isal is known to\n                # do this, maybe others too?) will return max_length bytes,\n                # but internally buffer more data such that the payload is\n                # >max_length, so we return one extra byte and if we're able\n                # to do that, then the message is too big.\n                payload_merged = self._decompressobj.decompress_sync(\n                    assembled_payload + WS_DEFLATE_TRAILING,\n                    (\n                        self._max_msg_size + 1\n                        if self._max_msg_size\n                        else self._max_msg_size\n                    ),\n                )\n                if self._max_msg_size and len(payload_merged) > self._max_msg_size:\n                    raise WebSocketError(\n                        WSCloseCode.MESSAGE_TOO_BIG,\n                        f\"Decompressed message exceeds size limit {self._max_msg_size}\",\n                    )\n            elif type(assembled_payload) is bytes:\n                payload_merged = assembled_payload\n            else:\n                payload_merged = bytes(assembled_payload)\n\n            size = len(payload_merged)\n            if opcode == OP_CODE_TEXT:\n                if self._decode_text:\n                    try:\n                        text = payload_merged.decode(\"utf-8\")\n                    except UnicodeDecodeError as exc:\n                        raise WebSocketError(\n                            WSCloseCode.INVALID_TEXT, \"Invalid UTF-8 text message\"\n                        ) from exc\n","sourceCodeStart":239,"sourceCodeEnd":275,"githubUrl":"https://github.com/aio-libs/aiohttp/blob/d9aaf697c2cd4783ca5749a971965c689f3ec24f/aiohttp/_websocket/reader_py.py#L239-L275","documentation":"Raised as WebSocketError(MESSAGE_TOO_BIG) at reader_py.py:257 after a permessage-deflate decompression when the decompressed payload length exceeds self._max_msg_size. This guards against zip-bomb style attacks where a tiny compressed frame expands past the limit. The decompressor is intentionally allowed to return one extra byte (max_msg_size+1) so that a payload exactly at the boundary is still detectable as over-limit.","triggerScenarios":"A compressed (permessage-deflate) text/binary message whose decompressed size exceeds the configured max_msg_size. Default max_msg_size is 4 MiB (4*1024*1024) on both client (client.py:944/1019) and server (web_ws.py:109). The connection is closed with code 1009 (MESSAGE_TOO_BIG).","commonSituations":"Legitimate large payloads (bulk JSON, images) sent compressed when max_msg_size was left at the 4 MiB default; a malicious peer performing a compression amplification / zip-bomb attack; raising max_msg_size on one side but not the other.","solutions":["Increase max_msg_size on the receiving side: `ws_connect(url, max_msg_size=16*1024*1024)` or `WebSocketResponse(max_msg_size=...)`.","If you cannot raise the limit, have the sender split the payload into smaller chunks or avoid permessage-deflate for that message.","Treat MESSAGE_TOO_BIG as fatal for the session: log, close, and optionally ask the peer to resend smaller frames."],"exampleFix":"// before\nws = await session.ws_connect(url)  # max_msg_size defaults to 4 MiB\n\n# after\nws = await session.ws_connect(url, max_msg_size=16 * 1024 * 1024)","handlingStrategy":"validation","validationCode":"# raise the cap to match the largest expected compressed-then-decompressed payload\nMAX = 16 * 1024 * 1024\nws = await session.ws_connect(url, compress=15, max_msg_size=MAX)","typeGuard":null,"tryCatchPattern":"msg = await ws.receive()\nif msg.type == aiohttp.WSMsgType.ERROR and msg.data.code == aiohttp.WSCloseCode.MESSAGE_TOO_BIG:\n    await ws.close()\n    notify_peer_to_chunk()","preventionTips":["Set max_msg_size large enough for the decompressed payload, not just the compressed wire size.","Keep max_msg_size symmetric on client and server.","For unbounded data, have the sender chunk into messages below the limit rather than raising it indefinitely."],"tags":["websocket","limits","compression","deflate","zip-bomb","message-size"],"analyzedSha":"d9aaf697c2cd4783ca5749a971965c689f3ec24f","analyzedAt":"2026-08-06T21:30:48.638Z","schemaVersion":2},"datasetVersion":"2026-08-07T03:17:09.362Z"}