基于element-ui,使用到vuex存储loading,除了普通和后台交互,还有上传图片到七牛,从七牛查询txt。
import axios from 'axios'
import { Message, Loading } from 'element-ui';
import store from '../store'
import commonFun from './commonFun'
const ajaxParams = {};//以完整url为key,存放每个请求的参数,避免同时多个请求被覆盖,比如noLoading,isQiNiu,isTxt等
axios.defaults = Object.assign(axios.defaults, {
baseURL: process.env.VUE_APP_HOST,
// timeout: 20000,
// withCredentials: true,//不能用这个,如果后台的跨域设置是*
/*headers:{//不能写这里,要用拦截器,不然token不会更新
token : localStorage.loginToken
}*/
})
axios.interceptors.request.use(config => {
if(!(config.isQiNiu || config.isTxt)){//isQiNiu和isTxt 都是请求第三方
config.headers.token = localStorage.loginToken;
// 请求默认60s
if(!config.timeout){
config.timeout = 60000;
}
}
let urlKey = commonFun.urlHasHttp(config.url) ? config.url : config.baseURL + config.url;//补全完整url,作为ajaxParams的key
ajaxParams[urlKey] = {
noLoading: !!config.noLoading,
isQiNiu: !!config.isQiNiu,
isTxt: !!config.isTxt,
};
if(!ajaxParams[urlKey].noLoading){
store.commit('addLoading'); //增加一个请求loading(num)
}
store.commit('addAjax');// 只要是请求 就加1
return config;
}, err=> {
console.log(err)
return Promise.reject(null);
})
axios.interceptors.response.use(response => {
let urlKey = response.config.url;
if(ajaxParams[urlKey] && !ajaxParams[urlKey].noLoading){
store.commit('subLoading');
}
store.commit('subAjax');
let data = response.data
if (data.code === 0 || data.code === '0') {
cb();
return data.data;
}else if(data.code == 10001){
store.commit('setAjaxMsg', '登录过期');
cb();
}else{
if((data.key && ajaxParams[urlKey].isQiNiu) || ajaxParams[urlKey].isTxt){
cb();
return data;
}else{
if(store.state.ajaxMsg != '登录过期'){
store.commit('setAjaxMsg', data.message);
}
cb();
return Promise.reject(null);
}
}
}, function (error) {
store.commit('subLoading');// 都有接口报错了 不管之前有没有加1,直接减1;
store.commit('subAjax');
console.log(error, JSON.stringify(error));
if(store.state.ajaxMsg != '登录过期'){
store.commit('setAjaxMsg', '网络异常,请稍后再试');
}
cb();
return Promise.reject(null);
})
function cb(){
if(store.state.ajaxNum <= 0 && store.state.ajaxMsg){
let msg = store.state.ajaxMsg;
store.commit('setAjaxMsg', '');
if(msg != '登录过期'){
Message(msg);
}else{
Message({
message: msg,
duration: 1000,
onClose: function(){
if(localStorage.needDebug){
delete localStorage.needDebug;
}else{
localStorage.loginToken = '';
window.location.href = process.env.VUE_APP_LOGINHOST;
}
}
})
}
}
}
const ajax = {}
ajax.get = (url, params, myconfig) => {
return axios.get(url, {
params: {...params, t: new Date().getTime()},
...myconfig,
})
}
ajax.delete = (url, params,myconfig) => {
return axios.delete(url, {
data: params,
...myconfig
})
}
ajax.post = (url, params,myconfig) => {
return axios(url, {
method: 'post',
data: params,
...myconfig
})
}
ajax.put = (url, params,myconfig) => {
return axios(url, {
method: 'put',
data: params,
...myconfig
})
}
ajax.all = axios.all;
ajax.spread = axios.spread;
export default ajax;
vuex里面存放的状态:
之所以分成loadingNum和ajaxNum,是因为有的请求可能不加loading
import Vue from "vue";
import Vuex from "vuex";
Vue.use(Vuex);
export default new Vuex.Store({
state: {
loadingNum: 0,
ajaxMsg: '',//多个请求的时候 只弹一个
ajaxNum: 0,
},
mutations: {
addLoading: (state) => state.loadingNum += 1,
subLoading: (state) => state.loadingNum = state.loadingNum > 0?state.loadingNum-1:0,
setAjaxMsg: (state, msg) => state.ajaxMsg = msg,
addAjax: (state) => state.ajaxNum += 1,
subAjax: (state) => state.ajaxNum = state.ajaxNum > 0?state.ajaxNum-1:0,
},
actions: {},
});
下面是使用例子:
this.$ajax.all([
this.$ajax.get('/integral/category'),
this.$ajax.get('/integral/prodhot')
])
.then(this.$ajax.spread(function (res1, res2) {
console.log(res1)
console.log(res2)
}));
// 查询txt接口
this.$ajax.get(url, null, {isTxt: true})
.then(res => {
// console.log(res)
cb(res);
})
假设请求接口,有顺序依赖:
let me = this;
me.$ajax.get('/common/uptoken')
.then(res=>{
console.log(1);
console.log(res);
return me.$ajax.get('/product/jd_product/jd_category')
})
.then(res=>{
console.log(2);
console.log(res);
return me.$ajax.get('/product/jd_product/count',{},{'noLoading':true})
})
.then(res=>{
console.log(3);
console.log(res);
return me.getCategory1();
})
.then(res=>{
console.log(4);
console.log(res);
})
-----
getCategory1(){
return this.$ajax.get('/integral/category')
},
或者使用async/await
async init(){
let res1 = await this.loadVip(),
res2 = await this.getVersion();
if(res1 && res1.list){
this.vipArr = res1.list.map(v=>{
return {
id : v.id+'',
title : '('+v.id+')'+v.title
}
})
}
this.setVersion(res2)
this.loadPage();
},
loadVip(){
return this.$ajax.get('/vip/vip_config',{status: 2,type: 1})
},
getVersion(){
return this.$ajax.get('/common/version',{os:this.formData.os})
},
setVersion(res){
let version_arr = [],version_obj = {};
if(res && res.list){
res.list.forEach((v,i)=>{
version_arr.push({
id: v.code+'',
name: v.name
})
version_obj[v.code+''] = v.name;
})
}
this.version_arr = [...version_arr];
this.version_obj = {...version_obj};
},
上传图片使用,可查看这篇文章https://www.jianshu.com/p/86fc1ab2112d