django+vue+vue-resource+django-cors-headers实现前后端分离

PS:网上资料要不残缺,要不通篇一律的复制。。自己花了几天时间整理出确切可行方案

参考  https://cloud.tencent.com/developer/article/1005607?fromSource=waitui

   https://zhuanlan.zhihu.com/p/24893786

安装VUE 

首先网上载NODE 安装NODE

http://nodejs.cn/

安装VUE.JS

#CMD执行
npm install -g vue-cli  #方法一源在国外相当慢
#方法二速度较快
npm install -g cnpm --registry=https://registry.npm.taobao.org
cnpm install -g vue-cli
#输入vue如果有信息安装成功

创建项目(在 django项目下,与app同级)

vue init webpack django_front(项目文件夹名)

进入到django-front目录下执行

cnpm install //安装vue所须要的node依赖

 

 cnpm install //安装vue所须要的node依赖

 

npm run dev运行

前端设置路由

import Vue from 'vue'
import Router from 'vue-router'
import tomato from '@/components/tomato'
import watermelon from '@/components/watermelon'
Vue.use(Router)
export default new Router({
  mode: 'history',
  routes: [
    {
      path: '/tomato',
      name: 'tomato',
      component: tomato
    },
    {
      path: '/watermelon',
      name: 'watermelon',
      component: watermelon
    }
  ]
})

tomato.vue模板

<template>
  <div class="tomato">
    <img src="../../static/tomato.png"/>
    <h1>{{ msg }}</h1>
        <a
          href="/watermelon"
        >
          西瓜
        </a>
  </div>
</template>

<script>
export default {
  name: 'tomato',
  data () {
    return {
      msg: 'this is tomato'
    }
  }
}
</script>

 

npm run build 生成部属用的目录 dist

配置 django 

pip install django-cors-headers #解决跨域问题

修改setting.py

MIDDLEWARE = [
    'django.middleware.security.SecurityMiddleware',
    'django.contrib.sessions.middleware.SessionMiddleware',
    'corsheaders.middleware.CorsMiddleware', #添加
    'django.middleware.common.CommonMiddleware',
    'django.middleware.csrf.CsrfViewMiddleware',
    'django.contrib.auth.middleware.AuthenticationMiddleware',
    'django.contrib.messages.middleware.MessageMiddleware',
    'django.middleware.clickjacking.XFrameOptionsMiddleware',
]
CORS_ORIGIN_ALLOW_ALL = True  #添加
TEMPLATES = [
    {
        'BACKEND': 'django.template.backends.django.DjangoTemplates',
        'DIRS': ['django_front/dist'],   #设定模板路径
        # 'DIRS': [os.path.join(BASE_DIR,'templates')],
        'APP_DIRS': True,
        'OPTIONS': {
            'context_processors': [
                'django.template.context_processors.debug',
                'django.template.context_processors.request',
                'django.contrib.auth.context_processors.auth',
                'django.contrib.messages.context_processors.messages',
            ],
        },
    },
]
STATIC_URL = '/static/'
# Add for vuejs
STATICFILES_DIRS = [
    os.path.join(BASE_DIR, "django_front/dist/static"),
]

urls.py

urlpatterns = [
    path('admin/', admin.site.urls),
    path(r'tomato/', TemplateView.as_view(template_name="index.html"),name="index"),
    path(r'watermelon/', TemplateView.as_view(template_name="index.html"),name="index")
]

到此整合完毕python manage.py runserver 8080

访问127.0.0.1:8080/tomato进行查看

ps 与bootstrap整合将bootstrap源码的dist文件放到django static目录即可

django与vue交互简单演示(基于以上配置完成)

 安装vue-resource(需在项目目录里面,在package.json同级)

npm install vue-resource --save

在入口文件main.js插入

import VueResource from 'vue-resource'
Vue.use(VueResource);

新建路由(router/index.js)submit

import Vue from 'vue'
import Router from 'vue-router'
import tomato from '@/components/tomato'
import watermelon from '@/components/watermelon'
import submit from '@/components/submit'
Vue.use(Router)
export default new Router({
  mode: 'history',
  routes: [
    {
      path: '/tomato',
      name: 'tomato',
      component: tomato
    },
    {
      path: '/watermelon',
      name: 'watermelon',
      component: watermelon
    },
    {
      path: '/submit',
      name: 'submit',
      component: submit
    },
  ]
})
View Code

创建submit模板/components/submit.vue

<template>
<div id="tomato">
  <form @submit.prevent="submit">
      <div class="field">
          书名:
          <input type="text" v-model="book.book_name">
      </div>

      <input type="submit"
             value="提交">
  </form>
  <button v-on:click="display">搜索</button>
  <table v-for="item in books">
    <tr>
      <td>书名:{{ item.fields.book_name}} && 添加时间:{{item.fields.add_time}}</td>
    </tr>
  </table>
</div>
</template>
<script>
  export default {
    data (){
      return {
      books: [],
      book:{
        book_name:null,
      }
    }
    },
//    mounted() {
//      // GET /someUrl
//      this.$http.get('http://127.0.0.1:8000/api/show_books').then(response => {
//        this.books = response.data.list;
//        console.log(this.books[0].fields.book_name);
//        // get body data
//        // this.someData = response.body;
//
//      }, response => {
//        console.log("error");
//      });
//    },
    methods: {
        submit: function() {
          var formData = JSON.stringify(this.book); // 这里才是你的表单数据
          //console.log(this.book.book_name);
          console.log(formData);
          this.$http.post('http://127.0.0.1:8000/api/add_book', formData).then((response) => {
              // success callback
              console.log(response.data);
          }, (response) => {
               console.log("error");
              // error callback
          });
        },
        display() {
      // GET /someUrl URL为django接口地址
        this.$http.get('http://127.0.0.1:8000/api/show_books').then(response => {
          this.books = response.data.list;
          console.log(this.books[0].fields.book_name);
          // get body data
          // this.someData = response.body;

        }, response => {
          console.log("error");
        });
    },

    },
  }
</script>
View Code

npm run build

django上的配置(setting配置以上)

创建数据库

from django.db import models
class Book(models.Model):
    book_name = models.CharField(max_length=64)
    add_time = models.DateTimeField(auto_now_add=True)

    def __unicode__(self):
        return self.book_name
#执行python manage.py makemigrations blog
#python manage.py migrate
View Code

views.py

# Create your views here.
from django.shortcuts import  render,HttpResponse,redirect
from .apps import AppnameConfig
from blog.models import *
from django.views.decorators.http import require_http_methods
import json
from django.core import serializers
from django.http import JsonResponse
import simplejson
@require_http_methods(["GET",'POST'])
def add_book(request):
    response = {}
    try:
        if  request.method=='POST':
            req = simplejson.loads(request.body)  # json格式传过来的数
            Book.objects.create(
                **req
            )
            # Book.objects.create(   #x-www-form-urlencoded传过来的数据
            #     **{"book_name":request.POST.get('book_name')},
            # )
            response['msg'] = 'success'
            response['error_num'] = 0
        if request.method=='GET':
            # book = Book(book_name=request.GET.get('book_name'))
            # book.save()
            Book.objects.create(  # 方法二建议这种,直接将前端字典插入
                **{"book_name":request.GET.get('book_name')},
            )
            response['msg'] = 'success'
            response['error_num'] = 0
    except  Exception as e:
        response['msg'] = str(e)
        response['error_num'] = 1
    return JsonResponse(response)

@require_http_methods(["GET"])
def show_books(request):
    response = {}
    try:
        books = Book.objects.filter()
        response['list']  = json.loads(serializers.serialize("json", books))
        response['msg'] = 'success'
        response['error_num'] = 0
    except  Exception as e:
        response['msg'] = str(e)
        response['error_num'] = 1

    return JsonResponse(response)
View Code

urls.py总路由

from django.contrib import admin
from django.urls import path,include
from blog import views
from django.conf.urls import url, include
from django.views.generic import TemplateView

urlpatterns = [
    url(r'^admin/', admin.site.urls),
    url(r'^api/', include('blog.url_blog')),
    url(r'^$', TemplateView.as_view(template_name="index.html")),
    path(r'tomato/', TemplateView.as_view(template_name="index.html"),name="index"),
    path(r'watermelon/', TemplateView.as_view(template_name="index.html"),name="index"),
    path(r'submit/', TemplateView.as_view(template_name="index.html"),name="index")
]
View Code

子路由url_blog.py

urlpatterns = [
    url(r'add_book$', views.add_book, ),
    url(r'show_books$', views.show_books, ),
]
View Code

测试

python  manage.py runserver 8000

网页访问127.0.0.1:8000/submit

vue与django 实现CSRF认证参考《vue与django CSRF认证

posted @ 2018-05-01 17:38  林夕之风  阅读(882)  评论(0编辑  收藏  举报