Fixed #4772 -- Fixed reverse URL creation to work with non-ASCII arguments.
Also included a test for non-ASCII strings in URL patterns, although that already worked correctly. git-svn-id: http://code.djangoproject.com/svn/django/trunk@5630 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
parent
fad7247715
commit
8c85ddf306
|
@ -9,7 +9,7 @@ a string) and returns a tuple in this format:
|
||||||
|
|
||||||
from django.http import Http404
|
from django.http import Http404
|
||||||
from django.core.exceptions import ImproperlyConfigured, ViewDoesNotExist
|
from django.core.exceptions import ImproperlyConfigured, ViewDoesNotExist
|
||||||
from django.utils.encoding import iri_to_uri
|
from django.utils.encoding import iri_to_uri, force_unicode
|
||||||
from django.utils.functional import memoize
|
from django.utils.functional import memoize
|
||||||
import re
|
import re
|
||||||
|
|
||||||
|
@ -101,7 +101,7 @@ class MatchChecker(object):
|
||||||
# First we need to figure out whether it's a named or unnamed group.
|
# First we need to figure out whether it's a named or unnamed group.
|
||||||
#
|
#
|
||||||
grouped = match_obj.group(1)
|
grouped = match_obj.group(1)
|
||||||
m = re.search(r'^\?P<(\w+)>(.*?)$', grouped)
|
m = re.search(r'^\?P<(\w+)>(.*?)$', grouped, re.UNICODE)
|
||||||
if m: # If this was a named group...
|
if m: # If this was a named group...
|
||||||
# m.group(1) is the name of the group
|
# m.group(1) is the name of the group
|
||||||
# m.group(2) is the regex.
|
# m.group(2) is the regex.
|
||||||
|
@ -127,9 +127,9 @@ class MatchChecker(object):
|
||||||
test_regex = grouped
|
test_regex = grouped
|
||||||
# Note we're using re.match here on purpose because the start of
|
# Note we're using re.match here on purpose because the start of
|
||||||
# to string needs to match.
|
# to string needs to match.
|
||||||
if not re.match(test_regex + '$', str(value)): # TODO: Unicode?
|
if not re.match(test_regex + '$', force_unicode(value), re.UNICODE):
|
||||||
raise NoReverseMatch("Value %r didn't match regular expression %r" % (value, test_regex))
|
raise NoReverseMatch("Value %r didn't match regular expression %r" % (value, test_regex))
|
||||||
return str(value) # TODO: Unicode?
|
return force_unicode(value)
|
||||||
|
|
||||||
class RegexURLPattern(object):
|
class RegexURLPattern(object):
|
||||||
def __init__(self, regex, callback, default_args=None, name=None):
|
def __init__(self, regex, callback, default_args=None, name=None):
|
||||||
|
@ -137,7 +137,7 @@ class RegexURLPattern(object):
|
||||||
# callback is either a string like 'foo.views.news.stories.story_detail'
|
# callback is either a string like 'foo.views.news.stories.story_detail'
|
||||||
# which represents the path to a module and a view function name, or a
|
# which represents the path to a module and a view function name, or a
|
||||||
# callable object (view).
|
# callable object (view).
|
||||||
self.regex = re.compile(regex)
|
self.regex = re.compile(regex, re.UNICODE)
|
||||||
if callable(callback):
|
if callable(callback):
|
||||||
self._callback = callback
|
self._callback = callback
|
||||||
else:
|
else:
|
||||||
|
@ -201,7 +201,7 @@ class RegexURLResolver(object):
|
||||||
def __init__(self, regex, urlconf_name, default_kwargs=None):
|
def __init__(self, regex, urlconf_name, default_kwargs=None):
|
||||||
# regex is a string representing a regular expression.
|
# regex is a string representing a regular expression.
|
||||||
# urlconf_name is a string representing the module containing urlconfs.
|
# urlconf_name is a string representing the module containing urlconfs.
|
||||||
self.regex = re.compile(regex)
|
self.regex = re.compile(regex, re.UNICODE)
|
||||||
self.urlconf_name = urlconf_name
|
self.urlconf_name = urlconf_name
|
||||||
self.callback = None
|
self.callback = None
|
||||||
self.default_kwargs = default_kwargs or {}
|
self.default_kwargs = default_kwargs or {}
|
||||||
|
|
|
@ -512,7 +512,7 @@ filter_raw_string = r"""
|
||||||
)?
|
)?
|
||||||
)""" % {
|
)""" % {
|
||||||
'str': r"""[^"\\]*(?:\\.[^"\\]*)*""",
|
'str': r"""[^"\\]*(?:\\.[^"\\]*)*""",
|
||||||
'var_chars': "A-Za-z0-9\_\." ,
|
'var_chars': "\w\." ,
|
||||||
'filter_sep': re.escape(FILTER_SEPARATOR),
|
'filter_sep': re.escape(FILTER_SEPARATOR),
|
||||||
'arg_sep': re.escape(FILTER_ARGUMENT_SEPARATOR),
|
'arg_sep': re.escape(FILTER_ARGUMENT_SEPARATOR),
|
||||||
'i18n_open' : re.escape("_("),
|
'i18n_open' : re.escape("_("),
|
||||||
|
@ -520,7 +520,7 @@ filter_raw_string = r"""
|
||||||
}
|
}
|
||||||
|
|
||||||
filter_raw_string = filter_raw_string.replace("\n", "").replace(" ", "")
|
filter_raw_string = filter_raw_string.replace("\n", "").replace(" ", "")
|
||||||
filter_re = re.compile(filter_raw_string)
|
filter_re = re.compile(filter_raw_string, re.UNICODE)
|
||||||
|
|
||||||
class FilterExpression(object):
|
class FilterExpression(object):
|
||||||
"""
|
"""
|
||||||
|
|
|
@ -735,7 +735,8 @@ class Templates(unittest.TestCase):
|
||||||
'url02' : ('{% url regressiontests.templates.views.client_action client.id, action="update" %}', {'client': {'id': 1}}, '/url_tag/client/1/update/'),
|
'url02' : ('{% url regressiontests.templates.views.client_action client.id, action="update" %}', {'client': {'id': 1}}, '/url_tag/client/1/update/'),
|
||||||
'url03' : ('{% url regressiontests.templates.views.index %}', {}, '/url_tag/'),
|
'url03' : ('{% url regressiontests.templates.views.index %}', {}, '/url_tag/'),
|
||||||
'url04' : ('{% url named.client client.id %}', {'client': {'id': 1}}, '/url_tag/named-client/1/'),
|
'url04' : ('{% url named.client client.id %}', {'client': {'id': 1}}, '/url_tag/named-client/1/'),
|
||||||
'url05' : (u'{% url метка_оператора 1 %}', {}, '/url_tag/unicode/1/'),
|
'url05' : (u'{% url метка_оператора v %}', {'v': u'Ω'},
|
||||||
|
'/url_tag/%D0%AE%D0%BD%D0%B8%D0%BA%D0%BE%D0%B4/%CE%A9/'),
|
||||||
|
|
||||||
# Failures
|
# Failures
|
||||||
'url-fail01' : ('{% url %}', {}, template.TemplateSyntaxError),
|
'url-fail01' : ('{% url %}', {}, template.TemplateSyntaxError),
|
||||||
|
|
|
@ -9,5 +9,7 @@ urlpatterns = patterns('',
|
||||||
(r'^client/(\d+)/$', views.client),
|
(r'^client/(\d+)/$', views.client),
|
||||||
(r'^client/(\d+)/(?P<action>[^/]+)/$', views.client_action),
|
(r'^client/(\d+)/(?P<action>[^/]+)/$', views.client_action),
|
||||||
url(r'^named-client/(\d+)/$', views.client, name="named.client"),
|
url(r'^named-client/(\d+)/$', views.client, name="named.client"),
|
||||||
url(r'^unicode/(\d+)/$', views.client, name=u"метка_оператора"),
|
|
||||||
|
# Unicode strings are permitted everywhere.
|
||||||
|
url(ur'^Юникод/(\w+)/$', views.client, name=u"метка_оператора"),
|
||||||
)
|
)
|
||||||
|
|
Loading…
Reference in New Issue