restframework-simpleJWT重写认证机制

本文介绍了一个修改过的JWT认证类,通过缓存技术实现对用户对象的高效查找,提高验证速度并确保安全性。核心内容包括自定义认证方法、白名单和黑名单管理,以及如何利用access_token和refresh_token进行用户验证和刷新。
Python3.8

Python 是一种高级、解释型、通用的编程语言,以其简洁易读的语法而闻名,适用于广泛的应用,包括Web开发、数据分析、人工智能和自动化脚本

from rest_framework_simplejwt.authentication import JWTAuthentication
class MyJWTAuthentication(JWTAuthentication):
    '''
    修改JWT认证类,返回自定义User表对象
    '''

    def authenticate(self, request):
        header = self.get_header(request)
        if header is None:
            return None
        # 获取 access_token
        raw_token = self.get_raw_token(header)
        user = None
        token = None
        if raw_token is None:
            return None
        # 定义当前 access_token白名单
        wraw_token = str(raw_token, 'utf-8') + config.JWT_WHITE_LIST_TAG
        # 是否被录入黑名单
        if cache.has_key(str(validated_token) + config.JWT_BLACK_LIST_TAG):
            raise AuthenticationFailed(_('Token contained no recognizable user identification'))
        # 当出现 在白名单中时
        elif cache.has_key(wraw_token):
            # 在缓存中 获取 在 中间件 设置的 用户对象
            user = cache.get(wraw_token)["user_obj"]
            token = raw_token
        else:
            try:
                # 对收到的access_token 进行认证
                token = self.get_validated_token(raw_token)
                # 根据认证后的 access_token 获取用户对象
                user = self.get_user(token)
            except Exception as e:
                # 普通 access_token异常不进行处理 该怎样抛出响应就抛出响应
                #  原access_token异常,为刷新接口时,获取 request.data 的 refresh_token
                if request.data.get("refresh_token"):
                    refresh_token = request.data.get("refresh_token")
                    # 获取当前 refresh_token 的 有效时间
                    refresh_time_remaining = output_time_remaining(refresh_token)
                    # refresh_token 在有效期内
                    if refresh_time_remaining > 0:
                        # 且不在黑名单中
                        if not cache.has_key(refresh_token):
                            decoded_data = jwt_decode(str(refresh_token), config.JWT_SECRET_KEY, verify=False,
                                                      algorithms="HS256")
                            # 获取 用户对象
                            user = Person_info.objects.get(**{'person_id': decoded_data["user_id"]})
        return user, token

    def get_user(self, validated_token):
        try:
            user_id = validated_token['user_id']
        except KeyError:
            raise InvalidToken(_('Token contained no recognizable user identification'))
        try:
            user = Person_info.objects.get(**{'person_id': user_id})
        except Person_info.DoesNotExist:
            raise AuthenticationFailed(_('User not found'), code='user_not_found')
        return user

您可能感兴趣的与本文相关的镜像

Python3.8

Python3.8

Conda
Python

Python 是一种高级、解释型、通用的编程语言,以其简洁易读的语法而闻名,适用于广泛的应用,包括Web开发、数据分析、人工智能和自动化脚本

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值