首页 > 其他分享 >8.simple-jwt

8.simple-jwt

时间:2024-08-14 21:05:14浏览次数:12  
标签:simple JWT jwt rest framework user simplejwt refresh

【一】simple-jwt快速使用

1)安装

pip install djangorestframework-simplejwt

2)使用

1.签发

  • 路由 配置

    from django.urls import path
    from rest_framework_simplejwt.views import token_obtain_pair
    
    urlpatterns = [
        path('login/', token_obtain_pair)
    ]
    

2.认证

  • 视图类

    from rest_framework.permissions import IsAuthenticated
    from rest_framework_simplejwt.authentication import JWTTokenUserAuthentication
    
    
    class UserAPIView(APIView):
        # 认证
        authentication_classes = [JWTAuthentication]
        # 权限
        permission_classes = [IsAuthenticated]
    
        def get(self, request):
            return Response('已登陆')
    
  • 使用

    • 在 请求头 内添加:
    • {Authorization":"Bearer+空格+返回的access内容"}

3.补充

  • 如果不加权限

    • 携带了token,就进行校验;未携带token,不进行认证校验
  • 返回的refresh有效时间长,access有效时间短,

    • access是由refresh生成而来
    • 每次签发都会更新refreshaccess

【二】simple-jwt的配置文件

1)Simple JWT的默认配置

# JWT配置
SIMPLE_JWT = {
    # Access Token的有效期
    'ACCESS_TOKEN_LIFETIME': timedelta(minutes=5),
    # Refresh Token的有效期
    'REFRESH_TOKEN_LIFETIME': timedelta(days=7),  
    
    # 对于大部分情况,设置以上两项就可以了,以下为默认配置项目,可根据需要进行调整
    
    # 是否自动刷新Refresh Token
    'ROTATE_REFRESH_TOKENS': False,  
    # 刷新Refresh Token时是否将旧Token加入黑名单,如果设置为False,则旧的刷新令牌仍然可以用于获取新的访问令牌。需要将'rest_framework_simplejwt.token_blacklist'加入到'INSTALLED_APPS'的配置中
    'BLACKLIST_AFTER_ROTATION': False,  
    'ALGORITHM': 'HS256',  # 加密算法
    'SIGNING_KEY': settings.SECRET_KEY,  # 签名密匙,这里使用Django的SECRET_KEY
    # 如为True,则在每次使用访问令牌进行身份验证时,更新用户最后登录时间
    "UPDATE_LAST_LOGIN": False, 
    # 用于验证JWT签名的密钥返回的内容。可以是字符串形式的密钥,也可以是一个字典。
    "VERIFYING_KEY": "",
    "AUDIENCE": None,# JWT中的"Audience"声明,用于指定该JWT的预期接收者。
    "ISSUER": None, # JWT中的"Issuer"声明,用于指定该JWT的发行者。
    "JSON_ENCODER": None, # 用于序列化JWT负载的JSON编码器。默认为Django的JSON编码器。
    "JWK_URL": None, # 包含公钥的URL,用于验证JWT签名。
    "LEEWAY": 0, # 允许的时钟偏差量,以秒为单位。用于在验证JWT的过期时间和生效时间时考虑时钟偏差。
    # 用于指定JWT在HTTP请求头中使用的身份验证方案。默认为"Bearer"
    "AUTH_HEADER_TYPES": ("Bearer",), 
    # 包含JWT的HTTP请求头的名称。默认为"HTTP_AUTHORIZATION"
    "AUTH_HEADER_NAME": "HTTP_AUTHORIZATION", 
     # 用户模型中用作用户ID的字段。默认为"id"。
    "USER_ID_FIELD": "id",
     # JWT负载中包含用户ID的声明。默认为"user_id"。
    "USER_ID_CLAIM": "user_id",
    # 用于指定用户身份验证规则的函数或方法。默认使用Django的默认身份验证方法进行身份验证。
    "USER_AUTHENTICATION_RULE": "rest_framework_simplejwt.authentication.default_user_authentication_rule",
    #  用于指定可以使用的令牌类。默认为"rest_framework_simplejwt.tokens.AccessToken"。
    "AUTH_TOKEN_CLASSES": ("rest_framework_simplejwt.tokens.AccessToken",),
    # JWT负载中包含令牌类型的声明。默认为"token_type"。
    "TOKEN_TYPE_CLAIM": "token_type",
    # 用于指定可以使用的用户模型类。默认为"rest_framework_simplejwt.models.TokenUser"。
    "TOKEN_USER_CLASS": "rest_framework_simplejwt.models.TokenUser",
    # JWT负载中包含JWT ID的声明。默认为"jti"。
    "JTI_CLAIM": "jti",
    # 在使用滑动令牌时,JWT负载中包含刷新令牌过期时间的声明。默认为"refresh_exp"。
    "SLIDING_TOKEN_REFRESH_EXP_CLAIM": "refresh_exp",
    # 滑动令牌的生命周期。默认为5分钟。
    "SLIDING_TOKEN_LIFETIME": timedelta(minutes=5),
    # 滑动令牌可以用于刷新的时间段。默认为1天。
    "SLIDING_TOKEN_REFRESH_LIFETIME": timedelta(days=1),
    # 用于生成访问令牌和刷新令牌的序列化器。
    "TOKEN_OBTAIN_SERIALIZER": "rest_framework_simplejwt.serializers.TokenObtainPairSerializer",
    # 用于刷新访问令牌的序列化器。默认
    "TOKEN_REFRESH_SERIALIZER": "rest_framework_simplejwt.serializers.TokenRefreshSerializer",
    # 用于验证令牌的序列化器。
    "TOKEN_VERIFY_SERIALIZER": "rest_framework_simplejwt.serializers.TokenVerifySerializer",
    # 用于列出或撤销已失效JWT的序列化器。
    "TOKEN_BLACKLIST_SERIALIZER": "rest_framework_simplejwt.serializers.TokenBlacklistSerializer",
    # 用于生成滑动令牌的序列化器。
    "SLIDING_TOKEN_OBTAIN_SERIALIZER": "rest_framework_simplejwt.serializers.TokenObtainSlidingSerializer",
    # 用于刷新滑动令牌的序列化器。
    "SLIDING_TOKEN_REFRESH_SERIALIZER": "rest_framework_simplejwt.serializers.TokenRefreshSlidingSerializer",
}

2)自定义配置方式

  • setting.py

    from datetime import timedelta
    SIMPLE_JWT={
        # Access Token的有效期
        'ACCESS_TOKEN_LIFETIME': timedelta(minutes=60), 
        # Refresh Token的有效期
        'REFRESH_TOKEN_LIFETIME': timedelta(days=7), 
    }
    

【三】定制返回格式

  • 新建文件rewrite_jwt.py

  • 重写validate,返回的内容就是更改的格式

    from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
    
    
    class FormatToken(TokenObtainPairSerializer):
        def validate(self, attrs):
            old_data = super().validate(attrs)
            data = {'code': 100,
                    'msg': '登录成功成功',
                    'username': self.user.username,
                    'refresh': old_data.get('refresh'),
                    'access': old_data.get('access'),
                    }
            return data
    
  • 全局配置

    SIMPLE_JWT = {
        "TOKEN_OBTAIN_SERIALIZER": "App.tool.rewrite_jwt.FormatToken",
    }
    

【四】更改载荷

  • 与定制类似

  • 在validate的序列化类内重写一个类方法,返回的内容就是重写的载荷

    from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
    
    
    class FormatToken(TokenObtainPairSerializer):
        @classmethod
        def get_token(cls, user):
            token = super().get_token(user)
            token['username'] = user.username
            return token
        
        def validate(self, attrs):
            ......
            return data
    

【五】扩写auth的user表

  • 尽量在未迁移之前扩写

    • 删库,删迁移文件
    • (app内migrations的新增文件、django内置app的admin与auth)
  • 配置文件

    AUTH_USER_MODEL='App文件名.新的表名'
    

【六】多方式登录

  • 系列化类

    from rest_framework import serializers
    from rest_framework_simplejwt.tokens import RefreshToken
    
    
    # 只用于校验
    class LoginSerializer(serializers.Serializer):
        username = serializers.CharField()
        password = serializers.CharField()
    
        def validate(self, attrs):
            # 获取前端传入的信息
            username = attrs.get('username')
            password = attrs.get('password')
            # 正则判断登录方式
            import re
            from django.contrib.auth.models import User
            if re.match(r'^1[3-9][0-9]{9}$', username):
                # 手机登录
                user = User.objects.filter(mobile=username).first()
            elif re.match(r'^.+@.+$', username):
                # 邮箱登录
                user = User.objects.filter(email=username).first()
            else:
                # 账号登录
                user = User.objects.filter(username=username).first()
            # 校验密码
            if user and user.check_password(password):
                refresh = RefreshToken.for_user(user)
                self.context['refresh'] = str(refresh)
                self.context['access'] = str(refresh)
                print(self.context)
                return attrs
            else:
                raise '用户名或密码错误'
    
  • 视图类

    class LoginAPIView(APIView):
        def post(self, request):
            serializer = LoginSerializer(data=request.data)
            serializer.is_valid(raise_exception=True)
            refresh = serializer.context['refresh']
            access = serializer.context['access']
            return Response({'code': 100, 'mas': '登录成功', 'refresh': refresh, 'access': access})
    

【七】自定义用户表 的签发、认证

1)签发

  • 序列化类

    class LoginSerializer(serializers.Serializer):
        username = serializers.CharField()
        password = serializers.CharField()
    
        def validate(self, attrs):
            # 获取前端传入的信息
            username = attrs.get('username')
            password = attrs.get('password')
            # 选择用户表进行校验
            user = User.objects.filter(username=username).first()
            if user and user.check_password(password):
                refresh = RefreshToken.for_user(user)
                self.context['refresh'] = str(refresh)
                self.context['access'] = str(refresh)
                return attrs
            else:
                raise '用户名或密码错误'
    
  • 视图类

    class LoginAPIView(APIView):
        def post(self, request):
            serializer = LoginSerializer(data=request.data)
            serializer.is_valid(raise_exception=True)
            refresh = serializer.context['refresh']
            access = serializer.context['access']
            return Response({'code': 100, 'mas': '登录成功', 'refresh': refresh, 'access': access})
    

2)认证

  • 新建文件auth.py

  • 重写authenticate

    from rest_framework.authentication import BaseAuthentication
    from rest_framework_simplejwt.tokens import AccessToken
    
    from rest_framework.authtoken.admin import User
    
    
    class JsonWebTokenCommonAuthentication(BaseAuthentication):
        def authenticate(self, request):
            token = request.META.get('HTTP_AUTHORIZATION')
            if token:
                # 获取载荷的数据
                res = AccessToken(token=token)
                user_id = res['user_id']
                user = User.objects.get(pk=user_id)
                return user,token
            else:
                raise '未携带认证信息'
    
  • 使用

    class UserAPIView(APIView):
        # 自定义认证
        from App.tool.auth import JsonWebTokenCommonAuthentication
        authentication_classes = [JsonWebTokenCommonAuthentication]
    
        def get(self, request):
            return Response('已登陆')
    

标签:simple,JWT,jwt,rest,framework,user,simplejwt,refresh
From: https://www.cnblogs.com/Mist-/p/18359780

相关文章

  • 7.接口文档,JWT介绍
    【一】接口文档1)公司使用使用world编写MD共享文档第三方平台:如:https://www.showdoc.com.cn/公司自研2)主要内容如下说明变更记录全局错误相关接口简要描述请求URL请求方式参数返回示例返回参数说明备注3)字段生成(coreapi使用)安装pipinstal......
  • SimpleJarBoot 简单程序启动器
    ​ 介绍Jar包的程序启动器脚本Jar脚本,Jar运行脚本,Jar包脚本,Jar服务启动脚本安装脚本if[-f/usr/bin/curl];thencurl-sSOhttps://gitee.com/wl4837/simple-jar-boot/raw/master/simple-jar-boot.sh;elsewget-Osimple-jar-boot.shhttps://gitee.com/wl4837/sim......
  • 【CTF | WEB】002、攻防世界WEB题目之simple_php
    文章目录simple_php题目描述:解题思路:原理simple_php题目描述:小宁听说php是最好的语言,于是她简单学习之后写了几行php代码。解题思路:打开场景<?phpshow_source(__FILE__);include("config.php");$a=@$_GET['a'];$b=@$_GET['b'];if($a==0and$a){......
  • BugKu CTF Misc:被勒索了 & disordered_zip & simple MQTT & 请攻击这个压缩包
    前言BugKu是一个由乌云知识库(wooyun.org)推出的在线漏洞靶场。乌云知识库是一个致力于收集、整理和分享互联网安全漏洞信息的社区平台。BugKu旨在提供一个实践和学习网络安全的平台,供安全爱好者和渗透测试人员进行挑战和练习。它包含了各种不同类型的漏洞场景,如Web漏洞、系统......
  • .NET 8.0 中使用 JWT(JSON Web Token)进行身份验证和授权
    在.NET8.0中使用JWT(JSONWebToken)进行身份验证和授权,通常需要以下几个步骤:安装必要的NuGet包:Microsoft.AspNetCore.Authentication.JwtBearer配置JWT认证:在Program.cs或Startup.cs中配置JWT认证。生成和验证JWT:创建一个方法来生成JWT。在控制器中使用JWT......
  • 详细分析JWT的基本知识(附Demo)
    目录前言1.基本知识2.JWT验证过程3.Demo前言对于Java的基本知识推荐阅读:java框架零基础从入门到精通的学习路线附开源项目面经等(超全)【Java项目】实战CRUD的功能整理(持续更新)1.基本知识紧凑的、URL-safe的表示方式,通常用于认证和信息交换JWT由三部分组成......
  • Date日期类和SimpleDateFormat日期格式化类day12
    packagecom.shujia.day12;importjava.text.SimpleDateFormat;importjava.util.Date;/*日期相关的类:Date构造方法:publicDate()获取当前时间的Date类型格式:FriAug0920:33:11CST2024publicDate(longdate)获取指......
  • jwt伪造身份组组组合拳艰难通关
    前言现在的攻防演练不再像以往那样一个漏洞直捣黄龙,而是需要各种组合拳才能信手拈来,但是有时候使尽浑身解数也不能称心如意。前期信息收集首先是拿到靶标的清单访问系统的界面,没有什么能利用的功能点首先进行目录扫描,扫描发现存在xxx.zip的文件放置在web目录上一般zip文件......
  • ImportError:无法从“jwt.algorithms”导入名称“RSAAlgorithm”
    RSAAlgorithmPyJWT算法方法无法导入,但我确实安装了PyJWT错误:ImportError:cannotimportname'RSAAlgorithm'from'jwt.algorithms'我通过运行以下命令检查了该包是否可用:poetryshow|grep-ipyjwtpyjwt2.9.0J......
  • JWT的基本使用
    引言在当今数字化时代,Web应用的安全性已成为开发者和企业关注的焦点。随着分布式系统和微服务架构的兴起,传统的会话管理认证方法,例如基于Cookie和session的会话,已经显示出了其局限性。正是在这种背景下,JSONWebTokens(JWT)作为一种轻量级、自包含的认证机制应运而生。JWT允许......