Django 利用 API 实现 AJAX 操做

Django的缺点之一,就是它不支持AJAX。好吧,我知道这么一说又会有一群人反驳:Django有各类模块能够提供AJAX功能;写一个XML的view来实现AJAX;整合pyjams就什么功能都有了云云。嘛,均可以,我这也只是分享一个可行的方案,并非惟一的。若是这个方案正好适合你的项目,那直接拿去用不是更省时间吗?javascript

首先说一下如今项目的状况,前端工程师想用AJAX的方式(依赖于jQuery),经过POST/GET/PUT请求,提交JSON/XML/YAML格式的数据给后台数据库暴露出的一个API地址,以实现对后台数据的操做。若是在view里写一个函数来作比较麻烦,因此使用tastypie直接根据定义的model生成一个API。html

Install&Begin

须要安装django-tastpiepython-digestpython-dateutilmimeparse。最近由于某些缘由国外的https访问常常会受到影响,因此附上下载连接。固然能用pip/easy_install之类的命令来安装最好,已经给出了模块名,这里再也不重复写一次命令了。前端

仍是和之前同样,先以最快的方式先把tastypie跑起来:java

建立名为products应用为例,须要编辑products/models.py,新建products/api.py,而后编辑项目的urls.py:
products/models.py范例用,超简单,没什么可说的。python

from django.db import models
class Product(models.Model):
    name = models.CharField(max_length=16)
    brand = models.CharField(max_length=32)
    def __unicode__(self):
        return self.titlejquery

products/api.pygit

from tastypie.resources import ModelResource
from accounts.models import Product
class ProductResource(ModelResource):
    class Meta:
        queryset = Product.objects.all()
        resource_name = 'p' #可选,不设置的话默认为productgithub

urls.py,引入在api中定义的ProductResourceajax

from django.conf.urls.defaults import patterns, include, url
from accounts.api import ProductResource
urlpatterns = patterns('',
    url(r'^api/', include(ProductResource().urls)),
)mongodb

api定义完成,访问http://127.0.0.1:8000/api/p/?format=json能够看到JSON格式的数据,如右图。由于我装了JSONView for chrome,因此输出的JSON格式比默认的友好一些。

models.py和urls.py都是基础配置,因此主要说一下api.py。这里使用了ModelResource而不是Django提供的Resource,这样就脱离了Django的ORM,提供了扩展到NOSQL的可能性。网上有一个名为tastymongo的项目,做者的目的彷佛是想实现tastypie和mongodb的整合,可是一直没有更新,因此咱们项目中是直接利用mongoengine将这二者整合在一块儿。

POST & INSERT

以POST请求发送一个JSON数据给/api/p/这个地址实现数据的添加,在views.py中创建一个简单的函数,载入product/add.htm模板。html代码以下:

<html>
  <head>
    <title>Tastyapi</title>
  </head>
  <body>
    <form>
      <input type="text" id="brand" />
      <input type="text" id="name" />
      <input type="button" onclick="ajax_insert()" value="insert" />
    </form>
  <script type="text/javascript" src="https://ajax.googleapis.com/ajax/libs/jquery/1.6.1/jquery.min.js" ></script>
  <script type="text/javascript" >

  function ajax_insert()
  {
    var pname = $('#name').val();
    var pbrand = $('#brand').val();
    $.ajax({
      type : "POST", //要插入数据,因此是POST协议
      url : "/api/p/", //注意结尾的斜线,不然会出现500错误
      data : '{"name" : "'+pname+'", "brand" : "'+pbrand+'"}', //JSON数据
      success: function(){
        alert('Submit Success')
      },
      dataType : 'json', //在ie浏览器下我没有加dataTpye结果报错,因此建议加上
      contentType : 'application/json',
    });
  }
  </script>
  </body>
</html> 

这个时候若是进行操做,会返回401错误,由于尚未进行用户验证。毕竟api涉及对后台数据的操做,若是不验证提交者的身份,对于网站安全来讲不是什么好事。要实现验证惟一须要修改的是api.py文件:

from tastypie.resources import ModelResource
from accounts.models import Product
from tastypie.authentication import BasicAuthentication
from tastypie.authorization import DjangoAuthorization
class ProductResource(ModelResource):
    class Meta:
        queryset = Product.objects.all()
        resource_name = 'p'
        authorization = DjangoAuthorization()
        #authorization = Authorization()
        #authentication = BasicAuthentication()

设置只有只有登陆的用户能经过API操做数据。L10的Authorization()验证方式是容许任何人使用这个API,L11的BasicAuthentication()是使用 HTTP的验证方式,就是咱们常看到的,弹出一个难看的文本框,而后然你输入用户名和密码,这种验证方式不太友好,一般不会提供给普通用户使用。

PUT & DELETE

切换AJAX的请求为PUT或DELETE,能够进行更新或是删除操做,但要指定惟一的id或是slug:

 function ajax_delete()
  {
    $.ajax({
      type : "DELETE",
      url : "/api/p/1/", #删除id为1的记录
      success: function(){
        alert('Submit Success')
      },
    dataType : 'json',
    contentType : 'application/json',
    });
  }

更新操做使用PUT请求,能够直接参考手册,和添加操做相比,它要指定惟一的slug或是id;和删除操做相比,它要加上提交的data。

Afterword

Django是一个开放的框架,虽然它已经解决了不少问题,但自己确实有不少作得不够好的地方,不妨碍咱们去选择更适合本身的方案。tastypie很适合团队分工合做,即便是彻底不懂Django的前端,同样能经过API进行操做,并且能够与NOSQL数据库配合使用,至于其余的功能和用法期待你们挖掘吧。

相关文章
相关标签/搜索