From e208f82076182e71a4eb8470eb527363158f4b0c Mon Sep 17 00:00:00 2001 From: vishesh10 Date: Thu, 22 Feb 2024 16:46:24 +0530 Subject: [PATCH] Add support for multiple-compressed responses (#6063) --- .../downloadermiddlewares/httpcompression.py | 34 ++++++++-- .../compressed/html-gzip-deflate-gzip.bin | Bin 0 -> 8014 bytes .../compressed/html-gzip-deflate.bin | Bin 0 -> 7991 bytes ...st_downloadermiddleware_httpcompression.py | 58 ++++++++++++++++++ 4 files changed, 87 insertions(+), 5 deletions(-) create mode 100644 tests/sample_data/compressed/html-gzip-deflate-gzip.bin create mode 100644 tests/sample_data/compressed/html-gzip-deflate.bin diff --git a/scrapy/downloadermiddlewares/httpcompression.py b/scrapy/downloadermiddlewares/httpcompression.py index 709333948..1e340abb6 100644 --- a/scrapy/downloadermiddlewares/httpcompression.py +++ b/scrapy/downloadermiddlewares/httpcompression.py @@ -1,6 +1,7 @@ from __future__ import annotations import warnings +from itertools import chain from logging import getLogger from typing import TYPE_CHECKING, List, Optional, Union @@ -102,18 +103,18 @@ class HttpCompressionMiddleware: if isinstance(response, Response): content_encoding = response.headers.getlist("Content-Encoding") if content_encoding: - encoding = content_encoding.pop() max_size = request.meta.get("download_maxsize", self._max_size) warn_size = request.meta.get("download_warnsize", self._warn_size) try: - decoded_body = self._decode( - response.body, encoding.lower(), max_size + decoded_body, content_encoding = self._handle_encoding( + response.body, content_encoding, max_size ) except _DecompressionMaxSizeExceeded: raise IgnoreRequest( f"Ignored response {response} because its body " - f"({len(response.body)} B) exceeded DOWNLOAD_MAXSIZE " - f"({max_size} B) during decompression." + f"({len(response.body)} B compressed) exceeded " + f"DOWNLOAD_MAXSIZE ({max_size} B) during " + f"decompression." ) if len(response.body) < warn_size <= len(decoded_body): logger.warning( @@ -121,6 +122,7 @@ class HttpCompressionMiddleware: f"({len(decoded_body)} B) is larger than the " f"download warning size ({warn_size} B)." ) + response.headers["Content-Encoding"] = content_encoding if self.stats: self.stats.inc_value( "httpcompression/response_bytes", @@ -144,6 +146,28 @@ class HttpCompressionMiddleware: return response + def _handle_encoding(self, body, content_encoding, max_size): + to_decode, to_keep = self._split_encodings(content_encoding) + for encoding in to_decode: + body = self._decode(body, encoding, max_size) + return body, to_keep + + def _split_encodings(self, content_encoding): + to_keep = [ + encoding.strip().lower() + for encoding in chain.from_iterable( + encodings.split(b",") for encodings in content_encoding + ) + ] + to_decode = [] + while to_keep: + encoding = to_keep.pop() + if encoding not in ACCEPTED_ENCODINGS: + to_keep.append(encoding) + return to_decode, to_keep + to_decode.append(encoding) + return to_decode, to_keep + def _decode(self, body: bytes, encoding: bytes, max_size: int) -> bytes: if encoding == b"gzip" or encoding == b"x-gzip": return gunzip(body, max_size=max_size) diff --git a/tests/sample_data/compressed/html-gzip-deflate-gzip.bin b/tests/sample_data/compressed/html-gzip-deflate-gzip.bin new file mode 100644 index 0000000000000000000000000000000000000000..d66f4c5a03df80085208d8990df59e1702c63b50 GIT binary patch literal 8014 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 Q142u<+9f5~j5i+u01a&HYybcN literal 0 HcmV?d00001 diff --git a/tests/sample_data/compressed/html-gzip-deflate.bin b/tests/sample_data/compressed/html-gzip-deflate.bin new file mode 100644 index 0000000000000000000000000000000000000000..5066842ef7d137786f43682c99c63e24eae261ec GIT binary patch literal 7991 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 literal 0 HcmV?d00001 diff --git a/tests/test_downloadermiddleware_httpcompression.py b/tests/test_downloadermiddleware_httpcompression.py index 9deb81c37..ae5569d0a 100644 --- a/tests/test_downloadermiddleware_httpcompression.py +++ b/tests/test_downloadermiddleware_httpcompression.py @@ -27,6 +27,8 @@ FORMAT = { "x-gzip": ("html-gzip.bin", "gzip"), "rawdeflate": ("html-rawdeflate.bin", "deflate"), "zlibdeflate": ("html-zlibdeflate.bin", "deflate"), + "gzip-deflate": ("html-gzip-deflate.bin", "gzip, deflate"), + "gzip-deflate-gzip": ("html-gzip-deflate-gzip.bin", "gzip, deflate, gzip"), "br": ("html-br.bin", "br"), # $ zstd raw.html --content-size -o html-zstd-static-content-size.bin "zstd-static-content-size": ("html-zstd-static-content-size.bin", "zstd"), @@ -205,6 +207,62 @@ class HttpCompressionTest(TestCase): assert newresponse is not response self.assertEqual(newresponse.headers.getlist("Content-Encoding"), [b"uuencode"]) + def test_multi_compression_single_header(self): + response = self._getresponse("gzip-deflate") + request = response.request + newresponse = self.mw.process_response(request, response, self.spider) + assert newresponse is not response + assert "Content-Encoding" not in newresponse.headers + assert newresponse.body.startswith(b"