本教程将指导您如何使用Django REST Framework构建一个基于权限的用户管理系统。Django REST Framework是一个功能强大的Web API框架,用于构建易于维护和扩展的API。我将从创建项目开始,逐步讲解如何设计数据模型、序列化器、视图、路由、数据库迁移以及使用APIfox测试API。
1.首先,我们需要安装Django和Django REST Framework。Django是一个高级的Python Web框架,它可以帮助我们快速构建安全、可维护的Web应用。Django REST Framework是基于Django的一个扩展,它让我们能够更轻松地构建Web API。
安装Django和Django REST Framework:
pip install django djangorestframework
2.接下来,我们创建一个名为UserManagementSystem的Django项目,并在其中创建一个名为user_management的应用。
创建项目:
django-admin startproject UserManagementSystem
cd UserManagementSystem
3.创建应用:
python manage.py startapp user_management
为了支持JWT(JSON Web Token)身份验证,我们需要安装djangorestframework-simplejwt:
pip install djangorestframework-simplejwt
接下来,在UserManagementSystem/settings.py中进行以下配置:
INSTALLED_APPS = [
# ...
'rest_framework',
'user_management',
]
REST_FRAMEWORK = {
'DEFAULT_PERMISSION_CLASSES': [
'rest_framework.permissions.IsAuthenticated',
],
'DEFAULT_AUTHENTICATION_CLASSES': [
'rest_framework_simplejwt.authentication.JWTAuthentication',
],
}
#Simple JWT settingsfrom datetime import timedelta
SIMPLE_JWT = {
'ACCESS_TOKEN_LIFETIME': timedelta(minutes=5),
'REFRESH_TOKEN_LIFETIME': timedelta(days=1),
'ROTATE_REFRESH_TOKENS': False,
'BLACKLIST_AFTER_ROTATION': True,
'UPDATE_LAST_LOGIN': False,
'ALGORITHM': 'HS256',
'SIGNING_KEY': SECRET_KEY,
'VERIFYING_KEY': None,
'AUDIENCE': None,
'ISSUER': None,
'AUTH_HEADER_TYPES': ('Bearer',),
'AUTH_HEADER_NAME': 'HTTP_AUTHORIZATION',
'USER_ID_FIELD': 'id',
'USER_ID_CLAIM': 'user_id',
'AUTH_TOKEN_CLASSES': ('rest_framework_simplejwt.tokens.AccessToken',),
'TOKEN_TYPE_CLAIM': 'token_type',
'SLIDING_TOKEN_REFRESH_EXP_CLAIM': 'refresh_exp',
'SLIDING_TOKEN_LIFETIME': timedelta(minutes=5),
'SLIDING_TOKEN_REFRESH_LIFETIME': timedelta(days=1),
}
AUTH_USER_MODEL = 'user_management.User'
接下来,我们需要设计用户数据模型、序列化器、视图和路由。这部分的代码可以参考上文中的示例代码,逐个文件创建并添加相应的代码。
from django.db import models
from django.contrib.auth.models import AbstractUser
class User(AbstractUser):
ROLE_CHOICES=(
('admin','管理员'),
('normal','普通用户')
)
role=models.CharField(max_length=10,choices=ROLE_CHOICES,default='normal',verbose_name='角色')
class Meta:
verbose_name='用户'
verbose_name_plural=verbose_name
from rest_framework import serializers
from .models import User
class UserSerializer(serializers.ModelSerializer):
class Meta:
model = User
fields = ['id', 'username', 'password', 'email', 'role'] # 保留自定义字段列表
extra_kwargs = {
'password': {'write_only': True}
}
from rest_framework import viewsets, status
from rest_framework.permissions import IsAuthenticated
from rest_framework.response import Response
from rest_framework_simplejwt.views import TokenObtainPairView
from rest_framework_simplejwt.serializers import TokenObtainPairSerializer
from django.core.paginator import Paginator
from django.shortcuts import get_object_or_404
from .serializers import UserSerializer
from .models import User
# 自定义令牌获取序列化器,继承自TokenObtainPairSerializer
class CustomTokenObtainPairSerializer(TokenObtainPairSerializer):
# 设置用户名字段为'username'
username_field = 'username'
# 重写validate方法
def validate(self, attrs):
# 调用父类的validate方法,存入登录用户的数据
data = super().validate(attrs)
# 获取当前用户
user = self.user
# 向返回的数据中添加用户名字段
data['username'] = user.username
return data
# 自定义令牌获取视图,继承自TokenObtainPairView
class CustomTokenObtainPairView(TokenObtainPairView):
# 设置序列化器类为自定义的CustomTokenObtainPairSerializer
serializer_class = CustomTokenObtainPairSerializer
# 用户视图集
class UserViewSet(viewsets.ModelViewSet):
# 指定序列化器类
serializer_class = UserSerializer
# 指定权限类,要求用户认证
permission_classes = [IsAuthenticated]
# 定义获取查询集的方法
def get_queryset(self):
# 如果请求用户是管理员,返回所有用户
if self.request.user.role == 'admin':
return User.objects.all()
else:
# 否则,只返回当前用户
return User.objects.filter(id=self.request.user.id)
# 定义处理用户列表请求的方法
def list(self, request):
users = self.get_queryset() # 获取查询集
paginator = Paginator(users, 10) # 使用分页器,每页10个用户
page_number = request.GET.get('page') # 获取页码
page_obj = paginator.get_page(page_number) # 获取当前页对象
serializer = self.get_serializer(page_obj, many=True) # 序列化当前页对象
return Response(serializer.data) # 返回序列化数据
# 定义处理获取单个用户请求的方法
def retrieve(self, request, pk=None):
# 如果请求用户不是管理员且请求的用户ID与当前用户ID不匹配,则拒绝请求
if not request.user.role == 'admin' and str(request.user.id) != pk:
return Response({'detail': 'You do not have permission to perform this action.'}, status=status.HTTP_403_FORBIDDEN)
user = get_object_or_404(self.get_queryset(), pk=pk) # 获取指定用户对象
serializer = self.get_serializer(user) # 序列化用户对象
return Response(serializer.data) # 返回序列化数据
# 定义处理删除用户请求的方法
def destroy(self, request, pk=None):
# 如果请求用户不是管理员,拒绝请求
if not request.user.role == 'admin':
return Response({'detail': 'You are not authorized to perform this action.'}, status=status.HTTP_403_FORBIDDEN)
user = get_object_or_404(self.get_queryset(), pk=pk) # 获取指定用户对象
user.delete() # 删除用户
return Response(status=status.HTTP_204_NO_CONTENT) # 返回204状态码表示删除成功
# 定义处理创建用户请求的方法
def create(self, request):
# 如果请求用户不是管理员,拒绝请求
if not request.user.role == 'admin':
return Response({'detail': 'You are not authorized to perform this action.'}, status=status.HTTP_403_FORBIDDEN)
data = request.data.copy() # 复制请求数据
data['role'] = 'normal' # 设置新用户角色为普通用户
serializer = self.get_serializer(data=data) # 创建序列化器实例
serializer.is_valid(raise_exception=True) # 验证数据
serializer.save() # 保存用户
return Response(serializer.data, status=status.HTTP_201_CREATED) # 返回序列化数据
# 定义处理更新用户请求的方法
def update(self, request, pk=None):
# 如果请求用户不是管理员且请求的用户ID与当前用户ID不匹配,则拒绝请求
if not request.user.role == 'admin' and str(request.user.id) != pk:
return Response({'detail': 'You do not have permission to perform this action.'}, status=status.HTTP_403_FORBIDDEN)
user = get_object_or_404(self.get_queryset(), pk=pk) # 获取指定用户对象
data = request.data.copy() # 复制请求数据
data['role'] = user.role # 不允许修改用户的角色
serializer = self.get_serializer(user, data=data) # 创建序列化器实例
serializer.is_valid(raise_exception=True) # 验证数据
serializer.save() # 更新用户
return Response(serializer.data, status=status.HTTP_200_OK) # 返回序列化数据
from django.contrib import admin
from django.urls import path, include
from rest_framework import routers
from user_management.views import CustomTokenObtainPairView, UserViewSet
router = routers.DefaultRouter()
router.register(r'users', UserViewSet, basename='user')
urlpatterns = [
path('admin/', admin.site.urls),
path('api/token/', CustomTokenObtainPairView.as_view(), name='token_obtain_pair'),
path('api/', include(router.urls)),
]
在定义了数据模型后,我们需要将其映射到数据库。执行以下命令进行数据库迁移:
python manage.py makemigrations
python manage.py migrate
python manage.py shell
from user_management.models import User
# 创建具有 admin 角色的用户
user = User.objects.create_user(username='admin', password='123', role='admin')
python manage.py runserver
APIfox是一个功能强大的API测试工具。我们可以使用APIfox对我们创建的API进行测试。
我们可以使用APIfox逐个运行测试用例,观察返回的结果。如果返回的数据和预期一致,说明我们的项目已经成功搭建完成。
在本教程中,我们从头开始搭建了一个基于权限的用户管理系统。我们使用Django REST Framework构建了API,并引入了Simple JWT支持JWT身份验证。通过这个项目,您可以学习到Django REST Framework的基本使用方法和概念,以及如何利用API测试工具(如APIfox)进行API测试。
接下来,您可以进一步优化项目,例如优化视图和序列化器的代码,或者添加更多的功能。如果本文对您有所帮助,请记得关注作者。您的支持是我持续的动力!