一个订单的功能,增删改查须要四个视图函数,对应四个 urlpython
views.py数据库
def get_order(request): return HttpResponse('') def add_order(request): return HttpResponse('') def del_order(request): return HttpResponse('') def update_order(request): return HttpResponse('')
urls.pydjango
urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^get_order/', views.get_order), url(r'^add_order/', views.add_order), url(r'^del_order/', views.del_order), url(r'^update_order/', views.update_order), ]
这样一旦功能多了起来,对应的 url 也就多了,显然很差处理。如今只写一个 url,对应四个功能,因而要在视图函数中判断json
urls.pyapi
urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^order/', views.order), ]
views.py服务器
def order(request): if request.method == 'GET': return HttpResponse('获取订单') elif request.method == 'POST': return HttpResponse('建立订单') elif request.method == 'PUT': return HttpResponse('更新订单') elif request.method == 'DELETE': return HttpResponse('删除订单')
这就是 restful
规范之一:根据 method
不一样从而作不一样的操做restful
上面的方法也能够基于 CBV 来实现:app
urls.py函数
urlpatterns = [ url(r'^admin/', admin.site.urls), url(r'^order/', views.OrderView.as_view()) ]
views.pypost
from django.views import View class OrderView(View): def get(self, request, *args, **kwargs): return HttpResponse('获取订单') def post(self, request, *args, **kwargs): return HttpResponse('建立订单') def put(self, request, *args, **kwargs): return HttpResponse('更新订单') def delete(self, request, *args, **kwargs): return HttpResponse('删除订单')
API 与用户的通讯协议,老是使用 HTTPs 协议
应该尽可能将 API 部署在专用域名之下,若是肯定 API 很简单,不会有进一步的扩展,能够考虑放在主域名之下。
应该将API的版本放在URL中:https://www.qiuxirufeng.cn/api/v1.0
将版本号放在HTTP头信息中:https://www.qiuxirufeng.cn/students
表示 API 的具体网址,每一个网址表明一种资源,因此网址中不能有动词,只能有名词,而且所用的名词每每与数据库的表名对应。数据库中的表示记录同种数据的集合,因此 API 中的名词也应该使用复数。
方式 | 解释 |
---|---|
GET | 从服务器获取资源(一项或者多项) |
POST | 在服务器新建一个资源 |
PUT | 在服务器更新资源(客户端提供改变后的完整资源) |
PATCH | 在服务器更新资源(客户端提供改的属性) |
DELETE | 从服务器删除资源 |
HEAD | 获取资源的元数据 |
OPTIONS | 获取信息,关于资源的哪些属性是客户端能够改变的 |
描述 | 方式 |
---|---|
列出全部班级 | GET /grades/ |
获取某个指定班级编号的信息 | GET /grades/id |
列出某个指定编号的班级的全部学生 | GET /grades/id/students/ |
获取某个指定编号的学生信息 | GET /students/id |
建立一个学生 | POST /students/ |
更新某个指定学生的信息(信息所有由客户端提供) | PUT /students/id |
删除某个指定编号的学生 | DELETE /students/id |
删除某个指定班级的下的全部学生 | DELETE /grades/id/students/ |
若是资源数较多,服务器不能将全部数据一次所有返回给客户端,API 应该提供参数,经过在 url 上传参的形式传递搜索条件,过滤返回结果
描述 | 方式 |
---|---|
指定返回记录的数量 | GET /students/?limit= |
指定返回记录的开始位置 | GET /students/?offset= |
指定返回第几页数据,以及每页的记录数 | GET /students/?page=&per_page= |
指定返回结果按照哪一个属性排序,以及排序的顺序 | GET /students/?sortby=&order= |
指定筛选条件 | GET /students/?student_age_gt= |
注意:参数的设计容许存在冗余,即容许 API 路径和 URL 参数偶尔有重复
服务器向客户端返回的状态码和提示信息
若是错误码是 4xx,就应该向用户返回错误信息,通常来讲,返回的信息中将 error 做为键名,出错的信息做为键值便可
{ error: 'Invalid API KEY', }
针对不一样的操做,服务器向用户返回结果应该符合规范
方式 | 描述 |
---|---|
GET /students/ | 返回资源对象的列表 |
GET /students/id/ | 返回单个资源对象 |
POST /students/ | 返回新生成的资源对象 |
PUT /students/ | 返回完整的资源对象 |
PATCH /students/ | 返回完整的资源对象 |
DELETE /students/id/ | 返回一个空文档 |
RESTful API 最好作到 Hypermedia,即返回结果中提供连接,链向了其余的 API 方法,使得用户不查看文档,也知道下一步应该作什么
{ link:" www.qiuxirufeng.cn/grades/" } { "link":{ "rel":"collection www.qiuxirufeng.cn/index/", "href":"www.qiuxirufeng.cn/grades/", "title":"List of Grades", "type":"application/json", } }
''' rel:表示这个 API 与当前网址的关系 href:表示 API 路径 title:表示 API 的标题 type:表示返回的类型 '''
其余:服务器返回的数据尽可能使用 json 格式,避免使用 xml 格式