覆盖Django Rest中的authToken视图

时间:2016-02-08 09:54:40

标签: python django inheritance django-rest-framework

我在Django中使用基于令牌的身份验证,除了返回令牌之外还需要添加User对象。

如何覆盖此课程视图?我需要在哪里添加此类并进行更改?目前这可以在rest_framework包中找到,我不想修改库。

from rest_framework import parsers, renderers
from rest_framework.authtoken.models import Token
from rest_framework.authtoken.serializers import AuthTokenSerializer
from rest_framework.response import Response
from rest_framework.views import APIView


class ObtainAuthToken(APIView):
    throttle_classes = ()
    permission_classes = ()
    parser_classes = (parsers.FormParser, parsers.MultiPartParser, parsers.JSONParser,)
    renderer_classes = (renderers.JSONRenderer,)
    serializer_class = AuthTokenSerializer
    print "dasdsa"

    def post(self, request):
        serializer = self.serializer_class(data=request.data)
        serializer.is_valid(raise_exception=True)
        user = serializer.validated_data['user']
        token, created = Token.objects.get_or_create(user=user)
        return Response({'token': token.key})


obtain_auth_token = ObtainAuthToken.as_view()

5 个答案:

答案 0 :(得分:3)

您应该将CustomClassAuthToken,路线默认网址扩展到CustomClass

from rest_framework_jwt.views import ObtainJSONWebToken

class JSONWebTokenAPIOverride(ObtainJSONWebToken):
    """
    Override JWT
    """
    def post(self, request):
        # Do whatever you want

然后在urls.py

url(
    r'^api-auth$',
    cache_page(0)(views.JSONWebTokenAPIOverride.as_view())
)

我希望它有所帮助

答案 1 :(得分:0)

我想覆盖一些默认的CRSF功能,并使用以下方法:

from rest_framework.authentication import SessionAuthentication

class SessionCsrfExemptAuthentication(SessionAuthentication):

    def enforce_csrf(self, request):
        # Do not perform a csrf check
        return False

然后在我的设置文件中,我通过以下方式引用它:

'DEFAULT_AUTHENTICATION_CLASSES': (
    'myapp.utils.authenticate.SessionCsrfExemptAuthentication',
    'rest_framework.authentication.BasicAuthentication',
    'rest_framework_jwt.authentication.JSONWebTokenAuthentication',
    'oauth2_provider.ext.rest_framework.OAuth2Authentication',
    'rest_framework_social_oauth2.authentication.SocialAuthentication',
),

这允许我导入现有功能,覆盖它并在设置文件中引用它。我想你可以在这里使用类似的方法。

答案 2 :(得分:0)

我使用选项JWT_RESPONSE_PAYLOAD_HANDLER 在回复中,我包含令牌到期时间戳用户

settings.py 中添加:

JWT_AUTH = {
        ...
        'JWT_RESPONSE_PAYLOAD_HANDLER':'<app_name>.functions.custom_jwt_response',
}

然后在 functions.py 中添加以下内容

def custom_jwt_response(token, user=None, request=None):

    import jwt
    jwt = jwt.decode(token, verify=False)

    return {
        'token': token,
        'token_exp': jwt['exp'],
        'user': UserSerializer(user, context={'request': request}).data
    }

答案 3 :(得分:0)

来自docs

首先需要扩展ObtainAuthToken类。

# views.py

from rest_framework.authtoken.views import ObtainAuthToken
from rest_framework.authtoken.models import Token
from rest_framework.response import Response

class CustomAuthToken(ObtainAuthToken):

    def post(self, request, *args, **kwargs):
        serializer = self.serializer_class(data=request.data,
                                       context={'request': request})
        serializer.is_valid(raise_exception=True)
        user = serializer.validated_data['user']
        token, created = Token.objects.get_or_create(user=user)
        return Response({
            'token': token.key,
            'user_id': user.pk,
            'email': user.email
        })

然后将CustomAuthToken类添加到您的urls.py中,就像view

# urls.py
from django.urls import path
from . import views

urlpatterns += [
    path(r'api-token-auth/', views.CustomAuthToken.as_view())
]

答案 4 :(得分:0)

这里的答案很好,但我认为它们没有充分利用继承。当我们继承一个类时,我们不应该只是尝试重新发明轮子,而应该使用super()关键字。这是我的代码示例,在该示例中,我想在执行身份验证请求之前将username参数转换为小写:

class GetAuthToken(ObtainAuthToken):
   """
   Override Django's ObtainAuthToken to provide custom way of authenticating user for token
   """
   def post(self, request, *args, **kwargs):
      #-- turn username to lowercase
      if ('username' in request.data):
         request.data['username'] = request.data['username'].lower()

      #-- perform normal function
      return super().post(request, *args, **kwargs)