Skip to content

Commit

Permalink
Merge pull request #1649 from Pylons/1.6-fix-jsonp
Browse files Browse the repository at this point in the history
backport jsonp fixes from master
  • Loading branch information
mmerickel committed Apr 29, 2015
2 parents e2c74ab + 0d81596 commit f7c7aa2
Show file tree
Hide file tree
Showing 3 changed files with 26 additions and 4 deletions.
11 changes: 11 additions & 0 deletions CHANGES.txt
Original file line number Diff line number Diff line change
@@ -1,3 +1,14 @@
unreleased
==========

- Further fix the JSONP renderer by prefixing the returned content with
a comment. This should mitigate attacks from Flash (See CVE-2014-4671).
See https://github.com/Pylons/pyramid/pull/1649

- Allow periods and brackets (``[]``) in the JSONP callback. The original
fix was overly-restrictive and broke Angular.
See https://github.com/Pylons/pyramid/pull/1649

1.6 (2015-04-14)
================

Expand Down
7 changes: 4 additions & 3 deletions pyramid/renderers.py
Original file line number Diff line number Diff line change
Expand Up @@ -308,7 +308,7 @@ def default(obj):

json_renderer_factory = JSON() # bw compat

JSONP_VALID_CALLBACK = re.compile(r"^[a-zA-Z_$][0-9a-zA-Z_$]+$")
JSONP_VALID_CALLBACK = re.compile(r"^[$a-z_][$0-9a-z_\.\[\]]+[^.]$", re.I)

class JSONP(JSON):
""" `JSONP <http://en.wikipedia.org/wiki/JSONP>`_ renderer factory helper
Expand Down Expand Up @@ -393,10 +393,11 @@ def _render(value, system):

if callback is not None:
if not JSONP_VALID_CALLBACK.match(callback):
raise HTTPBadRequest('Invalid JSONP callback function name.')
raise HTTPBadRequest(
'Invalid JSONP callback function name.')

ct = 'application/javascript'
body = '%s(%s);' % (callback, val)
body = '/**/{0}({1});'.format(callback, val)
response = request.response
if response.content_type == response.default_content_type:
response.content_type = ct
Expand Down
12 changes: 11 additions & 1 deletion pyramid/tests/test_renderers.py
Original file line number Diff line number Diff line change
Expand Up @@ -669,7 +669,17 @@ def test_render_to_jsonp(self):
request = testing.DummyRequest()
request.GET['callback'] = 'callback'
result = renderer({'a':'1'}, {'request':request})
self.assertEqual(result, 'callback({"a": "1"});')
self.assertEqual(result, '/**/callback({"a": "1"});')
self.assertEqual(request.response.content_type,
'application/javascript')

def test_render_to_jsonp_with_dot(self):
renderer_factory = self._makeOne()
renderer = renderer_factory(None)
request = testing.DummyRequest()
request.GET['callback'] = 'angular.callbacks._0'
result = renderer({'a':'1'}, {'request':request})
self.assertEqual(result, '/**/angular.callbacks._0({"a": "1"});')
self.assertEqual(request.response.content_type,
'application/javascript')

Expand Down

0 comments on commit f7c7aa2

Please sign in to comment.