mirror of
				https://github.com/django/django.git
				synced 2025-10-31 01:25:32 +00:00 
			
		
		
		
	Merge branch 'url-tag-asvar'
git-svn-id: http://code.djangoproject.com/svn/django/trunk@8716 bcc190cf-cafb-0310-a4f2-bffc1f526a37
This commit is contained in:
		| @@ -351,22 +351,40 @@ class TemplateTagNode(Node): | ||||
|         return self.mapping.get(self.tagtype, '') | ||||
|  | ||||
| class URLNode(Node): | ||||
|     def __init__(self, view_name, args, kwargs): | ||||
|     def __init__(self, view_name, args, kwargs, asvar): | ||||
|         self.view_name = view_name | ||||
|         self.args = args | ||||
|         self.kwargs = kwargs | ||||
|         self.asvar = asvar | ||||
|  | ||||
|     def render(self, context): | ||||
|         from django.core.urlresolvers import reverse, NoReverseMatch | ||||
|         args = [arg.resolve(context) for arg in self.args] | ||||
|         kwargs = dict([(smart_str(k,'ascii'), v.resolve(context)) | ||||
|                        for k, v in self.kwargs.items()]) | ||||
|          | ||||
|          | ||||
|         # Try to look up the URL twice: once given the view name, and again | ||||
|         # relative to what we guess is the "main" app. If they both fail,  | ||||
|         # re-raise the NoReverseMatch unless we're using the  | ||||
|         # {% url ... as var %} construct in which cause return nothing. | ||||
|         url = '' | ||||
|         try: | ||||
|             return reverse(self.view_name, args=args, kwargs=kwargs) | ||||
|             url = reverse(self.view_name, args=args, kwargs=kwargs) | ||||
|         except NoReverseMatch: | ||||
|             project_name = settings.SETTINGS_MODULE.split('.')[0] | ||||
|             return reverse(project_name + '.' + self.view_name, | ||||
|             try: | ||||
|                 url = reverse(project_name + '.' + self.view_name, | ||||
|                               args=args, kwargs=kwargs) | ||||
|             except NoReverseMatch: | ||||
|                 if self.asvar is None: | ||||
|                     raise | ||||
|                      | ||||
|         if self.asvar: | ||||
|             context[self.asvar] = url | ||||
|             return '' | ||||
|         else: | ||||
|             return url | ||||
|  | ||||
| class WidthRatioNode(Node): | ||||
|     def __init__(self, val_expr, max_expr, max_width): | ||||
| @@ -1041,21 +1059,30 @@ def url(parser, token): | ||||
|  | ||||
|     The URL will look like ``/clients/client/123/``. | ||||
|     """ | ||||
|     bits = token.contents.split(' ', 2) | ||||
|     bits = token.contents.split(' ') | ||||
|     if len(bits) < 2: | ||||
|         raise TemplateSyntaxError("'%s' takes at least one argument" | ||||
|                                   " (path to a view)" % bits[0]) | ||||
|     viewname = bits[1] | ||||
|     args = [] | ||||
|     kwargs = {} | ||||
|     asvar = None | ||||
|          | ||||
|     if len(bits) > 2: | ||||
|         for arg in bits[2].split(','): | ||||
|         bits = iter(bits[2:]) | ||||
|         for bit in bits: | ||||
|             if bit == 'as': | ||||
|                 asvar = bits.next() | ||||
|                 break | ||||
|             else: | ||||
|                 for arg in bit.split(","): | ||||
|                     if '=' in arg: | ||||
|                         k, v = arg.split('=', 1) | ||||
|                         k = k.strip() | ||||
|                         kwargs[k] = parser.compile_filter(v) | ||||
|             else: | ||||
|                     elif arg: | ||||
|                         args.append(parser.compile_filter(arg)) | ||||
|     return URLNode(bits[1], args, kwargs) | ||||
|     return URLNode(viewname, args, kwargs, asvar) | ||||
| url = register.tag(url) | ||||
|  | ||||
| #@register.tag | ||||
|   | ||||
| @@ -675,6 +675,29 @@ The template tag will output the string ``/clients/client/123/``. | ||||
| <naming-url-patterns>`, you can refer to the name of the pattern in the ``url`` | ||||
| tag instead of using the path to the view. | ||||
|  | ||||
| Note that if the URL you're reversing doesn't exist, you'll get an | ||||
| :exc:`NoReverseMatch` exception raised, which will cause your site to display an | ||||
| error page. | ||||
|  | ||||
| **New in development verson:** If you'd like to retrieve a URL without displaying it, | ||||
| you can use a slightly different call: | ||||
|  | ||||
| .. code-block:: html+django | ||||
|  | ||||
|     {% url path.to.view arg, arg2 as the_url %} | ||||
|      | ||||
|     <a href="{{ the_url }}">I'm linking to {{ the_url }}</a> | ||||
|      | ||||
| This ``{% url ... as var %}`` syntax will *not* cause an error if the view is | ||||
| missing. In practice you'll use this to link to views that are optional: | ||||
|  | ||||
| .. code-block:: html+django | ||||
|  | ||||
|     {% url path.to.view as the_url %} | ||||
|     {% if the_url %} | ||||
|       <a href="{{ the_url }}">Link to optional stuff</a> | ||||
|     {% endif %} | ||||
|  | ||||
| .. templatetag:: widthratio | ||||
|  | ||||
| widthratio | ||||
|   | ||||
| @@ -896,6 +896,11 @@ class Templates(unittest.TestCase): | ||||
|             'url-fail02': ('{% url no_such_view %}', {}, urlresolvers.NoReverseMatch), | ||||
|             'url-fail03': ('{% url regressiontests.templates.views.client %}', {}, urlresolvers.NoReverseMatch), | ||||
|  | ||||
|             # {% url ... as var %} | ||||
|             'url-asvar01': ('{% url regressiontests.templates.views.index as url %}', {}, ''), | ||||
|             'url-asvar02': ('{% url regressiontests.templates.views.index as url %}{{ url }}', {}, '/url_tag/'), | ||||
|             'url-asvar03': ('{% url no_such_view as url %}{{ url }}', {}, ''), | ||||
|  | ||||
|             ### CACHE TAG ###################################################### | ||||
|             'cache01': ('{% load cache %}{% cache -1 test %}cache01{% endcache %}', {}, 'cache01'), | ||||
|             'cache02': ('{% load cache %}{% cache -1 test %}cache02{% endcache %}', {}, 'cache02'), | ||||
|   | ||||
		Reference in New Issue
	
	Block a user