[Zope2] Multiline response headers causing problems for proxies.

Laurence Rowe <[email protected]>
Newsgroups gmane.comp.web.zope.devel
Message-ID <[email protected]>
When using response.appendHeader, Zope appends the new value following
an ",\r\n\t" which splits the header over multiple lines. While this
behaviour is standards compliant, it causes problems for both Varnish
[1] and Nginx [2] which may then mangle the header value.

In fact the HTTP 1.0 spec notes that splitting over multiple lines in
not recommended [3], though the HTTP 1.1 spec does not mention this
explicitly, though it does say [4]:
    "Applications ought to follow "common form", where one is known or
indicated, when generating HTTP constructs, since there might exist
some implementations that fail to accept anything"

Are there any objections to me applying the attached patch to Zope
2.13 and trunk?

Laurence

[1] http://www.varnish-cache.org/trac/ticket/905
[2] http://nginx.org/pipermail/nginx-devel/2011-April/000859.html
[3] http://tools.ietf.org/html/rfc1945#section-4.2
[4] http://www.w3.org/Protocols/rfc2616/rfc2616-sec4.html

_______________________________________________
Zope-Dev maillist  -  [email protected]
https://mail.zope.org/mailman/listinfo/zope-dev
**  No cross posts or HTML encoding!  **
(Related lists - 
 https://mail.zope.org/mailman/listinfo/zope-announce
 https://mail.zope.org/mailman/listinfo/zope )
appendHeader.patch (application/octet-stream, 1.8 KB)
Index: src/ZPublisher/HTTPResponse.py
===================================================================
--- src/ZPublisher/HTTPResponse.py	(revision 121442)
+++ src/ZPublisher/HTTPResponse.py	(working copy)
@@ -338,7 +338,7 @@
             name = literal and name or key
             self.headers[name] = value
 
-    def appendHeader(self, name, value, delimiter=","):
+    def appendHeader(self, name, value, delimiter=", "):
         """ Append a value to an HTTP return header.
 
         Set an HTTP return header "name" with value "value",
@@ -353,7 +353,7 @@
         headers = self.headers
         if headers.has_key(name):
             h = headers[name]
-            h = "%s%s\r\n\t%s" % (h, delimiter, value)
+            h = "%s%s%s" % (h, delimiter, value)
         else:
             h = value
         self.setHeader(name,h, scrubbed=True)
Index: src/ZPublisher/tests/testHTTPResponse.py
===================================================================
--- src/ZPublisher/tests/testHTTPResponse.py	(revision 121442)
+++ src/ZPublisher/tests/testHTTPResponse.py	(working copy)
@@ -445,13 +445,13 @@
         response = self._makeOne()
         response.setHeader('foo', 'bar')
         response.appendHeader('foo', 'foo')
-        self.assertEqual(response.headers.get('foo'), 'bar,\r\n\tfoo')
+        self.assertEqual(response.headers.get('foo'), 'bar, foo')
 
     def test_appendHeader_w_existing_case_insenstative(self):
         response = self._makeOne()
         response.setHeader('xxx', 'bar')
         response.appendHeader('XXX', 'foo')
-        self.assertEqual(response.headers.get('xxx'), 'bar,\r\n\tfoo')
+        self.assertEqual(response.headers.get('xxx'), 'bar, foo')
 
     def test_appendHeader_drops_CRLF(self):
         # RFC2616 disallows CRLF in a header value.
lmpx.com only provides a reader for public news (NNTP) servers. It is not affiliated with the servers or forums shown here and is not responsible for the content of articles, which is written by their respective authors.