VUE 数据请求和响应(axios)

1. 概述

1.1 简介

  axios是一个基于Promise(本机支持ES6 Promise实现) 的HTTP库,用于浏览器和 nodejs 的 HTTP 客户端。具有以下特征:

    • 从浏览器中创建 XMLHttpRequests
      • XMLHttpRequest对象用于在后台与服务器交换数据,可做到在不重新加载页面的情况下更新网页,在页面已加载后从服务器请求数据或接收数据,在后台向服务器发送数据。所有的浏览器都支持XMLHttpRequest对象。
    • 从 node.js 创建 http 请求
      • 如get/post等
    • 支持 Promise API
      • 如promise所支持的链式回调,.then(res => {}).catch(err =>{})
    • 拦截请求和响应
      • 在请求之前或响应之后进行的处理,如请求之前增加统一的token标识,响应之后对公用的错误进行处理等。
    • 转换请求数据和响应数据
    • 取消请求
    • 自动转换JSON数据
    • 客户端支持防御XSRF

1.2 引入使用

  npm install axios  进行安装,安装成功后 import axios from 'axios' 进行引入模块,再对axios对象进行设置。如

/**
 * 创建axios对象
 **/
let axiosInstance =axios.create({
  baseURL: configHttp.domain,
  withCredentials:true,
});

  备注:使用 Vue.prototype.$http = axios; 进行配置于vue项目中,在页面中可使用this.$http.get('xxxx').then().catch()。

1.3 常用请求配置

  1.3.1 url

  数据请求的服务器URL,此配置必须存在,否则无访问路径无法进行数据请求。

  1.3.2 method

  创建请求时使用的方法,默认get方式。有多种请求方式,如:request/get/delete/head/post/put/patch,常用get与post.

  1.3.3 baseURL

  设置一个统一的基础路径(如http://www.demo.com/api/),使axios的get或post中的url使用相对URL,更改访问域名或端口号时只更改对应的baseURL值即可。

  1.3.4 headers

  headers是即将被发送的自定义请求头,可设置请求的数据标识(token)或post请求的数据类型等。

  1.3.5 timeout

  请求超时时间,单位为毫秒,若超过超时时间则请求中断。0表示无超时时间。

  1.3.6 withCredentials

  跨域请求时是否需要使用凭证,默认为false

1.4 配置的默认与自定义实例

  优先级别为:自定义实例>全局默认值>自带默认值

  1.全局默认值

axios.defaults.baseURL = 'https://api.example.com';
axios.defaults.headers.common['Authorization'] = AUTH_TOKEN;
axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded';

  2.自定义实例

// 创建实例时设置配置的默认值
var instance = axios.create({
  baseURL: 'https://api.example.com'
});

// 在实例已创建后修改默认值
instance.defaults.headers.common['Authorization'] = AUTH_TOKEN;

  备注:也可在请求拦截中进行设置对应的配置。

1.5 拦截器

  在请求或响应被 then 或 catch 处理前拦截他们,分为请求拦截器和响应拦截器

    • 请求拦截器(interceptors.request)是指可以拦截每次或指定HTTP请求,并可修改配置项。
    • 响应拦截器()可以拦截每次HTTP请求对应的响应,并可修改返回结果项。

  示意图

  

  一般在请求拦截器中增加标识token或其他请求配置,在响应拦截器中对统一错误或状态码进行处理(跳转统一页面如登录)

// 添加请求拦截器
axios.interceptors.request.use(function (config) {
    // 在发送请求之前做些什么
    return config;
  }, function (error) {
    // 对请求错误做些什么
    return Promise.reject(error);
  });

// 添加响应拦截器
axios.interceptors.response.use(function (response) {
    // 对响应数据做点什么
    return response;
  }, function (error) {
    // 对响应错误做点什么
    return Promise.reject(error);
  });

2. 实例

 2.1 axios配置

  备注:在headers.post['Content-Type']不为application/json时,传递post参数时需使用querystring中的querystring.stringify对参数进行格式化处理。

import axios from 'axios'
import configHttp from '../../configHttp'

/**
 * 创建axios对象
 **/
let axiosInstance =axios.create({
  baseURL: configHttp.domain,
  withCredentials:true,
});

/**
 * 访问请求拦截(在请求前处理)
 **/
axiosInstance.interceptors.request.use(
  function (config) {
    config.headers.common['Platform'] = 'web';
    return config;
  },
  function (error) {
    return Promise.reject(error)
  }
);

/**
 * 响应请求拦截(在响应前处理)
 **/
axiosInstance.interceptors.response.use(
  function (response) {
    return response;
  },
  function (error) {
    if(error.response){
      let status=error.response.status;
      switch (status) {
        case 401:
            // 跳转至login
          break;
      }
    }
    //处理报错 记录日志
    if (error !== undefined) {
      console.log(error);
    }

  }
);
/**
 * http请求响应处理函数
 **/
let httpResponseHandle = function(){
  let self = this;
  let res = self.res;
  if (res.code == '0') {
    self.successCallback && self.successCallback(res);
  } else if (res.code == 'C00004' || res.code =='C00002') {
    // 清除token
    // 跳转至login
  } else {
    // 统一错误弹出
    self.failCallback && self.failCallback(res);
  }
};

let http= {
  /**
   * 以get方式请求获取JSON数据
   * @param {Object} opts 配置项,可以包含以下成员:
   * @param {String} opts.url 请求地址
   * @param {Object} opts.params 附加的请求参数
   * @param {Function} opts.successCallback 成功的回调函数
   * @param {Function} opts.failCallback 失败的回调函数
   * **/
  get: function (opts) {
    axiosInstance
      .get(opts.url, {params: opts.params})
      .then(function (res) {
        opts.res = res.data;
        httpResponseHandle.call(opts);
      })
      .catch(function (err) {
        if (err.response) {
          if (err.response.data) {
            opts.res = err.response.data;
            httpResponseHandle.call(opts);
          } else {
            // 统一错误弹出
          }
        }
      });
  },

  /**
   * 以post方式请求获取JSON数据
   * @param {Object} opts 配置项,可以包含以下成员:
   * @param {String} opts.url 请求地址
   * @param {Object} opts.params 附加的请求参数
   * @param {Function} opts.successCallback 成功的回调函数
   * @param {Function} opts.failCallback 失败的回调函数
   * **/
  post: function (opts) {
    axiosInstance
      .post(opts.url, opts.params)
      .then(function (res) {
        opts.res = res.data;
        httpResponseHandle.call(opts);
      })
      .catch(function (err) {
        if (err.response) {
          if (err.response.data) {
            opts.res = err.response.data;
            httpResponseHandle.call(opts);
          } else {
            // 统一错误弹出
          }
        }
      });
  }
};

export default http;

 2.2 实例调用

  在Vue中使用prototype进行设置,不能使用use设置。

  1.main.js中直接写入

import http from '@/common/js/http.js';
Vue.prototype.$http = http;

  2.其他引入

import Vue from 'vue'
import axios from '../common/js/http.js'

Vue.prototype.$http = axios

 2.3 页面使用

  vue单页面中的methods中使用

  1.get示例

  this.$http.get({
          url: 'comm/getDataInfo',
          params: {
            param1: xxx,
            param2: '3'
          },
          successCallback: res => {
            // 数据处理
          },
          failCallback: res => {}
        });

  2.post示例

   this.$http.post({
        url: 'common/userLogin',
        params: {
          username: 'admin',
          password: '123456'
        },
        successCallback: res => {
          // 数据处理
        },
        failCallback: res => {}
      });

 2.4 http请求Content-Type: application/x-www-form-urlencoded

  接口使用x-www-form-urlencoded格式接收/传递数据时,需要使用qs(原来的querystring)对所传递的参数进行格式化处理;

  1.设置数据格式

headers: {
  'Content-Type': 'application/x-www-form-urlencoded',
}

  2.在请求拦截处统一处理参数格式化

config.data = qs.stringify(config.data)
import axios from 'axios'
import qs from 'qs'
const http = axios.create({
  timeout: 15000,
  headers: {
    'Content-Type': 'application/x-www-form-urlencoded',
  },
})
/**
 * 请求拦截器
 */
http.interceptors.request.use(config => {
  const objParams = {
    appKey: 'ccc',
    bizContent: JSON.stringify(config.data),
  }
  config.data = qs.stringify(objParams) // objParams为传递参数
  return config
}, error => {
  Promise.reject(error)
})
posted @ 2018-12-26 14:49  ajuan  阅读(6466)  评论(0编辑  收藏  举报