gitee地址:https://gitee.com/mengxianchen/axios-request-tool?
线上体验地址:?http://121.43.41.227:82/? ?浏览器网络设置成3G 体验效果最佳
一. 创建一个空的vue2项目
?一顿操作后
1. vue create excel_demo
2. cd?excel_demo
3. npm run serve
效果如下
??
二. 前期准备
1. 关闭eslint检查
vue.config.js加上?
lintOnSave: false
2.安装插件 element-ui
npm i element-ui
main.js里面加上?
import ElementUI from 'element-ui';
import 'element-ui/lib/theme-chalk/index.css';
Vue.use(ElementUI);
2. 安装插件axios????????
npm i?axios
三. src/App.vue的内容替换成以下代码
创建两个按钮分别来演示
未封装时,如何发送get和post请求
可以看出重复的地方很多,像基地址一样,使用的axios属性一样,响应的数据格式一样,都是{code,message,data}
如果项目中请求几百个,后期更新维护会很麻烦
<template>
<div class="box">
<el-button type="primary" @click="getReq">get请求</el-button>
<el-button type="success" @click="postReq">post请求</el-button>
</div>
</template>
<script>
// 导入axios用来发请求
import axios from "axios";
export default {
name: "App",
components: {},
methods: {
// 发送get请求
getReq(){
axios({
method:'get',
url:'https://www.fastmock.site/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/getUser',
})
.then(getRes => {
console.log(getRes);
this.$message.success(getRes.data.message)
});
},
// 发送post请求
postReq(){
axios({
method:'post',
url:'https://www.fastmock.site/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/updUser',
data:{ p1 :'参数1', p2 :'参数2'}
})
.then(postRes => {
console.log(postRes);
this.$message.success(postRes.data.message)
});
},
},
};
</script>
<style>
.box{
margin: 100px 500px;
}
</style>
四. 在src目录下新建?utils/request.js
封装一个axios实例,导出去供人使用
该工具实现了
1. 统一基地址
2. 每次发送请求出现加载遮罩层,响应数据后关闭遮罩层
3. 优化响应数据格式,降低复杂度
import axios from "axios"
import { Loading } from 'element-ui';
// 封装自定义axios实例
const serve = axios.create({
// 设置基地址
baseURL:'https://www.fastmock.site',
})
let loadingInstance
// 请求拦截器
serve.interceptors.request.use(function (config) {
// 开启加载弹窗
loadingInstance = Loading.service({ fullscreen: true });
// console.log('开启弹窗',loadingInstance);
return config;
}, function (error) {
return Promise.reject(error);
});
// 响应拦截器
serve.interceptors.response.use(function (response) {
// 关闭加载弹窗
// 如果响应过快需要将浏览器Network里网络设置成3G,才能看到加载效果
loadingInstance.close();
console.log('减少复杂度之前的响应数据',response);
// 优化响应数据格式,减少复杂度
return {
code: response.data.code,
message: response.data.message,
data: response.data.data,
}
}, function (error) {
return Promise.reject(error);
});
export default serve
五. 在App.vue使用
导入axios改成导入工具层的request.js
代码优化为↓
<template>
<div class="box">
<el-button type="primary" @click="getReq">get请求</el-button>
<el-button type="success" @click="postReq">post请求</el-button>
</div>
</template>
<script>
// 导入axios工具文件用来发请求
import request from "@/utils/request";
export default {
name: "App",
components: {},
// 封装请求工具优化后↓↓↓
methods: {
// 发送get请求
async getReq() {
const res = await request({
url: "/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/getUser",
});
console.log(res);
this.$message.success(res.message);
},
// 发送post请求
async postReq() {
const res = await request({
url: "/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/updUser",
method: "post",
data: { p1: "参数1", p2: "参数2" },
});
console.log(res);
this.$message.success(res.message);
},
},
};
</script>
<style>
.box {
margin: 100px 500px;
}
</style>
看到这里 ,一部分长得好看的小伙伴,会想到当前代码可以再分一个 接口层
六. 再次解耦,请求都放到接口层 创建目录src/api/user/user.js
src 下创建 api/user.js
import request from '@/utils/request'
export function apiGet(){
return request({
url: '/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/getUser',
method: 'get'
})
}
export function apiPost(data){
return request({
url: '/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/updUser',
method: 'post',
data
})
}
这里的传参可能不好理解! 为什么参数传了 url和method? 能在 utils/request.js 里用?
utils/request.js 里并没有写接收这两个参数的代码。
因为?utils/request.js 导出的是一个自定义配置的axios实例,给它传参数等于在给它进行自定义配置。 具体能传哪些参数 参考axios文档:?http://www.axios-js.com/zh-cn/docs/#axios-create-config
?
app.vue代码优化。?script标签覆盖为以下代码
此时页面效果一样,导入接口的方法后,仅一行代码就能发送请求。
记得加 async await来修饰
<script>
// 导入接口层方法
import {apiGet,apiPost} from "@/api/user";
export default {
name: "App",
components: {},
// 封装请求工具优化后↓↓↓
methods: {
// 发送get请求
async getReq() {
const res = await apiGet();
console.log(res);
this.$message.success(res.message);
},
// 发送post请求
async postReq() {
const res = await apiPost({ p1: "参数1", p2: "参数2" });
console.log(res);
this.$message.success(res.message);
},
},
};
</script>
七. 优化遮罩层 请求时控制是否使用
原理就是发送个自定义请求头参数,请求拦截器里通过判断该参数来控制
utils/request.js 中请求拦截器和响应拦截器 的代码优化如下
// 请求拦截器
serve.interceptors.request.use(function (config) {
console.log('请求头',config.headers);
// 请求头中接收参数 是否加载遮罩层弹窗()
const isLoading = config.headers.isLoading
// isLoading存在 则开启遮罩层弹窗
isLoading ? loadingInstance = Loading.service({ fullscreen: true }) : null
// console.log('开启弹窗',loadingInstance);
return config;
}, function (error) {
return Promise.reject(error);
});
// 响应拦截器
serve.interceptors.response.use(function (response) {
// 如果响应过快需要将浏览器Network里网络设置成3G,才能看到加载效果
// 关闭遮罩层弹窗(如果有)
loadingInstance && loadingInstance.close();
console.log('减少复杂度之前的响应数据',response);
// 优化响应数据格式,减少复杂度
return {
code: response.data.code,
message: response.data.message,
data: response.data.data,
}
}, function (error) {
return Promise.reject(error);
});
api/user.js 代码优化如下
import request from '@/utils/request'
export function apiGet(isLoading = false){
return request({
url: '/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/getUser',
method: 'get',
headers:{ isLoading }
})
}
export function apiPost(data, isLoading = false){
return request({
url: '/mock/7a24fbd3721a2bb3ca8b81050909b081/login/api/updUser',
method: 'post',
data,
headers:{ isLoading }
})
}
App.vue 中 methods里的方法? 优化如下
用法:只需要传 bool值?
?true 或 1 或其他会隐式转化为true的值都可以? 都会触发遮罩层 !
methods: {
// 发送get请求
async getReq() {
const res = await apiGet(true);
console.log(res);
this.$message.success(res.message);
},
// 发送post请求
async postReq() {
const res = await apiPost({ p1: "参数1", p2: "参数2" }, true);
console.log(res);
this.$message.success(res.message);
},
},
完工,各位大佬可以在此基础上优化
|