下面是关于Django项目中使用JWT的实现代码的完整攻略,包括最基本的JWT的使用和带有自定义用户模型的JWT使用:
基本JWT的使用
步骤1:安装相关库
在Django项目中使用JWT,需要安装两个Python库:pyjwt
和django-rest-framework-jwt
,可以使用以下命令进行安装:
pip install pyjwt
pip install djangorestframework-jwt
步骤2:配置JWT
在Django项目的settings.py
文件中添加如下配置:
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework_jwt.authentication.JSONWebTokenAuthentication',
),
}
JWT_AUTH = {
'JWT_SECRET_KEY': '',
'JWT_ALGORITHM': 'HS256',
'JWT_ALLOW_REFRESH': True,
'JWT_REFRESH_EXPIRATION_DELTA': datetime.timedelta(days=7),
'JWT_EXPIRATION_DELTA': datetime.timedelta(hours=1),
}
其中,JWT_SECRET_KEY
是自定义的JWT密钥,可以在环境变量中定义。
步骤3:用户认证
在Django项目中,可以使用DRF的TokenObtainPairView
视图进行用户认证。假设我们的用户模型是Django自带的User
模型,那么可以创建一个视图类继承自TokenObtainPairView
,并指定用户模型为User
,如下所示:
from rest_framework_simplejwt.views import TokenObtainPairView
from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
from django.contrib.auth.models import User
class CustomTokenObtainPairSerializer(TokenObtainPairSerializer):
@classmethod
def get_user_model(cls):
return User
def validate(self, attrs):
data = super().validate(attrs)
data['username'] = self.user.username
return data
class CustomTokenObtainPairView(TokenObtainPairView):
serializer_class = CustomTokenObtainPairSerializer
这样,就可以在URL中使用CustomTokenObtainPairView.as_view()
来进行用户认证,并获取JWT。
步骤4:JWT的使用
获取JWT之后,可以将JWT作为请求头中的Authorization
字段,用于API调用上。例如,在Django视图中,可以使用如下方式获取JWT中的用户信息:
from rest_framework_jwt.authentication import JSONWebTokenAuthentication
class DemoView(APIView):
authentication_classes = (JSONWebTokenAuthentication,)
def get(self, request):
user = request.user
# do something
带有自定义用户模型的JWT使用
如果Django项目中使用的是自定义用户模型,那么需要对JWT进行相应的定制,以实现使用自定义用户模型的用户认证和获取JWT。以下是实现代码示例:
步骤1:安装相关库
安装django-allauth
和djangorestframework-simplejwt
,可以使用以下命令进行安装:
pip install django-allauth
pip install djangorestframework-simplejwt
步骤2:配置JWT
在Django项目的settings.py
文件中添加如下配置:
AUTH_USER_MODEL = 'accounts.User'
REST_FRAMEWORK = {
'DEFAULT_AUTHENTICATION_CLASSES': (
'rest_framework_simplejwt.authentication.JWTAuthentication',
),
}
SIMPLE_JWT = {
'ACCESS_TOKEN_LIFETIME': timedelta(minutes=60),
'REFRESH_TOKEN_LIFETIME': timedelta(days=7),
'ROTATE_REFRESH_TOKENS': False,
'JWT_SECRET_KEY': '',
'JWT_ALGORITHM': 'HS256',
'JWT_VERIFY': True,
'JWT_VERIFY_EXPIRATION': True,
'JWT_LEEWAY': 0,
'JWT_EXPIRATION_DELTA': timedelta(minutes=60),
'JWT_AUDIENCE': None,
'JWT_ISSUER': None,
'JWT_ALLOW_EXPIRED': False,
'JWT_REFRESH_EXPIRATION_DELTA': timedelta(days=7),
'JWT_AUTH_COOKIE': None,
}
其中,AUTH_USER_MODEL
为自定义用户模型,JWT_SECRET_KEY
是自定义的JWT密钥,可以在环境变量中定义。
步骤3:用户认证
在Django项目中,可以使用DRF的TokenObtainPairView
视图进行用户认证。在自定义用户模型中,可以通过以下方式创建一个用户认证视图类:
from rest_framework.views import APIView
from rest_framework_simplejwt.views import TokenObtainPairView
from allauth.socialaccount.providers.weibo.views import WeiboOAuth2Adapter
from rest_auth.registration.views import SocialLoginView
from rest_auth.serializers import TokenSerializer
from rest_auth.views import LoginView
from django.contrib.auth import login
from django.shortcuts import redirect
from rest_framework_simplejwt.tokens import RefreshToken
import datetime
class CustomLoginView(LoginView):
serializer_class = TokenSerializer
def post(self, request, *args, **kwargs):
serializer = self.get_serializer(data=request.data)
if serializer.is_valid(raise_exception=True):
time_delta = datetime.datetime.now() - datetime.datetime.fromtimestamp(
request.META.get('HTTP_USER_AGENT'), datetime.datetime).replace(tzinfo=None)
refresh = RefreshToken.for_user(serializer.validated_data['user'])
if time_delta.days == 0 and time_delta.seconds < 1800:
res = {"code": 200, "data": {"access_token": str(refresh.access_token)}, "msg": "OK"}
else:
res = {"code": 400, "msg": "验证码无效!"}
login(request, serializer.validated_data['user'])
response = Response(res)
response.set_cookie(key='token', value=res.get('data').get('access_token'),
expires=refresh.access_token.payload.get('exp'), httponly=True)
return response
class CustomTokenObtainPairView(TokenObtainPairView):
serializer_class = CustomTokenObtainPairSerializer
在该视图类中,使用allauth
库的WeiboOAuth2Adapter
进行社交登录(这是示例代码,根据使用情况进行相应的修改),使用rest_auth
库的SocialLoginView
进行社交登录认证,在登录完成后,将JWT写入cookie中。
步骤4:JWT使用
在Django视图中,可以使用如下方式获取JWT中的用户信息:
from rest_framework_simplejwt.authentication import JWTAuthentication
class DemoView(APIView):
authentication_classes = (JWTAuthentication,)
def get(self, request):
user = request.user
# do something
以上是使用自定义用户模型的JWT使用的实现代码示例。