序列化和restfull

先安装djangorestframework:

    pip install djangorestframework

建立模型:models.py

from django.db import models


# Create your models here.


class Grade(models.Model):
    name = models.CharField(max_length=32)
    boy_num = models.IntegerField()
    girl_num = models.IntegerField()
    is_delete = models.BooleanField(default=False)

    def __str__(self):
        return self.name

    class Meta:
        db_table = 'grades'



class StudentManager(models.Manager):
    def get_queryset(self):
        return super(StudentManager, self).get_queryset().filter(is_delete=False)


class Student(models.Model):    
    objects = StudentManager()
    name = models.CharField(max_length=32)
    sex = models.BooleanField()
    age = models.IntegerField()
    contend = models.CharField(max_length=128)
    grade = models.ForeignKey('Grade')
    is_delete = models.BooleanField(default=False)

    def __str__(self):
        return self.name

    class Meta:
        db_table = 'students'

    @classmethod
    def Create_student(cls, name, sex, age, contend, grade):
        return cls(name=name, sex=sex, age=age, contend=contend, grade=grade)

迁移到数据库:

    python manage.py makemigrations

    python manage.py migrate

要把学生从数据库里拿出来转化成json字符串返回, 用序列化的方式,我们给学生创建一个对应的序列化类,在应用目录下创建名为serializers.py的文件。(一个模型类对应一个序列化类i)

进入shell环境:python manage.py shell

引入序列化类,创建序列化对象,查看可序列化的对象:

    

找到一个学生:

    

依据学生创建序列化对象,再对对象进行序列化操作:

    

将数据渲染成Json格式:

    

反序列化:当客户需要增加、删除、修改数据时,就要这个过程反过来,就叫反序列化。

    

检测数据并保存:

    

在view.py中:

from django.http import HttpResponse
from django.http import JsonResponse
from rest_framework.parsers import JSONParser
from django.utils.six import BytesIO
from rest_framework.renderers import JSONRenderer

from .models import Student
from .serializers import StudentSerializer


# Create your views here.
def students(request):
    if request.method == 'GET':
        # 获取所有学生信息
        students = Student.objects.all()
        print('获取所有学生信息')
        serializer = StudentSerializer(students, many=True)
        return JsonResponse({'code': 200,
                             'msg': 'success',
                             'data': serializer.data
                             })
    elif request.method == 'POST':
        # 增加一个学生(反序列化)
        data = JSONRenderer().render(request.POST)
        stream = BytesIO(data)
        stu_dict = JSONParser().parse(stream)
        serializer = StudentSerializer(data=stu_dict)
        if not serializer.is_valid():
            # 验证失败
            return JsonResponse({
                'code': 400,
                'msg': '数据验证错误',
                'data': serializer.errors
            })
        # 验证成功
        serializer.save()
        return JsonResponse({
            'code': 201,
            'msg': 'success',
            'data': serializer.data
        })


def studentDetail(request, pk):
    try:
        stu = Student.objects.get(id=pk)
    except Student.DoesNotExist as e:
        return JsonResponse({'error': str(e), 'status': 404})
    if request.method == 'GET':
        # 获取某个学生的信息
        serializer = StudentSerializer(stu)
        return JsonResponse(serializer.data)
    elif request.method == 'PUT':
        # 修改某个学生的信息
        content = JSONRenderer().render(request.PUT)
        stream = BytesIO(content)
        stu_dict = JSONParser().parse(stream)
        serializer = StudentSerializer(stu, data=stu_dict)
        if serializer.is_valid():
            serializer.save()
            return JsonResponse(serializer.data, status=201)
        return JsonResponse({'error': serializer.errors}, status=400)
    elif request.method == 'DELETE':
        # 删除某个学生的信息
        stu.delete()
        return HttpResponse(status=204)

restframeworkpro/urls.py:

from django.conf.urls import url, include
from django.contrib import admin

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    url(r'^serializer/', include('restframeworkapp.urls')),
]

restframeworkapp/urls.py:

from django.conf.urls import url
from .views import students,studentDetail

urlpatterns = [
    url(r'^students/$', students),
    url(r'^students/(?P<pk>\d+)/$', studentDetail),
]

因为现在Django还解析不了PUT和DELETE,所以就引入rest_framework.

激活应用:

    

则在views.py中:

from rest_framework.decorators import api_view
from rest_framework.response import Response
from rest_framework import status
from .models import Student
from .serializers import StudentSerializer


# Create your views here.
@api_view(['GET', 'POST'])
def students(request):
    if request.method == 'GET':
        # 获取所有学生信息
        students = Student.objects.all()
        print('获取所有学生信息')
        serializer = StudentSerializer(students, many=True)
        return Response({'data': serializer.data
                         }, status=status.HTTP_200_OK)
    elif request.method == 'POST':
        # 增加一个学生(反序列化)
        # data = JSONRenderer().render(request.POST)
        # stream = BytesIO(data)
        # stu_dict = JSONParser().parse(stream)
        serializer = StudentSerializer(data=request.data)
        if not serializer.is_valid():
            # 验证失败
            return Response({
                'data': serializer.errors
            }, status=status.HTTP_400_BAD_REQUEST)
        # 验证成功
        serializer.save()
        return Response({
            'data': serializer.data
        }, status=status.HTTP_201_CREATED)


@api_view(['GET', 'PUT', 'DELETE'])
def studentDetail(request, pk):
    try:
        stu = Student.objects.get(pk=pk)
    except Student.DoesNotExist as e:
        return Response({'error': str(e)}, status=status.HTTP_404_NOT_FOUND)
    if request.method == 'GET':
        # 获取某个学生的信息
        serializer = StudentSerializer(stu)
        return Response(serializer.data)
    elif request.method == 'PUT':
        # 修改某个学生的信息
        # content = JSONRenderer().render(request.PUT)
        # stream = BytesIO(content)
        # stu_dict = JSONParser().parse(stream)
        serializer = StudentSerializer(stu, data=request.data)
        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data, status=status.HTTP_201_CREATED)
        return Response({'error': serializer.errors}, status=status.HTTP_400_BAD_REQUEST)
    elif request.method == 'DELETE':
        # 删除某个学生的信息
        stu.delete()
        return Response(status=status.HTTP_204_NO_CONTENT)

restfull类视图会稍微简单一点:

restframeworkapp/urls.py:

from django.conf.urls import url
from .views import StudentList, StudentDetailList
from rest_framework.urlpatterns import format_suffix_patterns
urlpatterns = [
    url(r'^students/$', StudentList.as_view()),
    url(r'^students/(?P<pk>\d+)/$', StudentDetailList.as_view()),
]
urlpatterns =format_suffix_patterns(urlpatterns)

views.py:

from django.http import Http404
from rest_framework.response import Response
from rest_framework import status
from rest_framework.views import APIView

from .models import Student
from .serializers import StudentSerializer


class StudentList(APIView):
    def get(self, request):
        # 获取所有学生信息
        students = Student.objects.all()
        print('获取所有学生信息')
        serializer = StudentSerializer(students, many=True)
        return Response({'data': serializer.data
                         }, status=status.HTTP_200_OK)

    def post(self, request):
        # 增加一个学生(反序列化)
        # data = JSONRenderer().render(request.POST)
        # stream = BytesIO(data)
        # stu_dict = JSONParser().parse(stream)
        serializer = StudentSerializer(data=request.data)
        if not serializer.is_valid():
            # 验证失败
            return Response({
                'data': serializer.errors
            }, status=status.HTTP_400_BAD_REQUEST)
        # 验证成功
        serializer.save()
        return Response({
            'data': serializer.data
        }, status=status.HTTP_201_CREATED)


class StudentDetailList(APIView):
    def get_object(self, pk):
        try:
            return Student.objects.get(pk=pk)
        except Student.DoesNotExist as e:
            raise Http404

    def get(self, request, pk):
        stu = self.get_object(pk)
        serializer = StudentSerializer(stu)
        return Response(serializer.data)

    def put(self, request, pk):
        stu = self.get_object(pk)
        serializer = StudentSerializer(stu, data=request.data)
        if serializer.is_valid():
            serializer.save()
            return Response(serializer.data, status=status.HTTP_201_CREATED)
        return Response({'error': serializer.errors}, status=status.HTTP_400_BAD_REQUEST)

    def delete(self, request, pk):
        stu = self.get_object(pk)
        stu.delete()
        return Response(status=status.HTTP_204_NO_CONTENT)

优点:

    把各种HTTP请求分离开

    可以轻松构成可重复使用的行为

    可以大大简化代码

    增加了可读性

---------------------------------------------------------------------------------------------------------------------------------------

使用mixins更加简化代码:

views.py中:

from .models import Student
from .serializers import StudentSerializer

from rest_framework import mixins
from rest_framework import generics


class StudentList(mixins.ListModelMixin, mixins.CreateModelMixin, generics.GenericAPIView):
    queryset = Student.objects.all()
    serializer_class = StudentSerializer

    def get(self, request, *args, **kwargs):
        # 获取所有学生信息
        return self.list(request, *args, **kwargs)

    def post(self, request, *args, **kwargs):
        return self.create(request, *args, **kwargs)


class StudentDetailList(mixins.RetrieveModelMixin, mixins.UpdateModelMixin, mixins.DestroyModelMixin,
                        generics.GenericAPIView):
    queryset = Student.objects.all()
    serializer_class = StudentSerializer

    def get(self, request, *args, **kwargs):
        return self.retrieve(request, *args, **kwargs)

    def put(self, request, *args, **kwargs):
        return self.update(request, *args, **kwargs)

    def delete(self, request, *args, **kwargs):
        return self.destroy(request, *args, **kwargs)

使用ListCreateAPIView,RetrieveUpdateDestroyAPIView:

from .models import Student
from .serializers import StudentSerializer

from rest_framework import generics


class StudentList(generics.ListCreateAPIView):
    queryset = Student.objects.all()
    serializer_class = StudentSerializer


class StudentDetailList(generics.RetrieveUpdateDestroyAPIView):
    queryset = Student.objects.all()
    serializer_class = StudentSerializer

viewset写法:

urls.py中: 

from django.conf.urls import url, include
from rest_framework.routers import DefaultRouter
from .views import StudentViewSet

router = DefaultRouter()
router.register(r'students', StudentViewSet)
urlpatterns = [
    url(r'^', include(router.urls))
]

views.py中:

from .models import Student
from .serializers import StudentSerializer
from rest_framework import viewsets


class StudentViewSet(viewsets.ModelViewSet):
    queryset = Student.objects.all()
    serializer_class = StudentSerializer

----------------------------------------------------------------------------------------------------------------------------------

Django序列化:

  查看班级所有学生:

    students

    {

        'code':200,

        'total':3,

        'data':[stu1, stu2, stu3]

    }

     将students转化为json字符串返回,需要字典转化字符串,我们需要将stu对象转化为字典,我们将对象转化为字典的过程就是序列化。

猜你喜欢

转载自blog.csdn.net/yx1179109710/article/details/81566930