summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJason Madden <jason+github@nextthought.com>2020-01-13 06:40:40 -0600
committerChris Dent <cdent@anticdent.org>2020-01-13 12:40:40 +0000
commitd38247d52c03ebf66a922ac1a1fa2cc9a77789ca (patch)
tree333b69fe1acde89b99093cc38128d55ba6ca78dc
parent1cc7e73f9980618f620d8e176858fe8f59ed03fc (diff)
downloadpaste-git-d38247d52c03ebf66a922ac1a1fa2cc9a77789ca.tar.gz
Make gzip middleware stop producing a spurious response body on HEAD requests. (#44)
Fixes #43
-rw-r--r--paste/fixture.py12
-rw-r--r--paste/gzipper.py7
-rw-r--r--tests/test_gzipper.py12
3 files changed, 27 insertions, 4 deletions
diff --git a/paste/fixture.py b/paste/fixture.py
index 4b88718..9f175fb 100644
--- a/paste/fixture.py
+++ b/paste/fixture.py
@@ -299,6 +299,18 @@ class TestApp(object):
extra_environ=extra_environ,status=status,
upload_files=None, expect_errors=expect_errors)
+ def head(self, url, headers=None, extra_environ=None,
+ status=None, expect_errors=False):
+ """
+ Do a HEAD request. Very like the ``.get()`` method.
+
+ Returns a `response object
+ <class-paste.fixture.TestResponse.html>`_
+ """
+ return self._gen_request('HEAD', url, headers=headers,
+ extra_environ=extra_environ,status=status,
+ upload_files=None, expect_errors=expect_errors)
+
diff --git a/paste/gzipper.py b/paste/gzipper.py
index eca8775..0882c67 100644
--- a/paste/gzipper.py
+++ b/paste/gzipper.py
@@ -25,9 +25,12 @@ class middleware(object):
self.compress_level = int(compress_level)
def __call__(self, environ, start_response):
- if 'gzip' not in environ.get('HTTP_ACCEPT_ENCODING', ''):
+ if 'gzip' not in environ.get('HTTP_ACCEPT_ENCODING', '') \
+ or environ['REQUEST_METHOD'] == 'HEAD':
# nothing for us to do, so this middleware will
- # be a no-op:
+ # be a no-op (there's no body expected in the HEAD case,
+ # and if we open a GzipFile we would produce an erroneous
+ # 20-byte header and trailer):
return self.application(environ, start_response)
response = GzipResponse(start_response, self.compress_level)
app_iter = self.application(environ,
diff --git a/tests/test_gzipper.py b/tests/test_gzipper.py
index 54b7901..d56c406 100644
--- a/tests/test_gzipper.py
+++ b/tests/test_gzipper.py
@@ -4,8 +4,10 @@ import gzip
import six
def simple_app(environ, start_response):
- start_response('200 OK', [('content-type', 'text/plain')])
- return [b'this is a test']
+ start_response('200 OK',
+ [('content-type', 'text/plain'),
+ ('content-length', '0')])
+ return [b'this is a test'] if environ['REQUEST_METHOD'] != 'HEAD' else []
wsgi_app = middleware(simple_app)
app = TestApp(wsgi_app)
@@ -17,3 +19,9 @@ def test_gzip():
assert res.body != b'this is a test'
actual = gzip.GzipFile(fileobj=six.BytesIO(res.body)).read()
assert actual == b'this is a test'
+
+def test_gzip_head():
+ res = app.head(
+ '/', extra_environ=dict(HTTP_ACCEPT_ENCODING='gzip'))
+ assert int(res.header('content-length')) == 0
+ assert res.body == b''