1 | diff --git a/django/core/handlers/wsgi.py b/django/core/handlers/wsgi.py
|
---|
2 | index 4c07105..976bba7 100644
|
---|
3 | --- a/django/core/handlers/wsgi.py
|
---|
4 | +++ b/django/core/handlers/wsgi.py
|
---|
5 | @@ -12,6 +12,7 @@ from django.core.handlers import base
|
---|
6 | from django.core.urlresolvers import set_script_prefix
|
---|
7 | from django.utils import datastructures
|
---|
8 | from django.utils.encoding import force_str, force_text, iri_to_uri
|
---|
9 | +from django.utils import six
|
---|
10 |
|
---|
11 | logger = logging.getLogger('django.request')
|
---|
12 |
|
---|
13 | @@ -125,10 +126,22 @@ class LimitedStream(object):
|
---|
14 | return line
|
---|
15 |
|
---|
16 |
|
---|
17 | +def fix_path_info(path):
|
---|
18 | + """
|
---|
19 | + On Python 3, wsgiref.WSGIRequestHandler is unconditionally decoding the
|
---|
20 | + request path with 'iso-8859-1' encoding. We have to fix this.
|
---|
21 | + See https://code.djangoproject.com/ticket/19468 and
|
---|
22 | + http://bugs.python.org/issue16679
|
---|
23 | + """
|
---|
24 | + return path.encode('iso-8859-1').decode('utf-8')
|
---|
25 | +
|
---|
26 | class WSGIRequest(http.HttpRequest):
|
---|
27 | def __init__(self, environ):
|
---|
28 | script_name = base.get_script_name(environ)
|
---|
29 | - path_info = force_text(environ.get('PATH_INFO', '/'))
|
---|
30 | + if six.PY3:
|
---|
31 | + path_info = fix_path_info(environ.get('PATH_INFO', '/'))
|
---|
32 | + else:
|
---|
33 | + path_info = force_text(environ.get('PATH_INFO', '/'))
|
---|
34 | if not path_info or path_info == script_name:
|
---|
35 | # Sometimes PATH_INFO exists, but is empty (e.g. accessing
|
---|
36 | # the SCRIPT_NAME URL without a trailing slash). We really need to
|
---|
37 | diff --git a/tests/regressiontests/requests/tests.py b/tests/regressiontests/requests/tests.py
|
---|
38 | index adf824d..7e67b32 100644
|
---|
39 | --- a/tests/regressiontests/requests/tests.py
|
---|
40 | +++ b/tests/regressiontests/requests/tests.py
|
---|
41 | @@ -11,6 +11,7 @@ from django.core.handlers.wsgi import WSGIRequest, LimitedStream
|
---|
42 | from django.http import HttpRequest, HttpResponse, parse_cookie, build_request_repr, UnreadablePostError
|
---|
43 | from django.test.client import FakePayload
|
---|
44 | from django.test.utils import override_settings, str_prefix
|
---|
45 | +from django.utils import six
|
---|
46 | from django.utils import unittest
|
---|
47 | from django.utils.http import cookie_date, urlencode
|
---|
48 | from django.utils.timezone import utc
|
---|
49 | @@ -57,6 +58,12 @@ class RequestsTests(unittest.TestCase):
|
---|
50 | self.assertEqual(build_request_repr(request, path_override='/otherpath/', GET_override={'a': 'b'}, POST_override={'c': 'd'}, COOKIES_override={'e': 'f'}, META_override={'g': 'h'}),
|
---|
51 | str_prefix("<WSGIRequest\npath:/otherpath/,\nGET:{%(_)s'a': %(_)s'b'},\nPOST:{%(_)s'c': %(_)s'd'},\nCOOKIES:{%(_)s'e': %(_)s'f'},\nMETA:{%(_)s'g': %(_)s'h'}>"))
|
---|
52 |
|
---|
53 | + @unittest.skipUnless(six.PY3, "PATH_INFO decoding only happens on Python 3")
|
---|
54 | + def test_wsgirequest_path_info(self):
|
---|
55 | + """Testing fix for #19468"""
|
---|
56 | + request = WSGIRequest({'PATH_INFO': '/سÙاÙ
|
---|
57 | /', 'REQUEST_METHOD': 'get', 'wsgi.input': BytesIO(b'')})
|
---|
58 | + self.assertEqual(request.path, "/سلام/")
|
---|
59 | +
|
---|
60 | def test_parse_cookie(self):
|
---|
61 | self.assertEqual(parse_cookie('invalid@key=true'), {})
|
---|
62 |
|
---|