欢迎来到尧图网

客户服务 关于我们

您的位置:首页 > 文旅 > 文化 > Django REST framework 源码剖析-认证器详解(Authentication)

Django REST framework 源码剖析-认证器详解(Authentication)

2025/4/2 0:58:22 来源:https://blog.csdn.net/Mr_Sunqq/article/details/144560050  浏览:    关键词:Django REST framework 源码剖析-认证器详解(Authentication)

Django REST framework 源码剖析-认证器详解(Authentication)

Authentication

  • 身份验证始终在视图的最开始运行,在权限和限制检查发生之前,以及在允许任何其他代码继续之前。
  • request.user属性通常设置为contrib.auth包的user类的实例。
  • request.auth属性用于任何其他身份验证信息,例如,它可以用来表示请求签名时使用的身份验证令牌。

配置全局认证器

REST_FRAMEWORK = {'DEFAULT_AUTHENTICATION_CLASSES': ['rest_framework.authentication.BasicAuthentication','rest_framework.authentication.SessionAuthentication',]
}

基于 APIView 类的视图

from rest_framework.authentication import SessionAuthentication, BasicAuthentication
from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response
from rest_framework.views import APIViewclass ExampleView(APIView):authentication_classes = (SessionAuthentication, 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)

基于函数视图的 @api_view 装饰器

@api_view(['GET'])
@authentication_classes((SessionAuthentication, BasicAuthentication))
@permission_classes((IsAuthenticated,))
def example_view(request, format=None):content = {'user': unicode(request.user),  # `django.contrib.auth.User` instance.'auth': unicode(request.auth),  # None}return Response(content)

未经授权和禁止响应 (Unauthorized and Forbidden responses)

  • 当未经验证的请求被拒绝许可时,有两种不同的错误代码可能是适当的。
  • HTTP 401 响应必须始终包含 WWW-Authenticate 标头,指示客户端如何进行身份验证。
  • HTTP 403 响应不包括 WWW-Authenticate 标头。
HTTP 401 未经授权
HTTP 403 权限被拒绝

API参考

BasicAuthentication

  • 此身份验证方案使用 HTTP 基本身份验证,对用户的用户名和密码进行签名。基本身份验证通常仅适用于测试。
  • 如果您在产品中使用 BasicAuthentication,您必须确保您的 API 仅在 https 上可用。您还应确保您的 API 客户端始终在登录时重新请求用户名和密码,并且不会存储这些详细信息到持久存储器中
  • 成功 提供以下凭据
request.user 将是 Django User 实例。
request.auth 将是 None
  • 失败请求头示例
WWW-Authenticate: Basic realm="api"

TokenAuthentication

  • 此身份验证方案使用简单的基于令牌的 HTTP 身份验证方案。令牌认证适用于客户端-服务器设置,例如本地桌面和移动客户端。
  • 如果您在产品中使用 TokenAuthentication,您必须确保您的 API 仅在 https 上可用
  • 使用TokenAuthentication认证方式,需要提供以下配置
INSTALLED_APPS = (...'rest_framework.authtoken'
)
  • 创建令牌提供给用户
from rest_framework.authtoken.models import Tokentoken = Token.objects.create(user=...)
print token.key
  • 客户端进行身份验证, 请求头添加如下信息
Authorization: Token 9944b09199c62bcf9418ad846dd0e4bbdfc6ee4b
  • 如果想要在标头中使用不同的关键字,例如 Bearer,只需将 TokenAuthentication 子类化并设置 keyword 类变量
  • 成功通过身份验证,TokenAuthentication 提供以下凭据。
request.user 将是 Django User 实例。
request.auth 将是 rest_framework.authtoken.models.Token 实例。
  • 拒绝许可的未经身份验证的响应将导致带有相应的 WWW-Authenticate 标头的 HTTP 401 Unauthorized 响应
WWW-Authenticate: Token
  • curl 命令行工具可用于测试令牌认证 API
curl -X GET http://127.0.0.1:8000/api/example/ -H 'Authorization: Token 9944b09199c62bcf9418ad846dd0e4bbdfc6ee4b'

生成令牌 (Generating Tokens)

通过使用信号 (By using signals)
  • 如果您想要每个用户都拥有一个自动生成的令牌,您只需捕获用户的 post_save 信号即可
from django.conf import settings
from django.db.models.signals import post_save
from django.dispatch import receiver
from rest_framework.authtoken.models import Token@receiver(post_save, sender=settings.AUTH_USER_MODEL)
def create_auth_token(sender, instance=None, created=False, **kwargs):if created:Token.objects.create(user=instance)
  • 如果您已经创建了一些用户,则可以为所有现有用户生成令牌,如下所示
from django.contrib.auth.models import User
from rest_framework.authtoken.models import Tokenfor user in User.objects.all():Token.objects.get_or_create(user=user)
通过暴露 api 端点 (By exposing an api endpoint)
  • 当使用 TokenAuthentication 时,你可能希望为客户端提供一种获取给定用户名和密码的令牌的机制。REST framework 提供了一个内置的视图来提供此行为
  • 默认的 obtain_auth_token 视图显式使用 JSON 请求和响应,而不是使用 settings 中默认的渲染器和解析器类
  • 将 obtain_auth_token 视图添加到你的 URLconf
from rest_framework.authtoken import views
urlpatterns += [url(r'^api-token-auth/', views.obtain_auth_token)
]
  • 如果需要自定义版本的 obtain_auth_token 视图,可以通过子类化 ObtainAuthToken 类,并在 url conf 中使用它来实现
from rest_framework.authtoken.views import ObtainAuthToken
from rest_framework.authtoken.models import Token
from rest_framework.response import Responseclass 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})
  • urls.py 如下:
urlpatterns += [url(r'^api-token-auth/', CustomAuthToken.as_view())
]
  • 通过Django admin管理token
  • xxx_app/admin.py
from rest_framework.authtoken.admin import TokenAdminTokenAdmin.raw_id_fields = ('user',)
使用 Django manage.py 命令 (Using Django manage.py command)
  • 使用以下命令生成用户令牌
./manage.py drf_create_token <username>
  • 此命令将返回给定用户的 API 令牌,如果它不存在则创建它
Generated token 9944b09199c62bcf9418ad846dd0e4bbdfc6ee4b for user user1
  • 如果您想要重新生成令牌 (例如如果它已被破坏或泄露),您可以传递一个额外的参数
./manage.py drf_create_token -r <username>

SessionAuthentication

  • 此身份验证方案使用 Django 的默认会话后端进行身份验证。会话身份验证适用于与您的网站在同一会话上下文中运行的 AJAX 客户端。
  • 成功
request.user 是 Django User 实例。
request.auth 是 None
  • 失败则返回, 未经许可的未经身份验证的响应将导致 HTTP 403 Forbidden 响应

RemoteUserAuthentication

  • 此身份验证方案允许您将身份验证委托给 Web 服务器,该服务器设置 REMOTE_USER 环境变量。
  • 要使用它,你必须在你的 AUTHENTICATION_BACKENDS 设置中有 django.contrib.auth.backends.RemoteUserBackend (或者子类)
  • 默认情况下,RemoteUserBackend 为尚不存在的用户名创建 User 对象, 要更改此行为和其他行为,请参阅 Django 文档。
  • 成功通过身份验证,RemoteUserAuthentication 提供以下凭据:
request.user 是 Django User 实例。
request.auth 是 None
  • 失败则返回, 未经许可的未经身份验证的响应将导致 HTTP 403 Forbidden 响应

自定义身份验证 (Custom authentication)

  • 要实现自定义的身份验证方案,要继承 BaseAuthentication 类并且重写 .authenticate(self, request) 方法。如果认证成功,该方法应返回 (user, auth) 的二元元组,否则返回 None
  • 在某些情况下,您可能想要从 .authenticate() 方法引发 AuthenticationFailed 异常,而不是返回 None。
  • 通常,您应采取的方法是:
- 如果未尝试验证,返回 None。还将检查任何其他正在使用的身份验证方案。
- 如果尝试验证失败,则引发 AuthenticationFailed 异常。无论是否进行任何权限检查,都将立即返回错误响应,并且不会检查任何其他身份验证方案。
  • 重写 .authenticate_header(self, request) 方法。如果实现,则应返回将用作 HTTP 401 Unauthorized 响应中的 WWW-Authenticate 标头的值的字符串
  • 如果 .authenticate_header() 方法未被重写,则身份验证方案将在未经验证的请求被拒绝访问时返回 HTTP 403 Forbidden 响应。

自定义请求标头中名为 ‘X_USERNAME’ 的用户名指定的用户的任何传入请求进行身份验证

from django.contrib.auth.models import User
from rest_framework import authentication
from rest_framework import exceptionsclass ExampleAuthentication(authentication.BaseAuthentication):def authenticate(self, request):username = request.META.get('X_USERNAME')if not username:return Nonetry:user = User.objects.get(username=username)except User.DoesNotExist:raise exceptions.AuthenticationFailed('No such user')return (user, None)

版权声明:

本网仅为发布的内容提供存储空间,不对发表、转载的内容提供任何形式的保证。凡本网注明“来源:XXX网络”的作品,均转载自其它媒体,著作权归作者所有,商业转载请联系作者获得授权,非商业转载请注明出处。

我们尊重并感谢每一位作者,均已注明文章来源和作者。如因作品内容、版权或其它问题,请及时与我们联系,联系邮箱:809451989@qq.com,投稿邮箱:809451989@qq.com

热搜词