Browse Source

Moved secret views into a ViewSet (no write ability yet)

Jeremy Stretch 8 years ago
parent
commit
4f8a5eb1a0

+ 8 - 0
netbox/secrets/api/serializers.py

@@ -34,3 +34,11 @@ class SecretSerializer(serializers.ModelSerializer):
     class Meta:
     class Meta:
         model = Secret
         model = Secret
         fields = ['id', 'device', 'role', 'name', 'plaintext', 'hash', 'created', 'last_updated']
         fields = ['id', 'device', 'role', 'name', 'plaintext', 'hash', 'created', 'last_updated']
+
+
+class WritableSecretSerializer(serializers.ModelSerializer):
+    plaintext = serializers.CharField()
+
+    class Meta:
+        model = Secret
+        fields = ['id', 'device', 'role', 'name', 'plaintext']

+ 1 - 4
netbox/secrets/api/urls.py

@@ -7,15 +7,12 @@ from . import views
 
 
 router = routers.DefaultRouter()
 router = routers.DefaultRouter()
 router.register(r'secret-roles', views.SecretRoleViewSet)
 router.register(r'secret-roles', views.SecretRoleViewSet)
+router.register(r'secrets', views.SecretViewSet)
 
 
 urlpatterns = [
 urlpatterns = [
 
 
     url(r'', include(router.urls)),
     url(r'', include(router.urls)),
 
 
-    # Secrets
-    url(r'^secrets/$', views.SecretListView.as_view(), name='secret_list'),
-    url(r'^secrets/(?P<pk>\d+)/$', views.SecretDetailView.as_view(), name='secret_detail'),
-
     # Miscellaneous
     # Miscellaneous
     url(r'^generate-keys/$', views.RSAKeyGeneratorView.as_view(), name='generate_keys'),
     url(r'^generate-keys/$', views.RSAKeyGeneratorView.as_view(), name='generate_keys'),
 
 

+ 22 - 0
netbox/secrets/api/views.py

@@ -4,6 +4,7 @@ from django.shortcuts import get_object_or_404
 
 
 from rest_framework import generics
 from rest_framework import generics
 from rest_framework import status
 from rest_framework import status
+from rest_framework.authentication import BasicAuthentication, SessionAuthentication
 from rest_framework.exceptions import PermissionDenied
 from rest_framework.exceptions import PermissionDenied
 from rest_framework.permissions import IsAuthenticated
 from rest_framework.permissions import IsAuthenticated
 from rest_framework.renderers import JSONRenderer
 from rest_framework.renderers import JSONRenderer
@@ -14,6 +15,7 @@ from rest_framework.viewsets import ModelViewSet
 from extras.api.renderers import FormlessBrowsableAPIRenderer, FreeRADIUSClientsRenderer
 from extras.api.renderers import FormlessBrowsableAPIRenderer, FreeRADIUSClientsRenderer
 from secrets.filters import SecretFilter
 from secrets.filters import SecretFilter
 from secrets.models import Secret, SecretRole, UserKey
 from secrets.models import Secret, SecretRole, UserKey
+from utilities.api import WritableSerializerMixin
 
 
 from . import serializers
 from . import serializers
 
 
@@ -37,6 +39,25 @@ class SecretRoleViewSet(ModelViewSet):
 # Secrets
 # Secrets
 #
 #
 
 
+# TODO: Need to implement custom create() and update() methods to handle secret encryption, and custom list() and
+# retrieve() methods to handle decryption.
+class SecretViewSet(WritableSerializerMixin, ModelViewSet):
+    queryset = Secret.objects.select_related(
+        'device__primary_ip4', 'device__primary_ip6', 'role',
+    ).prefetch_related(
+        'role__users', 'role__groups',
+    )
+    serializer_class = serializers.SecretSerializer
+    write_serializer_class = serializers.WritableSecretSerializer
+    filter_class = SecretFilter
+    # DRF's BrowsableAPIRenderer can't support passing the secret key as a header, so we disable it.
+    renderer_classes = [FormlessBrowsableAPIRenderer, JSONRenderer, FreeRADIUSClientsRenderer]
+    # Enabled BasicAuthentication for testing (until we have TokenAuthentication implemented)
+    authentication_classes = [BasicAuthentication, SessionAuthentication]
+    permission_classes = [IsAuthenticated]
+
+
+# TODO: Delete
 class SecretListView(generics.GenericAPIView):
 class SecretListView(generics.GenericAPIView):
     """
     """
     List secrets (filterable). If a private key is POSTed, attempt to decrypt each Secret.
     List secrets (filterable). If a private key is POSTed, attempt to decrypt each Secret.
@@ -83,6 +104,7 @@ class SecretListView(generics.GenericAPIView):
         return self.get(request, private_key=request.POST.get('private_key'))
         return self.get(request, private_key=request.POST.get('private_key'))
 
 
 
 
+# TODO: Delete
 class SecretDetailView(generics.GenericAPIView):
 class SecretDetailView(generics.GenericAPIView):
     """
     """
     Retrieve a single Secret. If a private key is POSTed, attempt to decrypt the Secret.
     Retrieve a single Secret. If a private key is POSTed, attempt to decrypt the Secret.

+ 6 - 1
netbox/secrets/filters.py

@@ -22,11 +22,16 @@ class SecretFilter(django_filters.FilterSet):
         to_field_name='slug',
         to_field_name='slug',
         label='Role (slug)',
         label='Role (slug)',
     )
     )
+    device_id = django_filters.ModelMultipleChoiceFilter(
+        name='device',
+        queryset=Device.objects.all(),
+        label='Device (ID)',
+    )
     device = django_filters.ModelMultipleChoiceFilter(
     device = django_filters.ModelMultipleChoiceFilter(
         name='device',
         name='device',
         queryset=Device.objects.all(),
         queryset=Device.objects.all(),
         to_field_name='name',
         to_field_name='name',
-        label='Device (Name)',
+        label='Device (name)',
     )
     )
 
 
     class Meta:
     class Meta: