Skip to content

Commit

Permalink
api/serializers: Force json module use to decode requests text response
Browse files Browse the repository at this point in the history
When the simplejson module is present in the Phython environment, requests will
use it to decode json but a call to response.json(cls=...) will raise an exception
as the arguments accepted by JSONDecoder are inconsistent between the standard library
json and simplejson (more details here: psf/requests#4842).

So ensure to use standard json module for decoding response texts.
  • Loading branch information
anlambert committed Oct 25, 2019
1 parent 91910d9 commit d88a9c5
Show file tree
Hide file tree
Showing 2 changed files with 16 additions and 5 deletions.
8 changes: 4 additions & 4 deletions swh/core/api/serializers.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@

import base64
import datetime
from json import JSONDecoder, JSONEncoder
import json
import types
from uuid import UUID

Expand All @@ -28,15 +28,15 @@ def decode_response(response):
if content_type.startswith('application/x-msgpack'):
r = msgpack_loads(response.content)
elif content_type.startswith('application/json'):
r = response.json(cls=SWHJSONDecoder)
r = json.loads(response.text, cls=SWHJSONDecoder)
else:
raise ValueError('Wrong content type `%s` for API response'
% content_type)

return r


class SWHJSONEncoder(JSONEncoder):
class SWHJSONEncoder(json.JSONEncoder):
"""JSON encoder for data structures generated by Software Heritage.
This JSON encoder extends the default Python JSON encoder and adds
Expand Down Expand Up @@ -101,7 +101,7 @@ def default(self, o):
return list(iterable)


class SWHJSONDecoder(JSONDecoder):
class SWHJSONDecoder(json.JSONDecoder):
"""JSON decoder for data structures encoded with SWHJSONEncoder.
This JSON decoder extends the default Python JSON decoder,
Expand Down
13 changes: 12 additions & 1 deletion swh/core/api/tests/test_serializers.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,12 +9,15 @@
from uuid import UUID

import arrow
import requests
import requests_mock

from swh.core.api.serializers import (
SWHJSONDecoder,
SWHJSONEncoder,
msgpack_dumps,
msgpack_loads
msgpack_loads,
decode_response
)


Expand Down Expand Up @@ -79,3 +82,11 @@ def test_generator_json(self):
def test_generator_msgpack(self):
data = msgpack_dumps(self.generator)
self.assertEqual(self.gen_lst, msgpack_loads(data))

@requests_mock.Mocker()
def test_decode_response_json(self, mock_requests):
mock_requests.get('https://example.org/test/data',
json=self.encoded_data,
headers={'content-type': 'application/json'})
response = requests.get('https://example.org/test/data')
assert decode_response(response) == self.data

0 comments on commit d88a9c5

Please sign in to comment.