Commit 636c45fc authored by Christopher Medrela's avatar Christopher Medrela
Browse files

Fixed #19890 -- ifchanged templatetag rendered its content twice

The content of ifchanged template tag was rendered twice: first time, to
compare it with the previous value and the second time, to return the
rendered output.
parent 8503120c
Loading
Loading
Loading
Loading
+3 −2
Original line number Diff line number Diff line
@@ -223,6 +223,7 @@ class IfChangedNode(Node):
        if self not in state_frame:
            state_frame[self] = None

        nodelist_true_output = None
        try:
            if self._varlist:
                # Consider multiple parameters.  This automatically behaves
@@ -230,13 +231,13 @@ class IfChangedNode(Node):
                compare_to = [var.resolve(context, True) for var in self._varlist]
            else:
                # The "{% ifchanged %}" syntax (without any variables) compares the rendered output.
                compare_to = self.nodelist_true.render(context)
                compare_to = nodelist_true_output = self.nodelist_true.render(context)
        except VariableDoesNotExist:
            compare_to = None

        if compare_to != state_frame[self]:
            state_frame[self] = compare_to
            return self.nodelist_true.render(context)
            return nodelist_true_output or self.nodelist_true.render(context)  # render true block if not already rendered
        elif self.nodelist_false:
            return self.nodelist_false.render(context)
        return ''
+12 −0
Original line number Diff line number Diff line
@@ -441,6 +441,18 @@ class Templates(TestCase):
        output1 = template.render(Context({'foo': range(3), 'get_value': lambda: next(gen1)}))
        self.assertEqual(output1, '[0,1,2,3]', 'Expected [0,1,2,3] in first template, got {0}'.format(output1))

    def test_ifchanged_render_once(self):
        """ Test for ticket #19890. The content of ifchanged template tag was
        rendered twice."""

        template = Template('{% ifchanged %}{{ gen.next }}{% endifchanged %}')
        def gen():
            for i in xrange(1,10):
                yield 'iteration no %d' % i

        output = template.render(Context({'gen': gen()}))
        self.assertEqual(output, 'iteration no 1')

    def test_templates(self):
        template_tests = self.get_template_tests()
        filter_tests = filters.get_filter_tests()