Django restframework auth 认证

在页面渲染和权限判断之前,判断用户是否可以访问该页面,身份验证是将传入请求与一组识别凭证(例如请求的用户或其签名的令牌)相关联的机制。然后,权限和限制策略可以使用这些凭据来确定请求是否应该被允许。

如何确定身份认证

身份验证方案的定义为“类列表”,即如果您需要定义身份认证的方案,需要编写验证类(通过继承Base类)。REST框架将尝试对列表中的每个类进行身份验证,并将设置request.userrequest.auth使用成功进行身份验证的第一个类的返回值(在编写过程中有可能编写了多个验证类,程序将一个类一个类进行匹配,程序将返回第一个匹配正确的值)。如果没有任何类通过身份验证,request.user则将设置为的实例django.contrib.auth.models.AnonymousUser,并将request.auth设置为None

未认证请求的request.user和值request.auth可以使用UNAUTHENTICATED_USERUNAUTHENTICATED_TOKEN设置进行修改。

在django restframework中,有四个已经提供好的,可以直接使用的认证类,BasicAuthentication && TokenAuthentication && SessionAuthenticatoin && RemoteUserAuthentication

BasicAuthentication:第一个样例

step1:DEFAULT_AUTHENTICATION_CLASSES设置全局设置默认身份验证方案,例如:

#settings.py
REST_FRAMEWORK = {
    'DEFAULT_AUTHENTICATION_CLASSES': [
        'rest_framework.authentication.BasicAuthentication',
    ]
}

step2:在Views文件中使用身份验证方案(并编号URL文件)

# url.py
from django.contrib import admin
from django.urls import path
from django.conf.urls import url

from pert.views import Example

urlpatterns = [
    path('admin/', admin.site.urls),
    path('example/', Example.as_view()),
]

# views.py
from rest_framework.authentication import SessionAuthentication, BasicAuthentication
from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response
from rest_framework.views import APIView

class ExampleView(APIView):
    # 由于在step1中设置了全局的验证方案,如果在编程过程中不需要使用全局验证方案则
    # authentication_classes = []
    authentication_classes = [BasicAuthentication]

    #设置,通过认证的用户具有访问权限
    permission_classes = [IsAuthenticated]

    def get(self, request, format=None):
        content = {
            'user': unicode(request.user),  # `django.contrib.auth.User` instance.
            'auth': unicode(request.auth),  # None
        }
        return Response(content)

step3:验证,当你get访问页面example时,您会发现跳出一个输入框【输入username && password】,(即匹配 默认的auth_user  MODEL )

自定义认证:第二个样例

step1:APP目录下生成utils目录,utils目录下生成authenticate.py文件,并编写认证类代码:

To implement a custom authentication scheme, subclass BaseAuthentication and override the .authenticate(self, request) method. The method should return a two-tuple of (user, auth) if authentication succeeds, or None otherwise.

In some circumstances instead of returning None, you may want to raise an AuthenticationFailed exception from the .authenticate() method.

Typically the approach you should take is:

  • If authentication is not attempted, return None. Any other authentication schemes also in use will still be checked.
  • If authentication is attempted but fails, raise a AuthenticationFailed exception. An error response will be returned immediately, regardless of any permissions checks, and without checking any other authentication schemes.

You may also override the .authenticate_header(self, request) method. If implemented, it should return a string that will be used as the value of the WWW-Authenticate header in a HTTP 401 Unauthorized response.

If the .authenticate_header() method is not overridden, the authentication scheme will return HTTP 403 Forbidden responses when an unauthenticated request is denied access.

# APPname.utils.authenticate
from pert import models
from rest_framework import exceptions
from rest_framework.authentication import BaseAuthentication


class MyAuthenticate(BaseAuthentication):
    def authenticate(self, request):
        token = request._request.GET.get('token')                         # 获取token参数
        token_obj = models.UserToken.objects.filter(token=token).first()  # 在数据库UserToken查找是否有相应的对象
        if not token_obj:                                                 # 如果没有,则报错
            raise exceptions.AuthenticationFailed('用户认证失败')
        return (token_obj.user, token_obj)                                # 这里需要返回两个对象,分别是UserInfo对象和UserToken对象
  
    def authenticate_header(self, request):  # 返回相应头信息
          pass

step2:DEFAULT_AUTHENTICATION_CLASSES设置全局设置默认身份验证方案,例如:

#settings.py
REST_FRAMEWORK = {
    'DEFAULT_AUTHENTICATION_CLASSES': [
        'rest_framework.authentication.BasicAuthentication',
        'rest_framework.authentication.SessionAuthentication',
        'appname.utils.authenticate.MyAuthenticate',
    ]
}

 step3:在Views文件中使用身份验证方案(并编号URL文件)

# url.py
from django.contrib import admin
from django.urls import path
from django.conf.urls import url

from pert.views import Example

urlpatterns = [
    path('admin/', admin.site.urls),
    path('api/v1/auth/', AuthView.as_view()),
    path('api/v1/order/', OrderView.as_view())
]

#models
from django.db import models

class UserInfo(models.Model):
    USER_TYPE = (
        (1, '普通用户'),
        (2, 'VIP'),
        (3, 'SVIP')
    )

    user_type = models.IntegerField(choices=USER_TYPE, default=1)
    username = models.CharField(max_length=32)
    password = models.CharField(max_length=64)

class UserToken(models.Model):
    user = models.OneToOneField(UserInfo,on_delete=models.CASCADE)
    token = models.CharField(max_length=64)

# views.py
class AuthView(View):
    def get(self, request, *args, **kwargs):
        # request.session["user"] = "szy"
        ret = {'code': 1000, 'msg': 'success', 'name': 'get method'}
        ret = json.dumps(ret, ensure_ascii=False)

        return HttpResponse(ret)

    def post(self, request, *args, **kwargs):
        ret = {'code': 1000, 'msg': None}
        try:
            data = JSONParser().parse(request)
            print(data)
            user = data["username"]
            print(user)
            pwd = data["password"]
            print(pwd)
            obj = models.UserInfo.objects.filter(username=user).first()

            if not obj:
                obj = models.UserInfo.objects.create(username=user, password=pwd)
                ret['code'] = 1001
                ret['msg'] = '创建用户成功'

            # 为用户创建token
            token = md5(user)
            # 存在就更新,不存在就创建
            models.UserToken.objects.update_or_create(user=obj, defaults={'token': token})
            ret['token'] = token
        except Exception as e:
            ret['code'] = 1002
            ret['msg'] = '请求异常'
        return JsonResponse(ret)

class OrderView(APIView):
    authentication_classes = [MyAuthenticate]
    # permission_classes = [IsAuthenticated]
    def get(self, request, *args, **kwargs):
        print(str(request.user))
        ret = {
            'code': 1024,
            'msg': '订单获取成功',
        }
        try:
            ret['data'] = ORDER_DICT
        except Exception as e:
            pass
        return JsonResponse(ret)

 step4:验证

  • 1
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值