Source code for timeline.views_api

"""REST API views for the timeline app"""

from rest_framework.exceptions import NotFound, PermissionDenied
from rest_framework.generics import ListAPIView, RetrieveAPIView
from rest_framework.permissions import IsAuthenticated
from rest_framework.renderers import JSONRenderer
from rest_framework.versioning import AcceptHeaderVersioning

# Projectroles dependency
from projectroles.views_api import (
    SODARAPIGenericProjectMixin,
    SODARPageNumberPagination,
)

from timeline.models import TimelineEvent
from timeline.serializers import TimelineEventSerializer


# Local constants
TIMELINE_API_MEDIA_TYPE = 'application/vnd.bihealth.sodar-core.timeline+json'
TIMELINE_API_DEFAULT_VERSION = '2.0'
TIMELINE_API_ALLOWED_VERSIONS = ['2.0']


class TimelineAPIVersioningMixin:
    """
    Timeline API view versioning mixin for overriding media type and
    accepted versions.
    """

    class TimelineAPIRenderer(JSONRenderer):
        media_type = TIMELINE_API_MEDIA_TYPE

    class TimelineAPIVersioning(AcceptHeaderVersioning):
        allowed_versions = TIMELINE_API_ALLOWED_VERSIONS
        default_version = TIMELINE_API_DEFAULT_VERSION

    renderer_classes = [TimelineAPIRenderer]
    versioning_class = TimelineAPIVersioning


[docs] class ProjectTimelineEventListAPIView( TimelineAPIVersioningMixin, SODARAPIGenericProjectMixin, ListAPIView ): """ List ``TimelineEvent`` objects belonging in a category or project. Events are ordered from newest to oldest. Supports optional pagination by providing the ``page`` query string. This will return results in the Django Rest Framework PageNumberPagination format. **URL:** ``/timeline/api/list/{Project.sodar_uuid}`` **Methods:** ``GET`` **Parameters:** - ``page``: Page number for paginated results (int, optional) **Returns:** List or paginated dict of ``TimelineEvent`` objects (see ``TimelineEventRetrieveAPIView``) """ pagination_class = SODARPageNumberPagination permission_required = 'timeline.view_timeline' serializer_class = TimelineEventSerializer def get_queryset(self): project = self.get_project() user = self.request.user q_kwargs = {'project': project} if not user.is_superuser and not project.is_owner_or_delegate(user): q_kwargs['classified'] = False return TimelineEvent.objects.filter(**q_kwargs).order_by('-pk')
[docs] class SiteTimelineEventListAPIView(TimelineAPIVersioningMixin, ListAPIView): """ List site-wide ``TimelineEvent`` objects. Events are ordered from newest to oldest. Supports optional pagination by providing the ``page`` query string. This will return results in the Django Rest Framework ``PageNumberPagination`` format. **URL:** ``/timeline/api/list/site`` **Methods:** ``GET`` **Parameters:** - ``page``: Page number for paginated results (int, optional) **Returns:** List or paginated dict of ``TimelineEvent`` objects (see ``TimelineEventRetrieveAPIView``) """ pagination_class = SODARPageNumberPagination permission_classes = [IsAuthenticated] serializer_class = TimelineEventSerializer def get_queryset(self): user = self.request.user q_kwargs = {'project': None} if not user.is_superuser: q_kwargs['classified'] = False return TimelineEvent.objects.filter(**q_kwargs).order_by('-pk')
[docs] class TimelineEventRetrieveAPIView(TimelineAPIVersioningMixin, RetrieveAPIView): """ Retrieve ``TimelineEvent`` object. Extra data is only returned for users with sufficient permissions (superusers, project owners and delegates). **URL:** ``/timeline/api/retrieve/{TimelineEvent.sodar_uuid}`` **Methods:** ``GET`` **Returns:** - ``project``: Project UUID (string or None) - ``app``: App name (string) - ``user``: UUID of user who created the event (string or None) - ``event_name``: Event name (string) - ``description``: Event description (string) - ``extra_data``: Event extra data (JSON or None) - ``classified``: Whether event is classified (boolean) - ``status_changes``: List of TimelineEventStatus objects (JSON) - ``event``: TimelineEvent UUID (string) - ``timestamp``: Status datetime (YYYY-MM-DDThh:mm:ssZ) - ``status_type``: Status type (string) - ``description``: Status description (string) - ``extra_data``: Status extra data (JSON or None) - ``sodar_uuid``: Status UUID (string) - ``event_objects``: List of TimelineEventObjectRef objects (JSON) - ``event``: TimelineEvent UUID (string) - ``label``: Object label as given in event description (string) - ``name``: Name for identifying the object (string) - ``object_uuid``: UUID of the referred object (string) - ``extra_data``: Object reference extra data (JSON or None) - ``sodar_uuid``: Object reference UUID (string) - ``sodar_uuid``: TimelineEvent UUID (string) **Version Changes:** - ``2.0``: Return ``user`` as UUID instead of ``SODARUserSerializer`` dict """ permission_classes = [IsAuthenticated] # Perms checked in get_object() serializer_class = TimelineEventSerializer def get_object(self): obj = TimelineEvent.objects.filter( sodar_uuid=self.kwargs.get('timelineevent') ).first() if not obj: raise NotFound() user = self.request.user if obj.project and not user.has_perm( 'timeline.view_timeline', obj.project ): raise PermissionDenied() if obj.classified: if ( obj.project and not user.is_superuser and not obj.project.is_owner_or_delegate(user) ): raise PermissionDenied() elif not obj.project and not user.is_superuser: raise PermissionDenied() return obj