Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Improve HTTP API #370

Closed
wants to merge 1 commit into from
Closed
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 3 additions & 1 deletion requirements/base.txt
Original file line number Diff line number Diff line change
Expand Up @@ -15,13 +15,15 @@ django-extensions==1.7.9
django-model-utils==3.0.0
#tastypie 0.13.3 has breaking changes
django-tastypie==0.13.1
formencode==1.3.1
futures==3.0.5 # used by gunicorn's async workers
gevent==1.2.1 # used by gunicorn's async workers
gunicorn==19.7.1
inflect==0.2.1
jsonfield==2.0.1
logutils==0.3.4.1
lxml==3.7.3
metsrw==0.2.0
git+https://github.com/artefactual-labs/mets-reader-writer.git@dev/issue-11581-premis-parsing
ndg-httpsclient==0.4.2
pyasn1==0.2.3
python-gnupg==0.4.0
Expand Down
112 changes: 112 additions & 0 deletions storage_service/locations/api/beta/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
"""Version beta of the Storage Service API.
The Storage Service exposes the following resources via a consistent HTTP JSON
interface under the path namespace /api/beta/:
- /locations/ --- purpose-specific paths within a /spaces/ resource
- /spaces/ --- storage space with behaviour specific to backing system
- /pipelines/ --- an Archivematica instance that is the source of a package
The following resources are read-only (update, create, delete and related
operations are disabled):
- /packages/ --- Information Package (SIP, DIP or AIP)
- /file/ --- a file on disk (which is in a package), represented as db row.
All resources have endpoints that follow this pattern::
+-----------------+-------------+----------------------------+------------+
| Purpose | HTTP Method | Path | Method |
+-----------------+-------------+----------------------------+------------+
| Create new | POST | /<cllctn_name>/ | create |
| Get create data | GET | /<cllctn_name>/new/ | new |
| Read all | GET | /<cllctn_name>/ | index |
| Read specific | GET | /<cllctn_name>/<id>/ | show |
| Update specific | PUT | /<cllctn_name>/<id>/ | update |
| Get update data | GET | /<cllctn_name>/<id>/edit/ | edit |
| Delete specific | DELETE | /<cllctn_name>/<id>/ | delete |
| Search | SEARCH | /<cllctn_name>/ | search |
| Search | POST | /<cllctn_name>/search/ | search |
| Get search data | GET | /<cllctn_name>/new_search/ | new_search |
+-----------------+-------------+----------------------------+------------+
.. note:: To remove the search-related routes for a given resource, create a
``'searchable'`` key with value ``False`` in the configuration for the
resource in the ``RESOURCES`` dict. E.g., ``'location': {'searchable':
False}`` will make the /locations/ resource non-searchable.
.. note:: All resources expose the same endpoints. If a resource needs special
treatment, it should be done at the corresponding class level. E.g., if
``POST /packages/`` (creating a package) is special, then do special stuff
in ``resources.py::Packages.create``. Similarly, if packages are indelible,
then ``resources.py::Packages.delete`` should return 404.
"""

from locations.api.beta.remple import API
from locations.api.beta.resources import (
ArkivumSpaces,
# Asyncs,
Callbacks,
DataverseSpaces,
DSpaceSpaces,
DuracloudSpaces,
Events,
FedoraSpaces,
FixityLogs,
LockssomaticSpaces,
NFSSpaces,
S3Spaces,
SwiftSpaces,
Files,
GPGSpaces,
LocalFilesystemSpaces,
Locations,
Packages,
Pipelines,
PipelineLocalSpaces,
Spaces,
Users,
Groups,
Permissions,
ContentTypes,
)

API_VERSION = 'beta'
SERVICE_NAME = 'Archivematica Storage Service'

resources = {
'pipeline': {'resource_cls': Pipelines},
'location': {'resource_cls': Locations},
'space': {'resource_cls': Spaces},
'user': {'resource_cls': Users},

# Space sub-types
'local_filesystem_space': {'resource_cls': LocalFilesystemSpaces},
'gpg_space': {'resource_cls': GPGSpaces},
'arkivum_space': {'resource_cls': ArkivumSpaces},
'dataverse_space': {'resource_cls': DataverseSpaces},
'dspace_space': {'resource_cls': DSpaceSpaces},
'duracloud_space': {'resource_cls': DuracloudSpaces},
'fedora_space': {'resource_cls': FedoraSpaces},
'lockssomatic_space': {'resource_cls': LockssomaticSpaces},
'nfs_space': {'resource_cls': NFSSpaces},
's3_space': {'resource_cls': S3Spaces},
'swift_space': {'resource_cls': SwiftSpaces},
'pipeline_local_space': {'resource_cls': PipelineLocalSpaces},

# The following resources are read-only because of their super-classes
'file': {'resource_cls': Files},
'package': {'resource_cls': Packages},
'event': {'resource_cls': Events},
'callback': {'resource_cls': Callbacks},
'fixity_log': {'resource_cls': FixityLogs},
'group': {'resource_cls': Groups},
'permission': {'resource_cls': Permissions},
'contenttype': {'resource_cls': ContentTypes},
}

api = API(api_version=API_VERSION, service_name=SERVICE_NAME)
api.register_resources(resources)
urls = api.get_urlpatterns()

__all__ = ('urls', 'api')
14 changes: 14 additions & 0 deletions storage_service/locations/api/beta/remple/README.rst
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
================================================================================
Remple: REST Simple
================================================================================

Usage::

>>> from remple import API, Resources
>>> class Users(Resources):
... model_cls = User # A Django model class
... schema_cls = UserSchema # A Formencode class
>>> resources = {'user': {'resource_cls': Users}}
>>> api = API(api_version='0.1.0', service_name='User City!')
>>> api.register_resources(resources)
>>> urls = api.get_urlpatterns() # Include these in Django urlpatterns
60 changes: 60 additions & 0 deletions storage_service/locations/api/beta/remple/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,60 @@
"""Remple: REST Simple
Usage::
>>> from remple import API, Resources
>>> class Users(Resources):
... model_cls = User # A Django model class
... schema_cls = UserSchema # A Formencode class
>>> resources = {'user': {'resource_cls': Users}}
>>> api = API(api_version='0.1.0', service_name='User City!')
>>> api.register_resources(resources)
>>> urls = api.get_urlpatterns() # Include thes in Django urlpatterns
"""

from __future__ import absolute_import

from .resources import Resources, ReadonlyResources
from .querybuilder import QueryBuilder
from .routebuilder import RouteBuilder as API
from .routebuilder import (
ID_PATT,
UUID_PATT,
get_collection_targeting_regex,
get_member_targeting_regex,
)
from .openapi import (
CustomEndPoint,
schema_name2path,
get_error_schema_path,
get_ref_response,
)
from . import utils
from .schemata import ResourceURI
from .constants import (
OK_STATUS,
NOT_FOUND_STATUS,
UNAUTHORIZED_MSG,
FORBIDDEN_STATUS,
)

__all__ = (
'API',
'CustomEndPoint',
'FORBIDDEN_STATUS',
'ID_PATT',
'NOT_FOUND_STATUS',
'OK_STATUS',
'QueryBuilder',
'ReadonlyResources',
'Resources',
'ResourceURI',
'UNAUTHORIZED_MSG',
'UUID_PATT',
'get_collection_targeting_regex',
'get_error_schema_path',
'get_ref_response',
'get_member_targeting_regex',
'schema_name2path',
'utils',
)
Loading