1、为学习axios做准备;安装axios并搭建json server服务
(1)安装axios并引入axios
-
npm install --save axios vue-axios
-
import axios from ‘axios’ //可以在axios配置文件中引入
(2)搭建json server服务
-
安装json-server:命令npm i -g json-server 注:nodejs版本要12以上
-
创建文件db.json
-
启动服务 json-server --watch db.json
{
"posts": [
{
"id": "1",
"title": "json-server",
"author": "typicode"
},
{
"id": "2",
"title": "server",
"author": "code"
},
{
"id": "3",
"title": "json",
"author": "typi"
}
],
"comments": [
{
"id": "1",
"title": "some comment",
"postId": "1"
}
],
"profile": {
"name": "typicode"
}
}
2、axios的介绍
(1)Axios 是一个基于 promise 的 HTTP 库,可以用在浏览器和 node.js 中。
(2)从浏览器中创建 XMLHttpRequests 发送Ajax请求
(3)从 node.js 创建 http 请求
(4)支持 Promise API
(5)拦截请求和响应
(6)转换请求数据和响应数据
(7)取消请求
(8)自动转换 JSON 数据
(9)客户端支持防御 XSRF
3、基本使用—使用axios函数发送请求axios({}) 接收参数为一个对象
(1)get请求
axios({
url:"http://localhost:3000/posts/1",
method:"GET",
}).then(res=>{
console.log("res-->",res)
})
(2)post请求—为posts添加数据
axios({
url:"http://localhost:3000/posts",
method:"POST",
data:{
"id": "4",
"title": "很好",
"author": "很ok"
}
}).then(res=>{
console.log("res-->",res)
})
(3)put请求 修改数据—修改指定的id为2 数据 并 更新
axios({
url:"http://localhost:3000/posts/2",
method:"PUT",
data:{
title:"ahaha",
date:"2022-3-9"
}
}).then(res=>{
console.log("res-->",res)
})
(4)delete请求----会根据指定id去删除相应的数据
axios({
url:"http://localhost:3000/posts/3",
method:"delete"
}).then(res=>{
console.log("res-->",res)
})
4、axios的其他请求方式—axios的对象函数发送请求
例如:request(配置对象config)、post(参数url,data,config)、get(参数url,config)、put(参数url,data,config)、delete(参数url,config)、patch(参数url,data,config)、options(参数url,config)、head(参数url,config)等请求方式
(1)request请求;也是接收一个对象参数
axios.request({
url:"http://localhost:3000/posts/1",
method:"GET",
}).then(res=>{
console.log("res-->",res)
})
(2)post请求;添加数据 接收三个参数 分别为 url、请求体{}、config(请求体和config二选一)
axios.post("http://localhost:3000/posts",{
"id": "4",
"title": "很好",
"author": "很ok"
}).then(res=>{
console.log("res-->",res)
})
5、axios请求的响应结果结构
![[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ExEEdDPr-1646963957509)(C:\Users\qctc\AppData\Roaming\Typora\typora-user-images\1646803253363.png)]](https://i-blog.csdnimg.cn/blog_migrate/1ad49a0292515ac39e7e1f96dbcd0394.png)
(1)config:配置对象,包含着请求类型、请求url、请求体等等
(2)data:响应体的结果,就是服务器返回的结果;是一个对象,因为被json解析了;
(3)headers:响应头信息
(4)request:原生的Ajax对象,发送Ajax请求就要用到底层的XMLHttpRequest;request所保存的就是当前Ajax发送请求是所创建的Ajax请求对象XMLHttpRequests。
(5)status和statusText:Ajax请求响应状态和字符串
6、axios拦截器
(1)请求拦截器
-
在请求前执行的回调函数
-
可以对请求进行检查或者配置进行特定处理(比如:判断请求的类型去指定请求头的content-type的类型)
-
成功的回调函数默认是config
-
失败的回调函数传递默认是error
axios.interceptors.request.use(config=>{
let paramsType = config.method === "get" ? 'params' : 'data';
if (config.method == "post"){
config.headers['Content-Type'] = 'application/x-www-form-urlencoded';
config.headers['Accept-Language'] = 'zh-CN';
if (!config.data){//没有参数时,config.data为null,需要转下类型
config.data = {}
}
}
return config
},error => {
return Promise.reject(error)
});
(2)响应拦截器
-
在请求得到响应后执行的回调函数
-
可以对相应的数据做一些特定的处理(比如:可以直接把响应体直接返回)
-
成功的回调函数传递默认是response
-
失败的回调函数传递默认是error
axios.interceptors.response.use(response=>{
return response;
},error => {
return Promise.reject(error)
});
export default axios
(3)先执行请求拦截再到响应拦截,最后去执行回调处理结果
注意:如果请求的成功拦截返回一个抛出异常 throw ‘error’;那么响应拦截只能走失败的响应拦截,then()方法只能指定失败的回调函数。跟promise就非常的相像
7、axios取消请求
(1)多次发送请求如何处理?阻止发送多次请求
解决方案:使用取消函数取消请求
1、当配置CancelToken对象时,保存cancel函数
-
创建一个用于将来中断请求的cancelPromise
-
并定义一个用于取消请求的cancel函数
-
将cancel函数传递出去
2、调用cancel函数取消请求
-
执行cancel函数,传入错误信息message
-
内部会让cancelPromise变为成功,且成功的值为一个Cancel对象
-
在cancelPromise成功回调中中断请求,并让发请求的promise失败,失败的reason为Cancel对象
1、取消请求;在配置对象中添加cancelToken属性,值为 axios.CancelToken构造函数 生成取消函数,每次发送Ajax时,把取消函数赋值给一个全局定义的变量
2、再根据全局变量去判断检测上一个请求是否已经完成,如果还在继续则执行取消函数
注:服务端做一个延迟响应,因为数据响应太快,可能还没来得及去做判断就已经执行完成且数据返回
let cancel = null;
const btn = document.querySelectorAll('button');
btn[0].onclick = function (){
if (cancel !== null){
cancel();
}
axios({
url:"http://localhost:3000/posts/1",
method:"GET",
cancelToken: new axios.CancelToken(function(e){
console.log(e)
cancel = e
})
}).then(res=>{
cancel = null
console.log(res)
})
}
![[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-IgnSsT5Q-1646963957511)(C:\Users\qctc\AppData\Roaming\Typora\typora-user-images\1646819211699.png)]](https://i-blog.csdnimg.cn/blog_migrate/1c897faedc92b291820b787e20c48aa2.png)
8、axios源码分析
(1)axios的文件结构说明

(2)源码分析总结
1、lib目录下的axios和core目录下的Axios关系?
-
从语法上来说:axios不是Axios的实例
原因:因为axios是通过createInstance构造函数创建得来的,先造一个context实例后造一个instance函数;以extend扩展的形式将 Axios.prototype原型 和 context实例对象的方法 都添加到 instance函数 身上;然后将实例对象的方法和属性拓展到instance函数身上;最后返回instance函数
-
从功能上来说:axios是Axios的实例
-
axios是createInstance(defaults)构造函数返回的函数
function createInstance(defaultConfig) {
var context = new Axios(defaultConfig);
var instance = bind(Axios.prototype.request, context);
utils.extend(instance, Axios.prototype, context);
utils.extend(instance, context);
return instance;
}
2、instance和axios的区别?
相同:
-
都是一个能发任意请求的函数:request(config)
-
都有发特定请求的各种方法:get()、post()、put()、delete()
-
都有默认配置和拦截器的属性:defaults/interceptors
不同:
-
默认配置很可能不一样
-
instance没有axios后面添加的一些方法:create()/CancelToken()/all()
3、axios的请求/响应数据转换器是什么?
(1)请求转换器:对请求头和请求体数据进行特定的处理的函数
if(utils.isObject(data)){
setContentTypeIfUnset(headers,'apliction/json;charset=utf-8');
return JSON.string(data);
})
(2)响应转换器:将响应体json字符串解析为js对象或数组函数
response.data = JSON.parse(response.data)