Axios配置

74 阅读3分钟

Axios的介绍参考文章# Axios 简单介绍 juejin.cn/post/709445…

为了方便文件管理,建立了以下目录:

image.png

axiosConfig.js Axios相关配置
axiosInstance.js Axios实例
index.js Axios接口封装
urls.js 接口地址

需要安装axios插件:

npm install axios

axiosConfig.js

import { Message } from "element-ui";

/**
 * axios请求配置
 */
const axiosConfig = {
    baseURL: '/',
    timeout: 60000,
    responseType: 'json',
    withCredentials: true,
    headers: {
        'Content-Type': 'application/json;charset=utf-8'
    }
};

/**
 *  在发送请求之前做些什么,如添加token、header配置等。
 */
function onRequestSucceed(config) {
    // 这里设置一个token,一般token是接口返回然后缓存在前端。
    if (sessionStorage.getItem('token')) {
        config.headers['token'] = sessionStorage.getItem('token');
    }

    // 不同的模块,添加模块id,这里需要结合router配置,在前置路由中缓存模块id,然后这里取出对应的模块id。就可区分每个模块的访问量。

    if (sessionStorage.getItem('menuCode')) {
        config.headers.menuCode = sessionStorage.getItem('menuCode');
    }

    return config;
}

/**
 * 对请求错误做些什么
 */
function onRequestFailed(error) {
    return Promise.reject(error);
}

/**
 * 对响应数据做点什么,2xx 范围内的状态码都会触发该函数。
 */
function onResponseSucceed(response) {
    // 可根据状态码的值,做不同的操作。
    if (response && response.status == 200) {
        return Promise.resolve(response);
    } else {
        return Promise.reject(response);
    }
}

/**
 * 对响应错误做点什么,超出 2xx 范围的状态码都会触发该函数。
 */
function onResponseFailed(error) {
    console.log('99',error);
    switch (error.response && error.response.status) {
        case 401:
            // 401 Unauthorized 请求需要用户身份验证,跳转至登录页面。
            Message({
                message: '登陆过期,请重新登录。',
                type: 'error'
            });
            // 登录页面
            // router.push('/login');
            // 登录页面地址
            let redirectUrl = 'http://redirectUrl';
            window.location.href = redirectUrl;
            break;
        case 403:
            // 403 Forbidden 请求被服务器拒绝,无权访问,跳转至无权限页面。
            Message({
                message: '暂无权限',
                type: 'error'
            });
            Message
            router.push('/noAuth');
            break;
        case 404:
            // 404 请求不存在。
            Message({
                message: '请求不存在',
                type: 'error'
            });
            router.push('/404');
            break;
        default:
            Message({
                message: error.response && error.response.data.message,
                type: 'error'
            });
    }
    return Promise.reject(error);
}

export { axiosConfig, onRequestSucceed, onRequestFailed, onResponseSucceed, onResponseFailed };

axiosInstance.js

import axios from "axios";
import { axiosConfig, onRequestSucceed, onRequestFailed, onResponseSucceed, onResponseFailed } from '@/scripts/axiosConfig.js';

// 创建axios实例
const Axios = new axios.create(axiosConfig);

// 请求拦截器
Axios.interceptors.request.use(onRequestSucceed,onRequestFailed);

// 响应拦截器
Axios.interceptors.response.use(onResponseSucceed,onResponseFailed);

export default Axios;

urls.js

const URL = {
    // get接口
    getInfo:'/api/info/xxx',
    // post接口
    getMapInfo:'/api/map/info/xxx'
}

export default URL;

index.js

import Axios from './axiosInstance';
import URL from './urls';

const API = {
    // get
    getInfo(params) {
        return Axios.get(URL.getInfo, { params });
    },
    // post
    getMapInfo(params) {
        return Axios.post(URL.getMapInfo, params);
    }
};

export default API;

界面使用接口:

DeptMap.vue

<template>
    <div class="dept-map-container">
        {{ type }}
    </div>
</template>

<script>
import API from '@/scripts/index.js';

export default {
    name: 'DeptMap',
    data() {
        return {
            type: '部门地图'
        };
    },
    mounted(){
        this.getMapInfo();
    },
    methods: {
        /**
         * 调用接口
         */
        getMapInfo() {
            let params = {
                type: 'map'
            };
            API.getMapInfo(params).then((res) =>{
                console.log(res);
            });
        }
    }
};
</script>

<style lang="less">
.dept-map-container {
    font-size: 100px;
    color: #377ef9;
}
</style>

因为在axiosConfig.js中获取的menuCode是每次跳转缓存的,所以需要在router/index.js中设置:

1.给每个路由添加meta,并给meta添加menuCode属性。

2.前置路由中缓存meta中的menuCode。

router/index.js

import Vue from 'vue';
import VueRouter from 'vue-router';

// 路由组件
import Home from '@/views/Home.vue';

Vue.use(VueRouter);

// 创建VueRouter实例
const router = new VueRouter({
    // 路由模式
    mode: 'history',
    // 配置路径和对应的组件
    routes: [
        {
            path: '/',
            name: 'home',
            component: Home,
            redirect: '/deptInfo',
            children: [
                {
                    path: '/deptInfo',
                    name: 'deptInfo',
                    component: () => import(/* webpackChunkName: "DeptInfo" */ '@/views/DeptInfo'),
                    meta: {
                        menuCode: 1,
                        moduleName: '部门信息'
                    },
                    children: [
                        {
                            path: 'deptInfoOne', // 注意路径不加/
                            name: 'deptInfoOne',
                            component: () => import(/* webpackChunkName: "deptInfoOne" */ '@/views/DeptInfo/components/deptInfoOne.vue'),
                            meta: {
                                menuCode: 3,
                                moduleName: '部门信息子路由1'
                            }
                        },
                        {
                            path: 'deptInfoTwo', // 注意路径不加/
                            name: 'deptInfoTwo',
                            component: () => import(/* webpackChunkName: "deptInfoTwo" */ '@/views/DeptInfo/components/deptInfoTwo.vue'),
                            meta: {
                                menuCode: 4,
                                moduleName: '部门信息子路由2'
                            }
                        }
                    ]
                },
                {
                    path: '/deptMap',
                    name: 'deptMap',
                    component: () => import(/* webpackChunkName: "deptMap" */ '@/views/DeptMap.vue'),
                    meta: {
                        menuCode: 2,
                        moduleName: '部门地图'
                    }
                }
            ]
        },

        {
            path: '/404',
            name: 'notFound',
            component: () => import(/* webpackChunkName: "notFound" */ '@/views/exception/notFound.vue')
        },
        {
            path: '/noAuth',
            name: 'noAuth',
            component: () => import(/* webpackChunkName: "noAuth" */ '@/views/exception/noAuth.vue')
        },

        // 需要放在最后
        {
            path: '*',
            redirect: '/404',
            hidden: true
        }
    ]
});

// 可选,全局前置路由守卫,初始化时执行、每次路由切换前执行。
router.beforeEach((to, from, next) => {
    // 路由若包含aaa,则可处理。
    if (to.path.includes('deptInfoOne')) {
        // next(); // 放行,让路由正常跳转。
        // next('/'); // 回到首页。
        // next(false); // 在当前路由不跳转。
        // next(to.path); // 强制跳转至指定路由。
    } else {
        // 处理缓存、权限控制等。
    }
    sessionStorage.setItem('menuCode', to.meta.menuCode);
    next();
});

export default router;