这篇介绍框架开发中用的比较多的HTTP工具axios,是一个类似ajax但比ajax强点的网络工具库。

axios简介

axios是一个类似于ajax的对HTTP请求封装的工具,比ajax多了一点新的特性,使用了ES6中的Promise管理异步,比传统的callback处理更加方便、简洁。以及提供了丰富的配置项和拦截器功能(类似于Java语言的Spring MVC框架中的拦截器),可以更加方便处理请求Token等数据。

官网:https://axios-http.com/zh/docs/intro

ES6中Promise的介绍

Promise主要用于异步计算,可以将异步操作队列化,按照期望的顺序执行,返回预期的结果。可以在对象之间传递和操作Promise,帮助我们处理队列。

之前处理异步纯粹使用回调函数,一旦回调次数过多会形成大于号“>”式程序,并且会剥夺函数return的能力,阅读效果极差,维护也很困难。Promise是一个对象,对象与函数最大的区别就是可以保存状态,函数不可以(闭包除外)。对象未剥夺函数return的能力,因此无需层层传递回调函数,进行回调获取数据。同样也不会造成“>”式程序,代码阅读性比较好,维护也会方便点。

更多关于Promise的使用可以到👉Promise对象学习。

axios的简单应用

// 默认传URL的GET方式
axios('http://localhost/api/demo?param1=1&param2=aa')
	.then(resp => {
		console.log(resp);
	});

// 传对象,指定method、body等,默认method为GET
axios({
  url: 'http://localhost/api/demo',
  params: {
    param1: 1, 
    param2: 'aa'
  },
  method: 'get'
}).then(resp => console.log(resp));


// POST传参需要data传参
axios({
  url: 'http://localhost/api/demo',
  data: {
    param1: 1, 
    param2: 'aa'
  },
  method: 'post'
}).then(resp => console.log(resp));

axios的get/post请求方式

上面是直接使用axios的构造函数进行get/post请求,这里使用axios提高的方法进行请求(常用的也是这种)。

GET

axios.get('http://localhost/api/demo?param1=1&param2=aa')
      .then(resp => console.log(resp));

axios.get('http://localhost/api/demo',{params: {
	  param1: 1,
	  param2: 'aa'
	}
})
      .then(resp => console.log(resp));

POST

// 这种方式默认content-type=application/x-www-form-urlencoded
// 即使你传的是json字符串也不会自动识别,需要你指定content-type
axios.post('http://localhost/api/demo', 'param1=1&param2=aa')
      .then(resp => console.log(resp));

// 这种方式默认content-type=application/json
axios.post('http://localhost/api/demo', {
	param1: 1,
	param2: 'aa'
})
      .then(resp => console.log(resp));

axios处理并发请求

ajax请求过多对页面的性能可能会有影响,而axios的并发请求axios.all()可以处理这种请求。

axios.all()Promise.all()的原理一样。

axios.all([
axios.get("http://localhost/api/demo/1"),
axios.get("http://localhost/api/demo/2"),
axios.get("http://localhost/api/demo/3")
]).then(resp => console.log(resp))// resp is an array
.catch(err => console.err(err))
.then(() => console.log("this like finally."));

axios的全局配置方式

axios支持对http请求时域名、超时时间、content-type等进行全局配置,配置后全局的axios都会使用这些配置。

axios.defaults.baseURL = 'https://api.example.com';
axios.defaults.timeout = 3000;
axios.defaults.headers.common['Authorization'] = AUTH_TOKEN;
axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded';
// 数据传输转换
axios.defaults.transformRequest = data => JSON.stringify(data);

axios.all([
axios.get("http://localhost/api/demo/1"),
axios.get("http://localhost/api/demo/2"),
axios.get("http://localhost/api/demo/3")
]).then(resp => console.log(resp))// resp is an array
.catch(err => console.err(err))
.then(() => console.log("this like finally."));

axios的实例封装

上面的全局配置是所有的请求都生效,如果URL域名不同那么就需要这节的请求方式了。我们可以将axios封装出一个个不同的实例,然后使用这些配置好的实例去请求就可以解决域名不同等的问题了。

// 创建实例时配置默认值
const dev = axios.create({
  baseURL: 'https://dev.example.com'
});

const test = axios.create({
  baseURL: 'https://test.example.com'
});

const prod = axios.create({
  baseURL: 'https://prod.example.com'
});

axios.all([
dev.get("http://localhost/api/demo/1"),
test.get("http://localhost/api/demo/2"),
prod.get("http://localhost/api/demo/3")
]).then(resp => console.log(resp))// resp is an array
.catch(err => console.err(err))
.then(() => console.log("this like finally."));

axios的拦截器应用

axios提供的拦截器功能可以为每个请求带上token、时间戳等等,为响应的内容进行判断进行处理等。

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

// 添加响应拦截器
axios.interceptors.response.use(function (response) {
    // 2xx 范围内的状态码都会触发该函数。
    // 对响应数据做点什么
    return response;
  }, function (error) {
    // 超出 2xx 范围的状态码都会触发该函数。
    // 对响应错误做点什么
    return Promise.reject(error);
  });

// 移除拦截器
const myInterceptor = axios.interceptors.request.use(function () {/*...*/});
axios.interceptors.request.eject(myInterceptor);

// 给自定义实例添加拦截器
const instance = axios.create();
instance.interceptors.request.use(function () {/*...*/});