Changeset View
Changeset View
Standalone View
Standalone View
swh/deposit/api/collection.py
# Copyright (C) 2017-2020 The Software Heritage developers | # Copyright (C) 2017-2020 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 | ||||
from typing import Any, Dict, Optional, Tuple | from typing import Optional, Tuple | ||||
from rest_framework import status | from rest_framework import status | ||||
from ..config import EDIT_IRI | from ..config import EDIT_IRI | ||||
from ..parsers import ( | from ..parsers import ( | ||||
SWHAtomEntryParser, | SWHAtomEntryParser, | ||||
SWHFileUploadTarParser, | SWHFileUploadTarParser, | ||||
SWHFileUploadZipParser, | SWHFileUploadZipParser, | ||||
SWHMultiPartParser, | SWHMultiPartParser, | ||||
) | ) | ||||
from .common import ACCEPT_ARCHIVE_CONTENT_TYPES, APIPost, ParsedRequestHeaders | from .common import ACCEPT_ARCHIVE_CONTENT_TYPES, APIPost, ParsedRequestHeaders, Receipt | ||||
class CollectionAPI(APIPost): | class CollectionAPI(APIPost): | ||||
"""Deposit request class defining api endpoints for sword deposit. | """Deposit request class defining api endpoints for sword deposit. | ||||
What's known as 'Col-IRI' in the sword specification. | What's known as 'Col-IRI' in the sword specification. | ||||
HTTP verbs supported: POST | HTTP verbs supported: POST | ||||
""" | """ | ||||
parser_classes = ( | parser_classes = ( | ||||
SWHMultiPartParser, | SWHMultiPartParser, | ||||
SWHFileUploadZipParser, | SWHFileUploadZipParser, | ||||
SWHFileUploadTarParser, | SWHFileUploadTarParser, | ||||
SWHAtomEntryParser, | SWHAtomEntryParser, | ||||
) | ) | ||||
def process_post( | def process_post( | ||||
self, | self, | ||||
req, | req, | ||||
headers: ParsedRequestHeaders, | headers: ParsedRequestHeaders, | ||||
collection_name: str, | collection_name: str, | ||||
deposit_id: Optional[int] = None, | deposit_id: Optional[int] = None, | ||||
) -> Tuple[int, str, Dict[str, Any]]: | ) -> Tuple[int, str, Receipt]: | ||||
"""Create a first deposit as: | """Create a first deposit as: | ||||
- archive deposit (1 zip) | - archive deposit (1 zip) | ||||
- multipart (1 zip + 1 atom entry) | - multipart (1 zip + 1 atom entry) | ||||
- atom entry | - atom entry | ||||
Args: | Args: | ||||
req (Request): the request holding the information to parse | req (Request): the request holding the information to parse | ||||
and inject in db | and inject in db | ||||
collection_name (str): the associated client | collection_name (str): the associated client | ||||
Returns: | Returns: | ||||
An http response (HttpResponse) according to the situation. | An http response (HttpResponse) according to the situation. | ||||
If everything is ok, a 201 response (created) with a | If everything is ok, a 201 response (created) with a | ||||
deposit receipt. | deposit receipt. | ||||
Otherwise, depending on the upload, the following errors | Raises: | ||||
can be returned: | |||||
- archive deposit: | - archive deposit: | ||||
- 400 (bad request) if the request is not providing an external | - 400 (bad request) if the request is not providing an external | ||||
identifier | identifier | ||||
- 403 (forbidden) if the length of the archive exceeds the | - 403 (forbidden) if the length of the archive exceeds the | ||||
max size configured | max size configured | ||||
- 412 (precondition failed) if the length or hash provided | - 412 (precondition failed) if the length or hash provided | ||||
mismatch the reality of the archive. | mismatch the reality of the archive. | ||||
- 415 (unsupported media type) if a wrong media type is | - 415 (unsupported media type) if a wrong media type is | ||||
Show All 12 Lines | ) -> Tuple[int, str, Receipt]: | ||||
identifier | identifier | ||||
- 400 (bad request) if the request's body is empty | - 400 (bad request) if the request's body is empty | ||||
- 415 (unsupported media type) if a wrong media type is | - 415 (unsupported media type) if a wrong media type is | ||||
provided | provided | ||||
""" | """ | ||||
assert deposit_id is None | assert deposit_id is None | ||||
if req.content_type in ACCEPT_ARCHIVE_CONTENT_TYPES: | if req.content_type in ACCEPT_ARCHIVE_CONTENT_TYPES: | ||||
data = self._binary_upload( | receipt = self._binary_upload( | ||||
req, headers, collection_name, check_slug_is_present=True | req, headers, collection_name, check_slug_is_present=True | ||||
) | ) | ||||
elif req.content_type.startswith("multipart/"): | elif req.content_type.startswith("multipart/"): | ||||
data = self._multipart_upload( | receipt = self._multipart_upload( | ||||
req, headers, collection_name, check_slug_is_present=True | req, headers, collection_name, check_slug_is_present=True | ||||
) | ) | ||||
else: | else: | ||||
data = self._atom_entry( | receipt = self._atom_entry( | ||||
req, headers, collection_name, check_slug_is_present=True | req, headers, collection_name, check_slug_is_present=True | ||||
) | ) | ||||
return status.HTTP_201_CREATED, EDIT_IRI, data | return status.HTTP_201_CREATED, EDIT_IRI, receipt |