Last active
September 7, 2018 00:27
-
-
Save iMerica/6e08d2be799d0c4494ee29cb6fa21111 to your computer and use it in GitHub Desktop.
Custom Auth for Django/DRF that allows for multiple API Tokens per user.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from rest_framework.authentication import TokenAuthentication | |
from .models import RESTAPIToken | |
class CustomRestAPIAuthentication(TokenAuthentication): | |
""" Custom Authentication """ | |
def get_model(self): | |
return RESTAPIToken |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
import binascii | |
import os | |
from django.conf import settings | |
from django.db import models | |
class RESTAPIToken(models.Model): | |
""" Tokens specifically for REST API Access (with M2M support ) """ | |
key = models.CharField(_("Key"), max_length=40, primary_key=True) | |
label = models.CharField(max_length=30, null=True) | |
user = models.ForeignKey( | |
settings.AUTH_USER_MODEL, related_name='rest_api_auth_token', | |
on_delete=models.CASCADE, | |
) | |
created = models.DateTimeField(_("Created"), auto_now_add=True) | |
objects = models.Manager() | |
def save(self, *args, **kwargs): | |
if not self.key: | |
self.key = self.generate_key() | |
return super(RESTAPIToken, self).save(*args, **kwargs) | |
@staticmethod | |
def generate_key(): | |
return binascii.hexlify(os.urandom(20)).decode() | |
def __str__(self): | |
return self.key |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from rest_framework import serializers | |
from .models import RESTAPIToken | |
class RestAPITokenSerializer(serializers.ModelSerializer): | |
class Meta: | |
model = RESTAPIToken | |
fields = ['key', 'label', 'created'] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from .views import RestAPITokenView, CoolPublicAPIResource | |
from django.conf.urls import url | |
PRIVATE_API_PREFIX = '/private/api/' | |
PUBLIC_API_PREFIX = '/public/api/' | |
urlpatterns = [ | |
url(fr'^{PRIVATE_API_PREFIX}api-tokens/$', RestAPITokenView.as_view(), name='api_tokens'), | |
url(fr'^{PUBLIC_API_PREFIX}/cool-public-api-resource/$', CoolPublicAPIResource.as_view(), name='cool_resource'), | |
] |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from rest_framework.generics import GenericAPIView | |
from rest_framework.mixins import RetrieveModelMixin, ListModelMixin, CreateModelMixin | |
from .serializers import RestAPITokenSerializer | |
from .authentication import CustomRestAPIAuthentication | |
class RestAPITokenView(GenericAPIView, ListModelMixin, CreateModelMixin): | |
""" For listing, creating REST API tokens in your regular UI """ | |
authentication_classes = (TokenAuthentication,) # Use the normal auth class | |
serializer_class = RestAPITokenSerializer | |
def get_queryset(self): | |
return RESTAPIToken.objects.filter(user=self.request.user) | |
def post(self, request, *args, **kwargs): | |
return self.create(request, *args, **kwargs) | |
def get(self, request, *args, **kwargs): | |
return self.list(request, *args, **kwargs) | |
class CoolPublicAPIResource(GenericAPIView, ListModelMixin): | |
authentication_classes = (CustomRestAPIAuthentication,) | |
def get(self, request, *args, **kwargs): | |
return self.list(request, *args, **kwargs) |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment