写一个出版社的增删查改resful接口
# models.py模板层 model.py 模板层 url 路由层 View Code 第四种方案:不建议使用
from django.db import modelsclass Book(models.Model): nid = models.AutoField(primary_key=True) name = models.CharField(max_length=32) price = models.CharField(max_length=32) publish_date = models.DateField() publish = models.ForeignKey(to='Publish',to_field='nid',on_delete=models.CASCADE) authors = models.ManyToManyField(to='Author') def __str__(self): return self.nameclass Author(models.Model): nid = models.AutoField(primary_key=True) name = models.CharField(max_length=32) age = models.IntegerField() author_detail = models.OneToOneField(to='AuthorDetail', to_field='nid', unique=True, on_delete=models.CASCADE)class AuthorDetail(models.Model): nid = models.AutoField(primary_key=True) telephone = models.BigIntegerField() birthday = models.DateField() addr = models.CharField(max_length=64)class Publish(models.Model): nid = models.AutoField(primary_key=True) name = models.CharField(max_length=32) city = models.CharField(max_length=32) email = models.EmailField() def __str__(self): return self.name def test(self): return self.email
#url 路由层
from django.conf.urls import url, includefrom django.contrib import adminfrom app01 import viewsfrom rest_framework import routers# 生成一个router对象router = routers.DefaultRouter()# 需要传两个参数,第一个参数就是匹配的路径,第二个参数,是视图类router.register('publish', views.PublishView)urlpatterns = [ url(r'^admin/', admin.site.urls), # url(r'^publish/',views.PublishView.as_view() ), # url(r'^publish/(?P\d+)',views.PublishDetailView.as_view() ), # url(r'^publish/$', views.PublishView.as_view({'get': 'list', 'post': 'create'})), # url(r'^publish/(?P \d+)', views.PublishView.as_view({'get': 'retrieve', 'put': 'update', 'delete': 'destroy'})), url(r'^test1/$', views.TestAll.as_view({ 'get': 'test'})), # url(r'^test2/$', views.TestAll.as_view({'get': 'test2'})), # url(r'^test3/$', views.TestAll.as_view({'get': 'test3'})), # 不会使用这种方法的 url('', include(router.urls)),]路由控制 三种: -一种基本路由:url(r'^publish/$', views.PublishView.as_view()), -半自动路径:views.PublishView.as_view({ 'get': 'list', 'post': 'create'})) -必须继承:ViewSetMixin -继承ViewSetMixin的先后顺序 -全自动路由:(基本不用) -from rest_framework import routers # 生成一个router对象 router=routers.DefaultRouter() # 需要传两个参数,第一个参数就是匹配的路径,第二个参数,是视图类 router.register('publish',views.PublishView) url('', include(router.urls)), #自动生成四个路由(PublishView必须继承ModelViewSet)
#MySer 序列化组件
from rest_framework import serializersfrom app01 import modelsclass AuthorSerializers(serializers.Serializer): nid = serializers.CharField() name = serializers.CharField() age = serializers.CharField()class PublishSerializers(serializers.ModelSerializer): class Meta: model = models.Publish fields = '__all__'
基本视图
最原始的 普通视图层
from django.shortcuts import render,HttpResponsefrom rest_framework.views import APIViewfrom app01 import modelsfrom app01.MySer import AuthorSerializers, PublishSerializersfrom django.http import JsonResponseclass PublishView(APIView): def get(self, request): publish_list = Publish.objects.all() bs = PublishSerializers(publish_list, many=True) return JsonResponse(bs.data,safe=False) def post(self, request): # 添加一条数据 print(request.data) bs = PublishSerializers(data=request.data) if bs.is_valid(): bs.save() # 生成记录 return JsonResponse(bs.data,safe=False) else: return JsonResponse(bs.errors,safe=False)class PublishDetailView(APIView): def get(self, request, pk): publish_obj = Publish.objects.filter(pk=pk).first() bs = PublishSerializers(publish_obj, many=False) return JsonResponse(bs.data,safe=False) def put(self, request, pk): publish_obj = Publish.objects.filter(pk=pk).first() bs = PublishSerializers(data=request.data, instance=publish_obj) if bs.is_valid(): bs.save() # update return JsonResponse(bs.data) else: return JsonResponse(bs.errors) def delete(self, request, pk): Publish.objects.filter(pk=pk).delete() return JsonResponse("")
1 .第一种方案 — 视图层
第一种方案class List: def list(self,request): queryset = self.queryset bs = self.serializers(queryset, many=True) return JsonResponse(bs.data,safe=False)class Create: def create(self,request): print(request.data) bs = PublishSerializers(data=request.data) if bs.is_valid(): bs.save() # 生成记录 return JsonResponse(bs.data,safe=False) else: return JsonResponse(bs.errors,safe=False)class PublishView(APIView,List,Create): queryset=Publish.objects.all() serializers=PublishSerializers def get(self, request): return self.list(request) def post(self, request): # 添加一条数据 return self.create(request)class BookView(APIView,List,Create): queryset=Book.objects.all() serializers=BookSerializer def get(self, request): return self.list(request) def post(self, request): return self.create(request)
第二种:ListCreateAPIView 继承了GenericAPIView, ListModelMixin, CreateModelMixin
2 .第二种方案 :drf提供的封装的类——视图层
第三种:路由:url(r'^publish/$', views.PublishView.as_view({'get': 'list', 'post': 'create'})),
url(r'^publish/(?P<pk>\d+)', views.PublishView.as_view({'get': 'retrieve', 'put': 'update','delete':'destroy'})), 3. 第三种方案 ——视图层
from rest_framework.generics import ListCreateAPIView, ListAPIView, RetrieveUpdateDestroyAPIViewfrom rest_framework.mixins import ListModelMixin, CreateModelMixin, RetrieveModelMixin, UpdateModelMixin, \ DestroyModelMixinfrom rest_framework.generics import GenericAPIViewclass PublishView(GenericAPIView, ListModelMixin, CreateModelMixin):class PublishView(ListCreateAPIView): queryset = Publish.objects.all() serializer_class = PublishSerializersclass PublishDetailView(RetrieveUpdateDestroyAPIView): queryset = Publish.objects.all() serializer_class = PublishSerializers
from rest_framework.views import APIViewfrom rest_framework.viewsets import ModelViewSetfrom rest_framework.renderers import JSONRenderer,BrowsableAPIRendererclass PublishView(ModelViewSet): # renderer_classes=[JSONRenderer,BrowsableAPIRenderer] queryset = Publish.objects.all() serializer_class = PublishSerializers
终极版本:
建议用魔法类ViewSetMixin
最终应该使用的方案:ViewSetMixin 它有什么作用?用了它之后,视图类中不需要写get,post,put方法了,自己定义方法就可以了 让请求方法对应到自己定义的方法上,然后再配置路由
快速写出5个接口:
-继承它ModelViewSet-写一个视图类,视图类中定义两个变量
from rest_framework.viewsets import ModelViewSet
class BookView(ModelViewSet):
queryset = Book.objects.all() serializer_class = BookSerializer -路由:(要写两条路由) url(r'^publish', views.PublishView.as_view({'get': 'list', 'post': 'create'})), url(r'^publish/(?P<pk>\d+)', views.PublishView.as_view({'get': 'retrieve', 'put': 'update','delete':'destroy'})),# from day100 import settings # settings 就是项目的配置文件 from django.conf import settings
-第一种:最原始的那种
-第二种:继承ViewSetMixin,它放在前面(好处,跟某个功能相关的,可以写在第一起) -可以自己封装一个View,继承ViewSetMixin,和APIViewfrom rest_framework.response import Response # 建议用魔法类ViewSetMixin
rom rest_framework.viewsets import ViewSetMixin# 注意先后顺序,ViewSetMixin写在前面class TestAll(ViewSetMixin,APIView): def test(self,request): print(settings.DEBUG) return HttpResponse('test') def test2(self, request): return HttpResponse('test2') def test3(self, request): return HttpResponse('test3')
配置文件查找顺序
先从视图类中查找--->项目配置文件(settings)----->drf默认的setting中取