Fix certificate's course title for xss tags injection.

This fix would enable course author to selectively add
basic html tags to course title, while removing any
other injected tags that could execute javascript.

LEARNER-3491
This commit is contained in:
Adeel Khan
2017-12-11 16:25:47 +05:00
parent 257de20d95
commit 5773001f75
2 changed files with 40 additions and 1 deletions

View File

@@ -3,6 +3,8 @@ Utilities for use in Mako markup.
"""
import markupsafe
import bleach
from mako.filters import decode
# Text() can be used to declare a string as plain text, as HTML() is used
# for HTML. It simply wraps markupsafe's escape, which will HTML-escape if
@@ -31,3 +33,24 @@ def HTML(html): # pylint: disable=invalid-name
"""
return markupsafe.Markup(html)
def strip_all_tags_but_br(string_to_strip):
"""
Strips all tags from a string except <br/>
Usage:
<%page expression_filter="h"/>
<%!
from openedx.core.djangolib.markup import strip_all_tags_but_br
%>
${accomplishment_course_title | n, strip_all_tags_but_br}
"""
if string_to_strip is None:
string_to_strip = ""
string_to_strip = decode.utf8(string_to_strip)
string_to_strip = bleach.clean(string_to_strip, tags=['br'], strip=True)
return string_to_strip

View File

@@ -11,7 +11,7 @@ from django.utils.translation import ungettext
from mako.template import Template
from nose.plugins.attrib import attr
from openedx.core.djangolib.markup import HTML, Text
from openedx.core.djangolib.markup import HTML, Text, strip_all_tags_but_br
@attr(shard=2)
@@ -74,3 +74,19 @@ class FormatHtmlTest(unittest.TestCase):
for i in [1, 2]:
out = Text(ungettext("1 & {}", "2 & {}", i)).format(HTML("<>"))
self.assertEqual(out, "{} &amp; <>".format(i))
def test_strip_all_tags_but_br_filter(self):
""" Verify filter removes every tags except br """
template = Template(
"""
<%page expression_filter="h"/>
<%!
from openedx.core.djangolib.markup import strip_all_tags_but_br
%>
${" course <br> title <script>" | n, strip_all_tags_but_br}
"""
)
rendered_template = template.render()
self.assertIn('<br>', rendered_template)
self.assertNotIn('<script>', rendered_template)