From 1bc768d3ab65bcf5dc558f041362ba46e7ce79ae Mon Sep 17 00:00:00 2001 From: nitinbhojwani Date: Sat, 26 Oct 2019 15:40:04 -0400 Subject: [PATCH 1/4] Add json_request decorator and test cases --- jsonview/decorators.py | 28 ++++++++++++ jsonview/tests.py | 100 ++++++++++++++++++++++++++++++++++++++++- 2 files changed, 127 insertions(+), 1 deletion(-) diff --git a/jsonview/decorators.py b/jsonview/decorators.py index bd224ed..f40234c 100644 --- a/jsonview/decorators.py +++ b/jsonview/decorators.py @@ -165,3 +165,31 @@ def _wrapped(request, *a, **kw): return decorator(args[0]) else: return decorator + + +def json_request(*args, **kwargs): + assume_json = bool(kwargs.get('assume_json', True)) + + def decorator(f): + @wraps(f) + def _wrapped(request, *a, **kw): + request.data = {} + if assume_json or request.META.get('CONTENT_TYPE') == JSON: + try: + if isinstance(request.body, bytes): + request.data = json.loads(request.body.decode('ascii')) + else: + request.data = json.loads(request.body) + except: + pass + elif request.method == 'GET': + request.data = request.GET.dict() + elif request.method == 'POST': + request.data = request.POST.dict() + return f(request, *a, **kw) + return _wrapped + + if len(args) == 1 and callable(args[0]): + return decorator(args[0]) + else: + return decorator diff --git a/jsonview/tests.py b/jsonview/tests.py index 933d0b8..4bfb2b1 100644 --- a/jsonview/tests.py +++ b/jsonview/tests.py @@ -17,7 +17,7 @@ import mock -from .decorators import json_view +from .decorators import json_view, json_request from .exceptions import BadRequest from .views import JsonView @@ -396,3 +396,101 @@ def get(self, request): eq_(JSON, res['content-type']) data = json.loads(res.content.decode('utf-8')) eq_('bar', data['foo']) + + +class JsonRequestTests(TestCase): + def test_application_json(self): + data = { + 'foo': 'bar', + 'baz': 'qux', + 'quz': [{'foo': 'bar'}], + } + + @json_request + def temp(req): + return req.data + + res = temp(rf.post( + '/', + data=json.dumps(data), + content_type='application/json' + )) + eq_(res, data) + + def test_get_requests(self): + data = { + 'foo': 'bar', + 'baz': '0' + } + + @json_request(assume_json=False) + def temp(req): + return req.data + + res = temp(rf.get('/?foo=bar&baz=0')) + eq_(res, data) + + def test_post_requests(self): + data = { + 'foo': 'bar', + 'baz': '0' + } + + @json_request(assume_json=False) + def temp(req): + return req.data + + # test application/x-www-form-urlencoded + res = temp(rf.post( + '/', + data='foo=bar&baz=0', + content_type='application/x-www-form-urlencoded' + )) + eq_(res, data) + + # test multipart/form-data + res = temp(rf.post('/', data=data, files=None)) + eq_(res, data) + + def test_assume_json(self): + data = { + 'foo': 'bar', + 'baz': '0' + } + + @json_request(assume_json=True) + def temp(req): + return req.data + + @json_request(assume_json=False) + def temp_2(req): + return req.data + + # test get request + res = temp(rf.get('/?foo=bar&baz=0')) + eq_(res, {}) + + res = temp_2(rf.get('/?foo=bar&baz=0')) + eq_(res, data) + + # test application/x-www-form-urlencoded + res = temp(rf.post( + '/', + data='foo=bar&baz=0', + content_type='application/x-www-form-urlencoded' + )) + eq_(res, {}) + + res = temp_2(rf.post( + '/', + data='foo=bar&baz=0', + content_type='application/x-www-form-urlencoded' + )) + eq_(res, data) + + # test multipart/form-data + res = temp(rf.post('/', data=data, files=None)) + eq_(res, {}) + + res = temp_2(rf.post('/', data=data, files=None)) + eq_(res, data) From ecd53c446092573786e9c3a6bba290ebacc38e7a Mon Sep 17 00:00:00 2001 From: James Socol Date: Sun, 31 Jan 2021 13:38:48 -0500 Subject: [PATCH 2/4] No bare exceptions --- jsonview/decorators.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/jsonview/decorators.py b/jsonview/decorators.py index f40234c..a25e9da 100644 --- a/jsonview/decorators.py +++ b/jsonview/decorators.py @@ -180,7 +180,7 @@ def _wrapped(request, *a, **kw): request.data = json.loads(request.body.decode('ascii')) else: request.data = json.loads(request.body) - except: + except Exception: pass elif request.method == 'GET': request.data = request.GET.dict() From 5cf9427dc4997fea4535a2e1a96913a83d2df616 Mon Sep 17 00:00:00 2001 From: James Socol Date: Sun, 31 Jan 2021 13:47:18 -0500 Subject: [PATCH 3/4] Drop b() helper from tests This was only necessary for Python 2/3 compatibility --- jsonview/tests.py | 15 +-------------- 1 file changed, 1 insertion(+), 14 deletions(-) diff --git a/jsonview/tests.py b/jsonview/tests.py index 4bfb2b1..6bcf66d 100644 --- a/jsonview/tests.py +++ b/jsonview/tests.py @@ -1,7 +1,4 @@ -from __future__ import absolute_import, unicode_literals - import json -import sys from unittest import SkipTest import django @@ -31,16 +28,6 @@ def eq_(a, b, msg=None): assert a == b, msg or '%r != %r' % (a, b) -if sys.version < '3': - def b(x): - return x -else: - import codecs - - def b(x): - return codecs.latin_1_encode(x)[0] - - class CustomTestEncoder(DjangoJSONEncoder): def default(self, o): try: @@ -255,7 +242,7 @@ def temp(req): res = temp(rf.get('/')) eq_(200, res.status_code) payload = json.dumps({'datetime': now}, cls=DjangoJSONEncoder) - eq_(b(payload), res.content) + eq_(payload, res.content) @override_settings(JSON_OPTIONS={'cls': None}) def test_datetime_no_serializer(self): From 7e18187331b26404c48443cbc5e27224b0b1f09c Mon Sep 17 00:00:00 2001 From: James Socol Date: Mon, 15 Sep 2025 18:06:01 -0400 Subject: [PATCH 4/4] wip --- jsonview/tests.py | 47 +++++++++-------------------------------------- 1 file changed, 9 insertions(+), 38 deletions(-) diff --git a/jsonview/tests.py b/jsonview/tests.py index 6bcf66d..34515d7 100644 --- a/jsonview/tests.py +++ b/jsonview/tests.py @@ -386,7 +386,7 @@ def get(self, request): class JsonRequestTests(TestCase): - def test_application_json(self): + def test_with_json_content_type(self): data = { 'foo': 'bar', 'baz': 'qux', @@ -395,7 +395,7 @@ def test_application_json(self): @json_request def temp(req): - return req.data + return req.json_data res = temp(rf.post( '/', @@ -404,61 +404,32 @@ def temp(req): )) eq_(res, data) - def test_get_requests(self): + def test_without_json_content_type(self): data = { 'foo': 'bar', 'baz': '0' } - @json_request(assume_json=False) - def temp(req): - return req.data - - res = temp(rf.get('/?foo=bar&baz=0')) - eq_(res, data) - - def test_post_requests(self): - data = { - 'foo': 'bar', - 'baz': '0' - } - - @json_request(assume_json=False) + @json_request(assume_json=True) def temp(req): - return req.data + return req.json_data - # test application/x-www-form-urlencoded res = temp(rf.post( '/', - data='foo=bar&baz=0', + data=json.dumps(data), content_type='application/x-www-form-urlencoded' )) eq_(res, data) - # test multipart/form-data - res = temp(rf.post('/', data=data, files=None)) - eq_(res, data) - - def test_assume_json(self): + def test_without_json_data(self): data = { 'foo': 'bar', 'baz': '0' } - @json_request(assume_json=True) - def temp(req): - return req.data - @json_request(assume_json=False) - def temp_2(req): - return req.data - - # test get request - res = temp(rf.get('/?foo=bar&baz=0')) - eq_(res, {}) - - res = temp_2(rf.get('/?foo=bar&baz=0')) - eq_(res, data) + def temp(req): + return req.json_data # test application/x-www-form-urlencoded res = temp(rf.post(