diff --git a/mayan/apps/events/api_views.py b/mayan/apps/events/api_views.py index eeea4c7d33..dc7f05d6ea 100644 --- a/mayan/apps/events/api_views.py +++ b/mayan/apps/events/api_views.py @@ -5,10 +5,11 @@ from django.http import Http404 from django.shortcuts import get_object_or_404 from actstream.models import Action, any_stream -from rest_framework import generics +from rest_framework import generics, viewsets +from rest_framework.response import Response +from rest_framework.decorators import action from mayan.apps.acls.models import AccessControlList -from mayan.apps.rest_api.permissions import MayanPermission from .classes import EventType, EventTypeNamespace from .models import Notification @@ -19,6 +20,52 @@ from .serializers import ( ) + +class EventTypeNamespaceAPIViewSet(viewsets.ReadOnlyModelViewSet): + lookup_field = 'name' + lookup_url_kwarg = 'event_type_namespace_name' + serializer_class = EventTypeNamespaceSerializer + + def get_object(self): + lookup_url_kwarg = self.lookup_url_kwarg or self.lookup_field + filter_kwargs = {self.lookup_field: self.kwargs[lookup_url_kwarg]} + return EventTypeNamespace.get(**filter_kwargs) + + @action( + detail=True, serializer_class=EventTypeSerializer, + url_name='event_type-list', url_path='event_types' + ) + def event_type_list(self, request, *args, **kwargs): + queryset = self.get_object().event_types + page = self.paginate_queryset(queryset) + + serializer = self.get_serializer( + queryset, many=True, context={'request': request} + ) + + if page is not None: + return self.get_paginated_response(serializer.data) + + return Response(serializer.data) + + def get_queryset(self): + return EventTypeNamespace.all() + + +class EventTypeAPIViewSet(viewsets.ReadOnlyModelViewSet): + lookup_field = 'id' + lookup_url_kwarg = 'event_type_id' + lookup_value_regex = r'[\w\.]+' + serializer_class = EventTypeSerializer + + def get_object(self): + namespace = EventTypeNamespace.get(name=self.kwargs['event_type_namespace_name']) + event_types = namespace.get_event_types() + return event_types.get(self.kwargs['event_type_id']) + + + +''' class APIObjectEventListView(generics.ListAPIView): """ get: Return a list of events for the specified object. @@ -49,88 +96,6 @@ class APIObjectEventListView(generics.ListAPIView): return any_stream(obj) -class APIEventTypeNamespaceDetailView(generics.RetrieveAPIView): - """ - get: Returns the details of an event type namespace. - """ - serializer_class = EventTypeNamespaceSerializer - - def get_object(self): - try: - return EventTypeNamespace.get(name=self.kwargs['name']) - except KeyError: - raise Http404 - - -class APIEventTypeNamespaceListView(generics.ListAPIView): - """ - get: Returns a list of all the available event type namespaces. - """ - serializer_class = EventTypeNamespaceSerializer - queryset = EventTypeNamespace.all() - - def get_serializer_context(self): - return { - 'format': self.format_kwarg, - 'request': self.request, - 'view': self - } - - -class APIEventTypeNamespaceEventTypeListView(generics.ListAPIView): - """ - get: Returns a list of all the available event types from a namespaces. - """ - serializer_class = EventTypeSerializer - - def get_queryset(self): - try: - return EventTypeNamespace.get( - name=self.kwargs['name'] - ).get_event_types() - except KeyError: - raise Http404 - - def get_serializer_context(self): - return { - 'format': self.format_kwarg, - 'request': self.request, - 'view': self - } - - -class APIEventTypeListView(generics.ListAPIView): - """ - get: Returns a list of all the available event types. - """ - serializer_class = EventTypeSerializer - queryset = EventType.all() - - def get_serializer_context(self): - return { - 'format': self.format_kwarg, - 'request': self.request, - 'view': self - } - - -class APIEventListView(generics.ListAPIView): - """ - get: Returns a list of all the available events. - """ - mayan_view_permissions = {'GET': (permission_events_view,)} - permission_classes = (MayanPermission,) - queryset = Action.objects.all() - serializer_class = EventSerializer - - def get_serializer_context(self): - return { - 'format': self.format_kwarg, - 'request': self.request, - 'view': self - } - - class APINotificationListView(generics.ListAPIView): """ get: Return a list of notifications for the current user. @@ -151,3 +116,4 @@ class APINotificationListView(generics.ListAPIView): queryset = queryset.filter(read=False) return queryset +''' diff --git a/mayan/apps/events/classes.py b/mayan/apps/events/classes.py index 992c9ed9db..16fdbb9ca0 100644 --- a/mayan/apps/events/classes.py +++ b/mayan/apps/events/classes.py @@ -45,7 +45,11 @@ class EventTypeNamespace(object): return event_type def get_event_types(self): - return EventType.sort(event_type_list=self.event_types) + result = {} + for event_type in self.event_types: + result[event_type.id] = event_type + + return result @python_2_unicode_compatible diff --git a/mayan/apps/events/serializers.py b/mayan/apps/events/serializers.py index c15a853bd8..c14a1b7397 100644 --- a/mayan/apps/events/serializers.py +++ b/mayan/apps/events/serializers.py @@ -4,10 +4,10 @@ from django.utils.six import string_types from actstream.models import Action from rest_framework import serializers -from rest_framework.reverse import reverse from mayan.apps.common.serializers import ContentTypeSerializer from mayan.apps.rest_api.fields import DynamicSerializerField +from mayan.apps.rest_api.relations import MultiKwargHyperlinkedIdentityField from mayan.apps.user_management.serializers import UserSerializer from .classes import EventType @@ -17,33 +17,34 @@ from .models import Notification, StoredEventType class EventTypeNamespaceSerializer(serializers.Serializer): label = serializers.CharField() name = serializers.CharField() - url = serializers.SerializerMethodField() - - event_types_url = serializers.HyperlinkedIdentityField( + event_type_list_url = serializers.HyperlinkedIdentityField( lookup_field='name', - view_name='rest_api:event-type-namespace-event-type-list', + lookup_url_kwarg='event_type_namespace_name', + view_name='rest_api:event_type_namespace-event_type-list' + ) + url = serializers.HyperlinkedIdentityField( + lookup_field='name', + lookup_url_kwarg='event_type_namespace_name', + view_name='rest_api:event_type_namespace-detail' ) - - def get_url(self, instance): - return reverse( - 'rest_api:event-type-namespace-detail', args=( - instance.name, - ), request=self.context['request'], format=self.context['format'] - ) class EventTypeSerializer(serializers.Serializer): label = serializers.CharField() name = serializers.CharField() id = serializers.CharField() - event_type_namespace_url = serializers.SerializerMethodField() - - def get_event_type_namespace_url(self, instance): - return reverse( - 'rest_api:event-type-namespace-detail', args=( - instance.namespace.name, - ), request=self.context['request'], format=self.context['format'] - ) + event_type_namespace = EventTypeNamespaceSerializer(source='namespace') + url = MultiKwargHyperlinkedIdentityField( + view_kwargs=( + { + 'lookup_field': 'namespace.name', 'lookup_url_kwarg': 'event_type_namespace_name', + }, + { + 'lookup_field': 'id', 'lookup_url_kwarg': 'event_type_id', + } + ), + view_name='rest_api:event_type-detail' + ) def to_representation(self, instance): if isinstance(instance, EventType): diff --git a/mayan/apps/events/tests/literals.py b/mayan/apps/events/tests/literals.py new file mode 100644 index 0000000000..7919302efa --- /dev/null +++ b/mayan/apps/events/tests/literals.py @@ -0,0 +1,7 @@ +from __future__ import unicode_literals + +TEST_EVENT_TYPE_NAMESPACE_LABEL = 'test event type namespace label' +TEST_EVENT_TYPE_NAMESPACE_NAME = 'test_event_type_namespace_name' +TEST_EVENT_TYPE_LABEL = 'test event type label' +TEST_EVENT_TYPE_NAME = 'test_event_type_name' + diff --git a/mayan/apps/events/tests/mixins.py b/mayan/apps/events/tests/mixins.py new file mode 100644 index 0000000000..e4ea3dd31b --- /dev/null +++ b/mayan/apps/events/tests/mixins.py @@ -0,0 +1,20 @@ +from __future__ import unicode_literals + +from ..classes import EventTypeNamespace + +from .literals import ( + TEST_EVENT_TYPE_LABEL, TEST_EVENT_TYPE_NAME, + TEST_EVENT_TYPE_NAMESPACE_LABEL, TEST_EVENT_TYPE_NAMESPACE_NAME +) + + +class EventTypeTestMixin(object): + def _create_test_event_type(self): + self.test_event_type_namespace = EventTypeNamespace( + label=TEST_EVENT_TYPE_NAMESPACE_LABEL, + name=TEST_EVENT_TYPE_NAMESPACE_NAME + ) + self.test_event_type = self.test_event_type_namespace.add_event_type( + label=TEST_EVENT_TYPE_LABEL, + name=TEST_EVENT_TYPE_NAME + ) diff --git a/mayan/apps/events/tests/test_api.py b/mayan/apps/events/tests/test_api.py index d0ffffd967..b285392936 100644 --- a/mayan/apps/events/tests/test_api.py +++ b/mayan/apps/events/tests/test_api.py @@ -1,11 +1,35 @@ from __future__ import unicode_literals -from django.urls import reverse - from mayan.apps.rest_api.tests import BaseAPITestCase +from .mixins import EventTypeTestMixin -class EventAPITestCase(BaseAPITestCase): - def test_evet_type_list_view(self): - response = self.client.get(reverse(viewname='rest_api:event-type-list')) + +class EventTypeNamespaceAPITestCase(EventTypeTestMixin, BaseAPITestCase): + def setUp(self): + super(EventTypeNamespaceAPITestCase, self).setUp() + self._create_test_event_type() + + def test_event_type_namespace_list_view(self): + response = self.get(viewname='rest_api:event_type_namespace-list') + self.assertEqual(response.status_code, 200) + + def test_event_type_namespace_event_type_list_view(self): + response = self.get( + viewname='rest_api:event_type_namespace-event_type-list', + kwargs={ + 'event_type_namespace_name': self.test_event_type_namespace.name + } + ) + + self.assertEqual(response.status_code, 200) + + def test_event_type_list_view(self): + response = self.get( + viewname='rest_api:event_type-detail', + kwargs={ + 'event_type_namespace_name': self.test_event_type_namespace.name, + 'event_type_id': self.test_event_type.id + } + ) self.assertEqual(response.status_code, 200) diff --git a/mayan/apps/events/urls.py b/mayan/apps/events/urls.py index f93a84eaac..34ddb15824 100644 --- a/mayan/apps/events/urls.py +++ b/mayan/apps/events/urls.py @@ -2,11 +2,7 @@ from __future__ import unicode_literals from django.conf.urls import url -from .api_views import ( - APIEventListView, APIEventTypeListView, APIEventTypeNamespaceDetailView, - APIEventTypeNamespaceEventTypeListView, APIEventTypeNamespaceListView, - APINotificationListView, APIObjectEventListView -) +from .api_views import EventTypeAPIViewSet, EventTypeNamespaceAPIViewSet from .views import ( CurrentUserEventListView, EventListView, EventTypeSubscriptionListView, NotificationListView, NotificationMarkRead, NotificationMarkReadAll, @@ -53,6 +49,21 @@ urlpatterns = [ ) ] + +api_router_entries = ( + { + 'prefix': r'event_type_namespaces', 'viewset': EventTypeNamespaceAPIViewSet, + 'basename': 'event_type_namespace' + }, + { + 'prefix': r'event_type_namespaces/(?P[^/.]+)/event_types', + 'viewset': EventTypeAPIViewSet, 'basename': 'event_type' + }, + #{'prefix': r'roles', 'viewset': RoleAPIViewSet, 'basename': 'role'}, +) + + +''' api_urls = [ url( regex=r'^event_type_namespaces/(?P[-\w]+)/$', @@ -82,3 +93,4 @@ api_urls = [ name='object-event-list', view=APIObjectEventListView.as_view() ) ] +'''