Browse Source

Refs #23269 -- Removed the removetags template tag and related functions per deprecation timeline.

Tim Graham 9 years ago
parent
commit
222d063301

+ 1 - 8
django/template/defaultfilters.py

@@ -13,7 +13,7 @@ from django.utils.dateformat import format, time_format
 from django.utils.encoding import force_text, iri_to_uri
 from django.utils.html import (
     avoid_wrapping, conditional_escape, escape, escapejs, linebreaks,
-    remove_tags, strip_tags, urlize as _urlize,
+    strip_tags, urlize as _urlize,
 )
 from django.utils.http import urlquote
 from django.utils.safestring import SafeData, mark_for_escaping, mark_safe
@@ -500,13 +500,6 @@ def safeseq(value):
     return [mark_safe(force_text(obj)) for obj in value]
 
 
-@register.filter(is_safe=True)
-@stringfilter
-def removetags(value, tags):
-    """Removes a space separated list of [X]HTML tags from the output."""
-    return remove_tags(value, tags)
-
-
 @register.filter(is_safe=True)
 @stringfilter
 def striptags(value):

+ 0 - 29
django/utils/html.py

@@ -3,10 +3,8 @@
 from __future__ import unicode_literals
 
 import re
-import warnings
 
 from django.utils import six
-from django.utils.deprecation import RemovedInDjango110Warning
 from django.utils.encoding import force_str, force_text
 from django.utils.functional import allow_lazy
 from django.utils.http import RFC3986_GENDELIMS, RFC3986_SUBDELIMS
@@ -184,39 +182,12 @@ def strip_tags(value):
 strip_tags = allow_lazy(strip_tags)
 
 
-def remove_tags(html, tags):
-    """Returns the given HTML with given tags removed."""
-    warnings.warn(
-        "django.utils.html.remove_tags() and the removetags template filter "
-        "are deprecated. Consider using the bleach library instead.",
-        RemovedInDjango110Warning, stacklevel=3
-    )
-    tags = [re.escape(tag) for tag in tags.split()]
-    tags_re = '(%s)' % '|'.join(tags)
-    starttag_re = re.compile(r'<%s(/?>|(\s+[^>]*>))' % tags_re, re.U)
-    endtag_re = re.compile('</%s>' % tags_re)
-    html = starttag_re.sub('', html)
-    html = endtag_re.sub('', html)
-    return html
-remove_tags = allow_lazy(remove_tags, six.text_type)
-
-
 def strip_spaces_between_tags(value):
     """Returns the given HTML with spaces between tags removed."""
     return re.sub(r'>\s+<', '><', force_text(value))
 strip_spaces_between_tags = allow_lazy(strip_spaces_between_tags, six.text_type)
 
 
-def strip_entities(value):
-    """Returns the given HTML with all entities (&something;) stripped."""
-    warnings.warn(
-        "django.utils.html.strip_entities() is deprecated.",
-        RemovedInDjango110Warning, stacklevel=2
-    )
-    return re.sub(r'&(?:\w+|#\d+);', '', force_text(value))
-strip_entities = allow_lazy(strip_entities, six.text_type)
-
-
 def smart_urlquote(url):
     "Quotes a URL if it isn't already quoted."
     def unquote_quote(segment):

+ 0 - 38
docs/ref/templates/builtins.txt

@@ -1866,44 +1866,6 @@ For example::
 
 If ``value`` is the list ``['a', 'b', 'c', 'd']``, the output could be ``"b"``.
 
-.. templatefilter:: removetags
-
-removetags
-^^^^^^^^^^
-
-.. deprecated:: 1.8
-
-    ``removetags`` cannot guarantee HTML safe output and has been deprecated due
-    to security concerns. Consider using `bleach`_ instead.
-
-.. _bleach: http://bleach.readthedocs.org/en/latest/
-
-Removes a space-separated list of [X]HTML tags from the output.
-
-For example::
-
-    {{ value|removetags:"b span" }}
-
-If ``value`` is ``"<b>Joel</b> <button>is</button> a <span>slug</span>"`` the
-unescaped output will be ``"Joel <button>is</button> a slug"``.
-
-Note that this filter is case-sensitive.
-
-If ``value`` is ``"<B>Joel</B> <button>is</button> a <span>slug</span>"`` the
-unescaped output will be ``"<B>Joel</B> <button>is</button> a slug"``.
-
-.. admonition:: No safety guarantee
-
-    Note that ``removetags`` doesn't give any guarantee about its output being
-    HTML safe. In particular, it doesn't work recursively, so an input like
-    ``"<sc<script>ript>alert('XSS')</sc</script>ript>"`` won't be safe even if
-    you apply ``|removetags:"script"``. So if the input is user provided,
-    **NEVER** apply the ``safe`` filter to a ``removetags`` output. If you are
-    looking for something more robust, you can use the ``bleach`` Python
-    library, notably its `clean`_ method.
-
-.. _clean: http://bleach.readthedocs.org/en/latest/clean.html
-
 .. templatefilter:: rjust
 
 rjust

+ 4 - 33
docs/ref/utils.txt

@@ -621,6 +621,8 @@ escaping HTML.
     through :func:`conditional_escape` which (ultimately) calls
     :func:`~django.utils.encoding.force_text` on the values.
 
+    .. _str.format: https://docs.python.org/library/stdtypes.html#str.format
+
 .. function:: format_html_join(sep, format_string, args_generator)
 
     A wrapper of :func:`format_html`, for the common case of a group of
@@ -650,39 +652,8 @@ escaping HTML.
     If ``value`` is ``"<b>Joel</b> <button>is</button> a <span>slug</span>"``
     the return value will be ``"Joel is a slug"``.
 
-    If you are looking for a more robust solution, take a look at the `bleach`_
-    Python library.
-
-.. function:: remove_tags(value, tags)
-
-    .. deprecated:: 1.8
-
-        ``remove_tags()`` cannot guarantee HTML safe output and has been
-        deprecated due to security concerns. Consider using `bleach`_ instead.
-
-    Removes a space-separated list of [X]HTML tag names from the output.
-
-    Absolutely NO guarantee is provided about the resulting string being HTML
-    safe. In particular, it doesn't work recursively, so the output of
-    ``remove_tags("<sc<script>ript>alert('XSS')</sc</script>ript>", "script")``
-    won't remove the "nested" script tags. So if the ``value`` is untrusted,
-    NEVER mark safe the result of a ``remove_tags()`` call without escaping it
-    first, for example with :func:`~django.utils.html.escape`.
-
-    For example::
-
-        remove_tags(value, "b span")
-
-    If ``value`` is ``"<b>Joel</b> <button>is</button> a <span>slug</span>"``
-    the return value will be ``"Joel <button>is</button> a slug"``.
-
-    Note that this filter is case-sensitive.
-
-    If ``value`` is ``"<B>Joel</B> <button>is</button> a <span>slug</span>"``
-    the return value will be ``"<B>Joel</B> <button>is</button> a slug"``.
-
-.. _str.format: https://docs.python.org/library/stdtypes.html#str.format
-.. _bleach: https://pypi.python.org/pypi/bleach
+    If you are looking for a more robust solution, take a look at the `bleach
+    <https://pypi.python.org/pypi/bleach>`_ Python library.
 
 .. function:: html_safe()
 

+ 1 - 1
docs/releases/1.5.txt

@@ -671,7 +671,7 @@ Miscellaneous
 
 * The ``slugify`` template filter is now available as a standard python
   function at :func:`django.utils.text.slugify`. Similarly, ``remove_tags`` is
-  available at :func:`django.utils.html.remove_tags`.
+  available at ``django.utils.html.remove_tags()``.
 
 * Uploaded files are no longer created as executable by default. If you need
   them to be executable change :setting:`FILE_UPLOAD_PERMISSIONS` to your

+ 0 - 49
tests/template_tests/filter_tests/test_removetags.py

@@ -1,49 +0,0 @@
-from django.template.defaultfilters import removetags
-from django.test import SimpleTestCase, ignore_warnings
-from django.utils.deprecation import RemovedInDjango110Warning
-from django.utils.safestring import mark_safe
-
-from ..utils import setup
-
-
-@ignore_warnings(category=RemovedInDjango110Warning)
-class RemovetagsTests(SimpleTestCase):
-
-    @setup({'removetags01': '{{ a|removetags:"a b" }} {{ b|removetags:"a b" }}'})
-    def test_removetags01(self):
-        output = self.engine.render_to_string(
-            'removetags01',
-            {
-                'a': '<a>x</a> <p><b>y</b></p>',
-                'b': mark_safe('<a>x</a> <p><b>y</b></p>'),
-            },
-        )
-        self.assertEqual(output, 'x &lt;p&gt;y&lt;/p&gt; x <p>y</p>')
-
-    @setup({'removetags02':
-        '{% autoescape off %}{{ a|removetags:"a b" }} {{ b|removetags:"a b" }}{% endautoescape %}'})
-    def test_removetags02(self):
-        output = self.engine.render_to_string(
-            'removetags02',
-            {
-                'a': '<a>x</a> <p><b>y</b></p>',
-                'b': mark_safe('<a>x</a> <p><b>y</b></p>'),
-            },
-        )
-        self.assertEqual(output, 'x <p>y</p> x <p>y</p>')
-
-
-@ignore_warnings(category=RemovedInDjango110Warning)
-class FunctionTests(SimpleTestCase):
-
-    def test_removetags(self):
-        self.assertEqual(
-            removetags(
-                'some <b>html</b> with <script>alert("You smell")</script> disallowed <img /> tags',
-                'script img',
-            ),
-            'some <b>html</b> with alert("You smell") disallowed  tags',
-        )
-
-    def test_non_string_input(self):
-        self.assertEqual(removetags(123, 'a'), '123')

+ 1 - 31
tests/utils_tests/test_html.py

@@ -4,10 +4,9 @@ from __future__ import unicode_literals
 import os
 from datetime import datetime
 
-from django.test import SimpleTestCase, ignore_warnings
+from django.test import SimpleTestCase
 from django.utils import html, safestring, six
 from django.utils._os import upath
-from django.utils.deprecation import RemovedInDjango110Warning
 from django.utils.encoding import force_text
 
 
@@ -123,25 +122,6 @@ class TestUtilsHtml(SimpleTestCase):
         for value, output in items:
             self.check_output(f, value, output)
 
-    @ignore_warnings(category=RemovedInDjango110Warning)
-    def test_strip_entities(self):
-        f = html.strip_entities
-        # Strings that should come out untouched.
-        values = ("&", "&a", "&a", "a&#a")
-        for value in values:
-            self.check_output(f, value)
-        # Valid entities that should be stripped from the patterns.
-        entities = ("&#1;", "&#12;", "&a;", "&fdasdfasdfasdf;")
-        patterns = (
-            ("asdf %(entity)s ", "asdf  "),
-            ("%(entity)s%(entity)s", ""),
-            ("&%(entity)s%(entity)s", "&"),
-            ("%(entity)s3", "3"),
-        )
-        for entity in entities:
-            for in_pattern, output in patterns:
-                self.check_output(f, in_pattern % {'entity': entity}, output)
-
     def test_escapejs(self):
         f = html.escapejs
         items = (
@@ -160,16 +140,6 @@ class TestUtilsHtml(SimpleTestCase):
         for value, output in items:
             self.check_output(f, value, output)
 
-    @ignore_warnings(category=RemovedInDjango110Warning)
-    def test_remove_tags(self):
-        f = html.remove_tags
-        items = (
-            ("<b><i>Yes</i></b>", "b i", "Yes"),
-            ("<a>x</a> <p><b>y</b></p>", "a b", "x <p>y</p>"),
-        )
-        for value, tags, output in items:
-            self.assertEqual(f(value, tags), output)
-
     def test_smart_urlquote(self):
         quote = html.smart_urlquote
         # Ensure that IDNs are properly quoted