1.概述
本次文章,主要分享如何基于restframe和django框架,对于用户表,和superuser管理员表,实现只有此管理员才能进行一些操作。例如,当我们对于用户表,只有相对应的管理员才能进行对其增删改查
2. 创建RESTframe视图
1.1 代码展示
url
from django.contrib import admin
from django.urls import path,include
from . import views
urlpatterns = [
# path('students/',views.students),
# path('students/<int:pk>/',views.students_detail),
# path('classes/',views.classes),
# path('classes/<int:pk>/',views.classes_detail),
path('students/',views.StudentsView.as_view()),
path('students/<int:pk>/',views.StudentDetailView.as_view()),
path('users/',views.UserView.as_view()),
path('users/<int:pk>/',views.UserDetailView.as_view())
]
from rest_framework.urlpatterns import format_suffix_patterns
# 可以使用allowed = ['json','html'] 参数指定允许的后缀
urlpatterns = format_suffix_patterns(urlpatterns)
实现User模型序列化
from rest_framework import serializers
from rest_app.models import *
from django.contrib.auth.models import User
class ClassesRelatedField(serializers.RelatedField):
def to_representation(self, value):
return {'id':value.id, 'name':value.name}
# 根据班级获取班级所有学生信息
class StudentSerializer(serializers.ModelSerializer):
# classes 属性名和Student类中外键属性名相同
classes = ClassesRelatedField(read_only=True)
class Meta:
model = Student
fields = ['id', 'name', 'age', 'sex','classes'] #或者 ='__all__'
class ClassesSerializer(serializers.ModelSerializer):
# students 属性要和student类中外键classes属性 related_name='students'
# 多条记录 指定many = True, read_only=True
students = StudentSerializer(many=True, read_only=True)
class Meta:
model = Classes
fields = ['id', 'name','students']
class UserSerializer(serializers.ModelSerializer):
class Meta:
model = User
fields = ['id','username']
views
from django.shortcuts import render
from django.views.decorators.csrf import csrf_exempt
from rest_app.models import *
from rest_app.app_serializer import StudentSerializer,ClassesSerializer,UserSerializer
from django.http import JsonResponse,HttpResponse,Http404
from rest_framework.parsers import JSONParser
from rest_framework.request import Request
from rest_framework.response import Response
from rest_framework import status
from rest_framework.decorators import api_view
from rest_framework.views import APIView
from rest_framework import mixins, generics
from rest_framework import permissions
from django.contrib.auth.models import User
# Create your views here.
'''
新增 post students/
删除 delete students/id/
修改 put students/id/
查询一个 get students/id/
查询所有 get students/
'''
# 优化代码:
class StudentsView(generics.ListCreateAPIView):
# 指定需要操作的数据与序列化类
queryset = Student.objects.all()
serializer_class = StudentSerializer
# 添加身份验证功能
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
class StudentDetailView(generics.RetrieveUpdateDestroyAPIView):
queryset = Student.objects.all()
serializer_class = StudentSerializer
# 添加身份验证功能
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
class UserView(generics.ListAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
class UserDetailView(generics.RetrieveAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
1.2 效果展示
3. 数据和用户关联管理
3.1代码展示
新增权限
# rest_app/app_permissions.py
from rest_framework import permissions
# 新增权限类: 如果不是当前登录的用户,无法修改其他用户对应的数据
class IsOwnerOrReadOnly(permissions.BasePermission):
def has_object_permission(self, request,view, obj):
if request.method in permissions.SAFE_METHODS:
return True
return obj.owner == request.user
views
from django.shortcuts import render
from django.views.decorators.csrf import csrf_exempt
from rest_app.models import *
from rest_app.app_serializer import StudentSerializer,ClassesSerializer,UserSerializer
from django.http import JsonResponse,HttpResponse,Http404
from rest_framework.parsers import JSONParser
from rest_framework.request import Request
from rest_framework.response import Response
from rest_framework import status
from rest_framework.decorators import api_view
from rest_framework.views import APIView
from rest_framework import mixins, generics
from rest_framework import permissions
from django.contrib.auth.models import User
from rest_app.app_permissions import IsOwnerOrReadOnly
# Create your views here.
'''
新增 post students/
删除 delete students/id/
修改 put students/id/
查询一个 get students/id/
查询所有 get students/
'''
# 优化代码:
class StudentsView(generics.ListCreateAPIView):
# 指定需要操作的数据与序列化类
queryset = Student.objects.all()
serializer_class = StudentSerializer
# 添加身份验证功能
permission_classes = [permissions.IsAuthenticatedOrReadOnly]
# 重写新增方法,在保存Student时候关联用户
def perform_create(self, serializer):
serializer.save(owner=self.request.user)
class StudentDetailView(generics.RetrieveUpdateDestroyAPIView):
queryset = Student.objects.all()
serializer_class = StudentSerializer
# 添加身份验证功能
# permission_classes = [permissions.IsAuthenticatedOrReadOnly]
permission_classes = [IsOwnerOrReadOnly]
class UserView(generics.ListAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
class UserDetailView(generics.RetrieveAPIView):
queryset = User.objects.all()
serializer_class = UserSerializer
models
from django.db import models
# Create your models here.
class Classes(models.Model):
name = models.CharField(max_length=20, verbose_name='班级名称')
class Student(models.Model):
SEX_CHOICES = ((1,'男'),(2,'女'))
name = models.CharField(max_length=20,verbose_name='姓名')
age = models.IntegerField(null=True, blank=True, verbose_name='年龄')
sex = models.IntegerField(choices=SEX_CHOICES,default=1,verbose_name='性别')
# 多方建立外键
classes = models.ForeignKey(Classes, related_name='students' ,on_delete=models.SET_NULL, null=True, verbose_name='班级')
owner = models.ForeignKey("auth.User",related_name='students', on_delete=models.SET_NULL, null=True)
序列化
from rest_framework import serializers
from rest_app.models import *
from django.contrib.auth.models import User
# 根据学生获取学生所在班级
# class ClassesSerializer(serializers.ModelSerializer):
# class Meta:
# model = Classes
# fields = ['id', 'name']
# class StudentSerializer(serializers.ModelSerializer):
# # 新增班级属性
# classes = ClassesSerializer() # 一定要加括号,创建实例对象。否则,只能输出id
# class Meta:
# model = Student
# fields = ['id', 'name', 'age', 'sex','classes'] #或者 ='__all__'
class ClassesRelatedField(serializers.RelatedField):
def to_representation(self, value):
return {'id':value.id, 'name':value.name}
# 根据班级获取班级所有学生信息
class StudentSerializer(serializers.ModelSerializer):
# classes 属性名和Student类中外键属性名相同
classes = ClassesRelatedField(read_only=True)
# 添加用户属性
owner = serializers.ReadOnlyField(source="owner.username") # 只需要查看username
class Meta:
model = Student
fields = ['id', 'name', 'age', 'sex','classes','owner'] #或者 ='__all__'
class ClassesSerializer(serializers.ModelSerializer):
# students 属性要和student类中外键classes属性 related_name='students'
# 多条记录 指定many = True, read_only=True
students = StudentSerializer(many=True, read_only=True)
class Meta:
model = Classes
fields = ['id', 'name','students']
class UserSerializer(serializers.ModelSerializer):
class Meta:
model = User
fields = ['id','username']