Django REST framweork
一:REST framweork 单表序列化例子
1.新建一个Django项目并创建一个APP
目录结构:
2. sudo pip3 install djangorestframework markdown django-filter # 安装所需模块
3.settings.py
INSTALLED_APPS = [ .... 'rest_framework', ]
4.编写测试模型:models.py
from django.db import models # Create your models here. class Classg(models.Model): cname = models.CharField(max_length=20) number = models.IntegerField()
teacher = models.ManyToManyField('Teacher', related_name='tracks') class Studnet(models.Model): sname = models.CharField(max_length=20) age = models.IntegerField() sex = models.BooleanField(default=0) classg = models.ForeignKey('Classg', related_name='tracks', on_delete=None) course = models.OneToOneField('Course', on_delete=None) class Course(models.Model): cname = models.CharField(max_length=20) class Teacher(models.Model): tname = models.CharField(max_length=20)
# 在本项目的根目录的终端进行同步迁移:
- python3 manage.py migrate
- python3 manage.py makemigrations
- python3 manage.py migrate
5.测试数据插入:在本项目的跟目录创建一个 insert_data.py
import os, django # 外部调用 Django models os.environ.setdefault("DJANGO_SETTINGS_MODULE", "proj.settings") django.setup() from celeryapp01.models import * import sys c1 = Classg.objects.create(cname='三年级一班', number=30) c2 = Classg.objects.create(cname='三年级二班', number=60) s1 = Course.objects.create(cname='数学') s2 = Course.objects.create(cname='语文') st1 = Studnet.objects.create(sname='张三', age=28, sex=1, classg=c1, course=s1) st2 = Studnet.objects.create(sname='李四', age=29, sex=0, classg=c2, course=s2) t1 = Teacher.objects.create(tname='比利') t2 = Teacher.objects.create(tname='许Var强') # 多对多正向插入 c1.teacher.add(t1) c2.teacher.add(t2)
6.celeryapp01 下创建 rest_serializer.py
from rest_framework import serializers from celeryapp01 import models class StudentSerizlizer(serializers.HyperlinkedModelSerializer): class Meta: model = models.Studnet fields = ('sname', 'age', 'sex',) # 这里将 你所想展示出来的字段
7.celeryapp01 下创建 rest_views.py
from rest_framework import viewsets from celeryapp01 import models from celeryapp01.rest_serializer import StudentSerizlizer class StudentViewSet(viewsets.ModelViewSet): queryset = models.Studnet.objects.all() serializer_class = StudentSerizlizer
8.在主路由的 urls.py :
from django.contrib import admin from django.urls import path,include urlpatterns = [ path('admin/', admin.site.urls), path(r'celeryapp01/', include('celeryapp01.api_urls')), ]
9.app的二级路由 api_urls.py:
from django.urls import path,include from celeryapp01 import views from rest_framework import routers from celeryapp01.rest_views import StudentViewSet router = routers.DefaultRouter() router.register(r'students', StudentViewSet) urlpatterns = [ path(r'api/', include(router.urls)), ]
# 逻辑关系
10.访问
------------------------以上是单表序列化--------------------------------
二:REST framweork 多表序列化例子
1.一对一:在 rest_serializer.py 添加如下
# 一对一,一个学生对应一个总分表的行对象 class StudentSerizlizer(serializers.HyperlinkedModelSerializer): cname = serializers.CharField(source='course.cname') # 查询与之关联的一对一关系字段 class Meta: model = models.Studnet fields = ('sname', 'age', 'sex', 'cname') class CourseSerizlizer(serializers.HyperlinkedModelSerializer): class Meta: model = models.Course fields = ('cname',)
rest_views.py 添加如下:
class StudentViewSet(viewsets.ModelViewSet): queryset = models.Studnet.objects.all() serializer_class = StudentSerizlizer class CourseViewSet(viewsets.ModelViewSet): queryset = models.Course.objects.all() serializer_class = CourseSerizlizer
api_urls.py 添加如下:
router.register(r'students', StudentViewSet) router.register(r'courses', CourseViewSet)
访问:
2.多对多(多个班级对应多个老师,多个老师对应多个班级):在 rest_serializer.py 添加如下
class ClassgSerizlizer(serializers.HyperlinkedModelSerializer): tracks = serializers.StringRelatedField(many=True) # 一对多 class Meta: model = models.Classg fields = ('cname', 'number', 'tracks') class TeacherSerizlizer(serializers.HyperlinkedModelSerializer): tracks = serializers.PrimaryKeyRelatedField(many=True, read_only=True) # 多对多 class Meta: model = models.Teacher fields = ('tname','tracks')
rest_views.py 添加如下:
class ClassgViewSet(viewsets.ModelViewSet): queryset = models.Classg.objects.all() serializer_class = ClassgSerizlizer class TeacherViewSet(viewsets.ModelViewSet): queryset = models.Teacher.objects.all() serializer_class = TeacherSerizlizer
api_urls.py:与一对一一样,换成相应的类一下即可
访问:
3.一对多(一个班级对应多个学生)rest_serializer.py添加如下:
class ClassgSerizlizer(serializers.HyperlinkedModelSerializer): tracks = serializers.StringRelatedField(many=True) # 一对多必须要添加这行代码 class Meta: model = models.Classg fields = ('cname', 'number', 'tracks') class StudentSerizlizer(serializers.HyperlinkedModelSerializer): cname = serializers.CharField(source='course.cname') # 查询与之相关联的行对象 class Meta: model = models.Studnet fields = ('sname', 'age', 'sex', 'cname')
rest_views.py :
class ClassgViewSet(viewsets.ModelViewSet): queryset = models.Classg.objects.all() serializer_class = ClassgSerizlizer
class TeacherViewSet(viewsets.ModelViewSet): queryset = models.Teacher.objects.all() serializer_class = TeacherSerizlizer
启动:
---------------------------------------------------------------------------
完整代码:
rest_serializer.py
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
from rest_framework import serializers from celeryapp01 import models class ClassgSerizlizer(serializers.HyperlinkedModelSerializer): tracks = serializers.StringRelatedField(many=True) class Meta: model = models.Classg fields = ('cname', 'number', 'tracks') class StudentSerizlizer(serializers.HyperlinkedModelSerializer): cname = serializers.CharField(source='course.cname') class Meta: model = models.Studnet fields = ('sname', 'age', 'sex', 'cname') class CourseSerizlizer(serializers.HyperlinkedModelSerializer): class Meta: model = models.Course fields = ('cname',) class TeacherSerizlizer(serializers.HyperlinkedModelSerializer): tracks = serializers.PrimaryKeyRelatedField(many=True, read_only=True) class Meta: model = models.Teacher fields = ('tname', 'tracks' )
rest_views.py
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
from rest_framework import viewsets from celeryapp01 import models from celeryapp01.rest_serializer import StudentSerizlizer, ClassgSerizlizer,CourseSerizlizer,TeacherSerizlizer class StudentViewSet(viewsets.ModelViewSet): queryset = models.Studnet.objects.all() serializer_class = StudentSerizlizer class CourseViewSet(viewsets.ModelViewSet): queryset = models.Course.objects.all() serializer_class = CourseSerizlizer class ClassgViewSet(viewsets.ModelViewSet): queryset = models.Classg.objects.all() serializer_class = ClassgSerizlizer class TeacherViewSet(viewsets.ModelViewSet): queryset = models.Teacher.objects.all() serializer_class = TeacherSerizlizer
api_urls.py
![](https://images.cnblogs.com/OutliningIndicators/ContractedBlock.gif)
from django.conf.urls import url,include from celeryapp01 import views from rest_framework import routers from celeryapp01.rest_views import StudentViewSet, ClassgViewSet, CourseViewSet,TeacherViewSet router = routers.DefaultRouter() router.register(r'students', StudentViewSet) router.register(r'courses', CourseViewSet) router.register(r'classgs', ClassgViewSet) router.register(r'teachers', TeacherViewSet) urlpatterns = [ url(r'api/', include(router.urls)), ]
总结:
1.具有一对多、多对多关系的model,也想序列化,必须要在关联字段里添加参数 :related_name='tracks' 如:
classg = models.ForeignKey('Classg', related_name='tracks', on_delete=None)
2.
tracks = serializers.StringRelatedField(many=True) #一对多
tracks = serializers.PrimaryKeyRelatedField(many=True, read_only=True) # 多对多
这两个序列化字段很有意思,如:A表和B表关系为一对多,模型的字典字段定义在B表,那么tracks = serializers.StringRelatedField(many=True) 必须写在B序列化的类里
多对多也是如此。