From d6e33795a90fe1cfd487acf230ddef1d9a28552a Mon Sep 17 00:00:00 2001 From: Gabriel Hurley Date: Sun, 7 Nov 2010 23:02:24 +0000 Subject: [PATCH] Fixed #11877 -- Documented that HttpRequest.get_host() fails behind multiple reverse proxies, and added an example middleware solution. Thanks to Tom Evans for the report, and arnav for the patch. git-svn-id: http://code.djangoproject.com/svn/django/trunk@14493 bcc190cf-cafb-0310-a4f2-bffc1f526a37 --- docs/ref/request-response.txt | 37 ++++++++++++++++++++++++++++------- 1 file changed, 30 insertions(+), 7 deletions(-) diff --git a/docs/ref/request-response.txt b/docs/ref/request-response.txt index 6cd328475b..7f2284f9f5 100644 --- a/docs/ref/request-response.txt +++ b/docs/ref/request-response.txt @@ -210,16 +210,39 @@ Methods .. method:: HttpRequest.get_host() - .. versionadded:: 1.0 + .. versionadded:: 1.0 - Returns the originating host of the request using information from the - ``HTTP_X_FORWARDED_HOST`` and ``HTTP_HOST`` headers (in that order). If - they don't provide a value, the method uses a combination of - ``SERVER_NAME`` and ``SERVER_PORT`` as detailed in `PEP 333`_. + Returns the originating host of the request using information from the + ``HTTP_X_FORWARDED_HOST`` and ``HTTP_HOST`` headers (in that order). If + they don't provide a value, the method uses a combination of + ``SERVER_NAME`` and ``SERVER_PORT`` as detailed in `PEP 333`_. - .. _PEP 333: http://www.python.org/dev/peps/pep-0333/ + .. _PEP 333: http://www.python.org/dev/peps/pep-0333/ + + Example: ``"127.0.0.1:8000"`` + + .. note:: The :meth:`~HttpRequest.get_host()` method fails when the host is + behind multiple proxies. One solution is to use middleware to rewrite + the proxy headers, as in the following example:: + + class MultipleProxyMiddleware(object): + FORWARDED_FOR_FIELDS = [ + 'HTTP_X_FORWARDED_FOR', + 'HTTP_X_FORWARDED_HOST', + 'HTTP_X_FORWARDED_SERVER', + ] + + def process_request(self, request): + """ + Rewrites the proxy headers so that only the most + recent proxy is used. + """ + for field in self.FORWARDED_FOR_FIELDS: + if field in request.META: + if ',' in request.META[field]: + parts = request.META[field].split(',') + request.META[field] = parts[-1].strip() - Example: ``"127.0.0.1:8000"`` .. method:: HttpRequest.get_full_path()