• Vue+element搭建后台管理系统五、网络请求封装vue封装axiaos


    上一章我们详解了项目的架构目录,这一章主要学习对接口的封装。

    网络请求封装是每个前端项目必不可少的一项,有利于方便统一管理,比如在请求头统一加上后台校验数据,这样就没必要在每个接口中都写一遍了嘛,这也是面向对象编程的一个好的提现。

    我们这次选用的是axios插件,这个插件优点还是蛮多的,支持promise,可以拦截请求和拦截响应,客户端支持防御XSRF攻击等等,那么我们就开始吧。

    一、安装axios

    老规矩,在控制台中输入:

    npm install axios -S

    二、对axiaos做封装

    我们在request目录的index.js文件中,

    导入axiaos插件,主角。

    导入用到的element-ui中的Message弹窗组件,主要用作提示报错,如:接口请求报错了,可以在响应拦截中弹窗提示相应信息。

    导入store,用于设置全局的状态管理,比如常用到的用户信息,站点管理这些。

    导入auth,封装有获取token方法的插件,如:获取浏览器缓存中的token信息。

    导入路由router,用于路由跳转,如:后台返回登录信息过期,那么我们在请求响应拦截捕获到了,然后我们就可以直接做路由跳转到登录页面了。

    并写入相应的请求拦截和响应拦截。

    import axios from 'axios'
    import { Message } from 'element-ui' //element弹窗
    import store from '@/store' //登录信息
    import { getToken } from '@/utils/helper/auth.js' //获取token
    import Router from '@/router/index.js' //路由对象
    
    const service = axios.create({
        timeout: 10000,
    })
    
    // request interceptor
    //请求拦截
    service.interceptors.request.use(
        (config) => {
            //header存放token-一般接口要求
            config.headers['token'] = getToken()
            //设置请求接口
            service.prototype.requestUrl = config.url
            return config
        },
        (error) => {
            // do something with request error
            console.log(error) // for debug
            return Promise.reject(error)
        }
    )
    
    // response interceptor
    //响应拦截
    service.interceptors.response.use(
        /**
         * 这里会返回http请求的信息,如数据、状态码
         */
        (data) => {
            data = data.data
            let res = {}
    
            if (data.code == '0') {
                console.log('接口请求数据正常')
            } else if (data.code == 201 || data.code == '9001') {
                Message({
                    message: '账号信息已过期,请重新登录',
                    type: 'warning',
                })
                //清空用户信息
                store.commit('user/logout')
                Router.push({ path: '/login' })
            } else {
                Message({
                    message: data.msg,
                    type: 'error',
                })
            }
    
            // 处理返回格式-自定义返回所有数据或数据包裹指定数据
            // eslint-disable-next-line no-prototype-builtins
            if (data.hasOwnProperty('data') && data.data != null && !data.total && service.prototype.requestUrl.indexOf('auth') == -1) {
                res = data.data
            } else {
                res = data
            }
    
            return res
        },
        (error) => {
            console.log('err' + error) // for debug
            Message({
                message: error.message,
                type: 'error',
                duration: 5 * 1000,
            })
            return Promise.reject(error)
        }
    )
    
    export default service

    加好上面的内容后,补充一下需要导入的内容。在utils文件夹下创建helper文件夹,然后新建auth.js文件,加入下面获取token的方法。

    utils/helper/auth.js内容:

    const TokenKey = 'token'
    
    export function getToken() {
      return localStorage.getItem(TokenKey)
    }
    
    export function setToken(token) {
      return localStorage.setItem(TokenKey, token)
    }
    
    export function removeToken() {
      return localStorage.removeItem(TokenKey)
    }

    补充一下store中的内容:

    store/modules/user.js内容:

    export default {
        namespaced: true,
        state: {
            userInfo: {
                id: null,
                account: '',
                realName: '',
                companies: '',
                sites: null,
            },
        },
        mutations: {
            setUserInfo(state, param) {
                state.userInfo = param
            },
            logout(state, param) {
                state.userInfo = param
            },
        },
    }

    补充好上面的内容后,然后做一下全局配置,这样可以在vue文件中通过this调用了。

    三、全局配置

    api目录下创建index.js文件

    导入Vue,通过原型继承,实现全局注册。

    导入string的toLowerCaseBar,这个方法是用来将小写驼峰的字符串转成小写横杆的字符串,比如:getDataApi转成get-data-api,主要的作用是做一个请求方法的统一管理。

    并写入下面内容:

    import Vue from 'vue'
    import { toLowerCaseBar } from '@/utils/helper/string.js' // 格式(小写驼峰)转 格式(小写横杠)
    
    /**
     * 页面调用API目录方法
     * @func ajax
     * @param {String} route 请求路径
     * @param {Object} param 接口参数
     */
    const ajax = (route, param) => {
        let arr = route.split('/') // 目录 -> 文件 -> 方法
        // 获取组s件
        let components = require('./' + toLowerCaseBar(arr[0]) + '/' + toLowerCaseBar(arr[1]) + '.js')[arr[2]]
        return components(param)
    }
    
    /**
     * 页面调用API目录方法
     * @func ajax
     * @param {String} route 请求路径
     * @param {Object} param 接口参数
     */
    Vue.prototype.$ajax = ajax
    
    export default ajax

    补充一下上述导入的string.js文件,同样在utils文件夹下的helper文件夹,创建string.js,为啥叫string.js呢?

    主要类似一个类吧,主要应用于字符串类型的操作,字符串截取,字符串转换等等。

    然后添加以下代码:

    /**
     * 格式(小写驼峰)转 格式(小写横杠)
     * @func toLowerCaseBar
     */
    export const toLowerCaseBar = (data) => {
        let res = ''
    
        if (data) {
            res = data.replace(/[A-Z]/g, (item) => `-${item.toLowerCase()}`)
        }
    
        return res
    }

    封装的工作做好了,然后在main.js文件中做一下全局导入,通过import 导入api下的index.js文件即可。

    ....
    import 'element-ui/lib/theme-chalk/index.css' //样式文件一定要引入
    
    import './api/index.js'
    //载入路由
    ....

    四、添加mock数据-测试

    现在我们在搭建框架的过程中,后台应该还没出接口供我们测试,那么就需要我们去造数据。

    打开cmd,安装我们所用到的工具,mockJS

    npm install --save-save mockjs

    然后我们在src目录下创建service文件夹,创建两个文件,index.js,test.mock.js主要用来存放虚拟接口数据的。

     index.js文件代码如下:

    import Mock from 'mockjs'
    
    //入口文件
    Mock.setup({
        timeout: '500-800',
    })
    
    const context = require.context('./', true, /\.mock.js$/)
    
    context.keys().forEach((key) => {
        Object.keys(context(key)).forEach((paramKey) => {
            Mock.mock(...context(key)[paramKey])
        })
    })
    export default context

    这个文件的作用将service下的每个数据模块导入然后再全局导出,这样我们在开发的时候,就可以做虚拟数据的按模块独立出来。例如下面的test.mock.js文件,可以作为一部分接口数据。

    test.mock.js代码如下:

    import Mock from 'mockjs'
    
    const { Random } = Mock
    
    export default [
        RegExp('/login.*'),
        'get',
        {
            'range|50-100': 50,
            'data|10': [
                {
                    // 唯一 ID
                    id: '@guid()',
                    // 生成一个中文名字
                    cname: '@cname()',
                    // 生成一个 url
                    url: '@url()',
                    // 生成一个地址
                    county: Mock.mock('@county(true)'),
                    // 从数组中随机选择一个值
                    'array|1': ['A', 'B', 'C', 'D', 'E'],
                    // 随机生成一个时间
                    time: '@datetime()',
                    // 生成一张图片
                    image: Random.dataImage('200x100', 'Mock Image'),
                },
            ],
        },
    ]

    做好之后,在main.js文件中导入:

    做好全局导入之后,我们就可以通过请求来做测试了。

    简单写一个请求数据的方法,在api文件夹下创建login文件夹,然后在login文件夹下创建auth-api.js,添加下面内容:

    导入request,前面封装的网络请求方法

    导入url,全局配置文件中的请求域。config.index.js代码如下:(域名记得换成自己本机nodeJS运行服务的域名)

    /* eslint-disable no-undef */
    const CONFIG = {
        //开发环境
        development: {
            url: 'http://192.168.0.101:8080', //本机ip地址域名
        },
        //生产环境
        production: {
            url: 'https://getman.cn/mock', //生产环境的请求域名
        }
    }
    export default CONFIG[process.env.NODE_ENV]

    auth-api.js代码入下:

    import request from '@/utils/request/index.js'
    import config from '@/config/config.index.js'
    
    /**
     * @description 登录
     * @param {JSON} param
     * @returns
     */
    export const loginApi = (param) => {
        return request({
            method: 'post', // 请求方式: GET、POST
            url: config.url + '/login',
            data: param, // 请求参数
        }).then((res) => {
            return new Promise((resolve) => {
                resolve(res)
            })
        })
    }

    然后我们在App.vue中添加一个点击方法,用作调起请求用的。

    <template>
      <div id="app">
        <img alt="Vue logo" src="./assets/logo.png">
        <el-button type="primary" @click="getData">测试按钮</el-button>
        <HelloWorld msg="Welcome to Your Vue.js App"/>
      </div>
    </template>
    
    <script>
    import HelloWorld from './components/HelloWorld.vue'
    
    export default {
      name: 'App',
      components: {
        HelloWorld
      },
      methods: {
          getData() {
              this.$ajax('login/authApi/loginApi', {}).then(res => {
                  console.log(res)
              }).catch(rej => {
                  console.log(rej)
              })
          }
      }
    }
    </script>
    
    <style>
    #app {
      font-family: Avenir, Helvetica, Arial, sans-serif;
      -webkit-font-smoothing: antialiased;
      -moz-osx-font-smoothing: grayscale;
      text-align: center;
      color: #2c3e50;
      margin-top: 60px;
    }
    </style>

     点击测试按钮,就可以正常调用网络请求的方法。

     本章内容就到这里结束吧,下一章为大家讲一下如何去实现权限管理。

  • 相关阅读:
    复旦大学数学学院18级高等代数II期中考试第七大题的三种证法及其推广
    复旦大学2019--2020学年第一学期高等代数I期末考试情况分析
    复旦大学2019--2020学年第一学期(19级)高等代数I期末考试第六大题解答
    复旦大学2019--2020学年第一学期(19级)高等代数I期末考试第七大题解答
    复旦大学2019--2020学年第一学期(19级)高等代数I期末考试第八大题解答
    复旦高等代数I(19级)每周一题
    复旦大学数学学院 18 级本科生对每周一题的评价
    复旦大学2018--2019学年第二学期高等代数II期末考试情况分析
    复旦大学2018--2019学年第二学期(18级)高等代数II期末考试第六大题解答
    CentOS7安装MySQL
  • 原文地址:https://www.cnblogs.com/liao123/p/15707535.html
Copyright © 2020-2023  润新知