Changeset View
Changeset View
Standalone View
Standalone View
swh/core/api/serializers.py
# Copyright (C) 2015-2018 The Software Heritage developers | # Copyright (C) 2015-2018 The Software Heritage developers | ||||
# See the AUTHORS file at the top-level directory of this distribution | # See the AUTHORS file at the top-level directory of this distribution | ||||
# License: GNU General Public License version 3, or any later version | # License: GNU General Public License version 3, or any later version | ||||
# See top-level LICENSE file for more information | # See top-level LICENSE file for more information | ||||
import base64 | import base64 | ||||
import datetime | import datetime | ||||
from json import JSONDecoder, JSONEncoder | import json | ||||
import types | import types | ||||
from uuid import UUID | from uuid import UUID | ||||
import arrow | import arrow | ||||
import dateutil.parser | import dateutil.parser | ||||
import msgpack | import msgpack | ||||
def encode_data_client(data): | def encode_data_client(data): | ||||
try: | try: | ||||
return msgpack_dumps(data) | return msgpack_dumps(data) | ||||
except OverflowError as e: | except OverflowError as e: | ||||
raise ValueError('Limits were reached. Please, check your input.\n' + | raise ValueError('Limits were reached. Please, check your input.\n' + | ||||
str(e)) | str(e)) | ||||
def decode_response(response): | def decode_response(response): | ||||
content_type = response.headers['content-type'] | content_type = response.headers['content-type'] | ||||
if content_type.startswith('application/x-msgpack'): | if content_type.startswith('application/x-msgpack'): | ||||
r = msgpack_loads(response.content) | r = msgpack_loads(response.content) | ||||
elif content_type.startswith('application/json'): | elif content_type.startswith('application/json'): | ||||
r = response.json(cls=SWHJSONDecoder) | r = json.loads(response.text, cls=SWHJSONDecoder) | ||||
else: | else: | ||||
raise ValueError('Wrong content type `%s` for API response' | raise ValueError('Wrong content type `%s` for API response' | ||||
% content_type) | % content_type) | ||||
return r | return r | ||||
class SWHJSONEncoder(JSONEncoder): | class SWHJSONEncoder(json.JSONEncoder): | ||||
"""JSON encoder for data structures generated by Software Heritage. | """JSON encoder for data structures generated by Software Heritage. | ||||
This JSON encoder extends the default Python JSON encoder and adds | This JSON encoder extends the default Python JSON encoder and adds | ||||
awareness for the following specific types: | awareness for the following specific types: | ||||
- bytes (get encoded as a Base85 string); | - bytes (get encoded as a Base85 string); | ||||
- datetime.datetime (get encoded as an ISO8601 string). | - datetime.datetime (get encoded as an ISO8601 string). | ||||
▲ Show 20 Lines • Show All 48 Lines • ▼ Show 20 Lines | def default(self, o): | ||||
try: | try: | ||||
iterable = iter(o) | iterable = iter(o) | ||||
except TypeError: | except TypeError: | ||||
raise e from None | raise e from None | ||||
else: | else: | ||||
return list(iterable) | return list(iterable) | ||||
class SWHJSONDecoder(JSONDecoder): | class SWHJSONDecoder(json.JSONDecoder): | ||||
"""JSON decoder for data structures encoded with SWHJSONEncoder. | """JSON decoder for data structures encoded with SWHJSONEncoder. | ||||
This JSON decoder extends the default Python JSON decoder, | This JSON decoder extends the default Python JSON decoder, | ||||
allowing the decoding of: | allowing the decoding of: | ||||
- bytes (encoded as a Base85 string); | - bytes (encoded as a Base85 string); | ||||
- datetime.datetime (encoded as an ISO8601 string). | - datetime.datetime (encoded as an ISO8601 string). | ||||
▲ Show 20 Lines • Show All 79 Lines • Show Last 20 Lines |