Code

Ticket #17675: 17675.2.patch

File 17675.2.patch, 4.7 KB (added by aaugustin, 2 years ago)
  • tests/regressiontests/templates/tests.py

     
    88    # before importing 'template'. 
    99    settings.configure() 
    1010 
    11 from datetime import datetime, timedelta 
     11from datetime import date, datetime, timedelta 
    1212import time 
    1313import os 
    1414import sys 
     
    13761376                          '{% endfor %},' 
    13771377                          '{% endfor %}', 
    13781378                          {}, ''), 
     1379 
     1380            # Regression tests for #17675 
     1381            # The date template filter has expects_localtime = True 
     1382            'regroup03': ('{% regroup data by at|date:"m" as grouped %}' 
     1383                          '{% for group in grouped %}' 
     1384                          '{{ group.grouper }}:' 
     1385                          '{% for item in group.list %}' 
     1386                          '{{ item.at|date:"d" }}' 
     1387                          '{% endfor %},' 
     1388                          '{% endfor %}', 
     1389                          {'data': [{'at': date(2012, 2, 14)}, 
     1390                                    {'at': date(2012, 2, 28)}, 
     1391                                    {'at': date(2012, 7, 4)}]}, 
     1392                          '02:1428,07:04,'), 
     1393            # The join template filter has needs_autoescape = True 
     1394            'regroup04': ('{% regroup data by bar|join:"" as grouped %}' 
     1395                          '{% for group in grouped %}' 
     1396                          '{{ group.grouper }}:' 
     1397                          '{% for item in group.list %}' 
     1398                          '{{ item.foo|first }}' 
     1399                          '{% endfor %},' 
     1400                          '{% endfor %}', 
     1401                          {'data': [{'foo': 'x', 'bar': ['ab', 'c']}, 
     1402                                    {'foo': 'y', 'bar': ['a', 'bc']}, 
     1403                                    {'foo': 'z', 'bar': ['a', 'd']}]}, 
     1404                          'abc:xy,ad:z,'), 
     1405 
    13791406            ### SSI TAG ######################################################## 
    13801407 
    13811408            # Test normal behavior 
  • django/template/defaulttags.py

     
    1010    TemplateSyntaxError, VariableDoesNotExist, InvalidTemplateLibrary, 
    1111    BLOCK_TAG_START, BLOCK_TAG_END, VARIABLE_TAG_START, VARIABLE_TAG_END, 
    1212    SINGLE_BRACE_START, SINGLE_BRACE_END, COMMENT_TAG_START, COMMENT_TAG_END, 
    13     get_library, token_kwargs, kwarg_re) 
     13    VARIABLE_ATTRIBUTE_SEPARATOR, get_library, token_kwargs, kwarg_re) 
    1414from django.template.smartif import IfParser, Literal 
    1515from django.template.defaultfilters import date 
    1616from django.utils.encoding import smart_str, smart_unicode 
     
    287287        self.target, self.expression = target, expression 
    288288        self.var_name = var_name 
    289289 
     290    def resolve_expression(self, obj, context): 
     291        # This method is called for each object in self.target. See regroup() 
     292        # for the reason why we temporarily put the object in the context. 
     293        context[self.var_name] = obj 
     294        return self.expression.resolve(context, True) 
     295 
    290296    def render(self, context): 
    291297        obj_list = self.target.resolve(context, True) 
    292298        if obj_list == None: 
     
    298304        context[self.var_name] = [ 
    299305            {'grouper': key, 'list': list(val)} 
    300306            for key, val in 
    301             groupby(obj_list, lambda v, f=self.expression.resolve: f(v, True)) 
     307            groupby(obj_list, lambda obj: self.resolve_expression(obj, context)) 
    302308        ] 
    303309        return '' 
    304310 
     
    11121118    if lastbits_reversed[1][::-1] != 'as': 
    11131119        raise TemplateSyntaxError("next-to-last argument to 'regroup' tag must" 
    11141120                                  " be 'as'") 
    1115  
    1116     expression = parser.compile_filter(lastbits_reversed[2][::-1]) 
    1117  
    11181121    var_name = lastbits_reversed[0][::-1] 
     1122    # RegroupNode will take each item in 'target', put it in the context under 
     1123    # 'var_name', evaluate 'var_name'.'expression' in the current context, and 
     1124    # group by the resulting value. After all items are processed, it will 
     1125    # save the final result in the context under 'var_name', thus clearing the 
     1126    # temporary values. This hack is necessary because the template engine 
     1127    # doesn't provide a context-aware equivalent of Python's getattr. 
     1128    expression = parser.compile_filter(var_name + 
     1129                                       VARIABLE_ATTRIBUTE_SEPARATOR + 
     1130                                       lastbits_reversed[2][::-1]) 
    11191131    return RegroupNode(target, expression, var_name) 
    11201132 
    11211133@register.tag