zoukankan      html  css  js  c++  java
  • uniapp请求拦截

    在项目根目录下新建service文件夹,后续封装的文件放在这个文件夹下。


     
    image.png

    主要的封装是在LsxmRequest.js中,配置项在config.js中,api.js为接口的统一管理文件,项目接口增多时,可以考虑按照功能块对api.js进行进一步划分成多个模块,最后import到api.js中。
    1、利用Symbol特性定义四个私有变量,防止变量污染

    const config = Symbol('config')
    const isCompleteURL = Symbol('isCompleteURL')
    const requestBefore = Symbol('requestBefore')
    const requestAfter = Symbol('requestAfter')
    

    2、定义LsxmRequest类并添加默认配置、拦截器与请求方法

    class LsxmRequest {
        //默认配置
        [config] = {
            baseURL: '',
            header: {
                'content-type': 'application/json'
            },
            method: 'GET',
            dataType: 'json',
            responseType: 'text'
        }
        //拦截器
        interceptors = {
            request: (func) => {
                if (func) 
                {
                    LsxmRequest[requestBefore] = func
                } 
                else 
                {
                    LsxmRequest[requestBefore] = (request) => request
                }
            },
            response: (func) => {
                if (func) 
                {
                    LsxmRequest[requestAfter] = func
                } 
                else 
                {
                    LsxmRequest[requestAfter] = (response) => response
                }
            }
        }
    
        static [requestBefore] (config) {
            return config
        }
    
        static [requestAfter] (response) {
            return response
        }
    
        static [isCompleteURL] (url) {
            return /(http|https)://([w.]+/?)S*/.test(url)
        }
        
        request (options = {}) {
            options.baseURL = options.baseURL || this[config].baseURL
            options.dataType = options.dataType || this[config].dataType
            options.url = LsxmRequest[isCompleteURL](options.url) ? options.url : (options.baseURL + options.url)
            options.data = options.data
            options.header = {...options.header, ...this[config].header}
            options.method = options.method || this[config].method
    
            options = {...options, ...LsxmRequest[requestBefore](options)}
    
            return new Promise((resolve, reject) => {
                options.success = function (res) {
                    resolve(LsxmRequest[requestAfter](res))
                }
                options.fail= function (err) {
                    reject(LsxmRequest[requestAfter](err))
                }
                uni.request(options)
            })
        }
    
        get (url, data, options = {}) {
            options.url = url
            options.data = data
            options.method = 'GET'
            return this.request(options)
        }
    
        post (url, data, options = {}) {
            options.url = url
            options.data = data
            options.method = 'POST'
            return this.request(options)
        }
    }
    

    3、后续需要自定义config与获取接口地址,在类中添加get和set方法:

    setConfig (func) {
            this[config] = func(this[config])
    }
    getConfig() {
        return this[config];
    }
    

    4、用自定义插件注册的方法将apis.js(后续在main.js中需要导入apis.js)中的接口赋到自定义的Vue原型变量$lsxmApi上,为了避免每个页面都要引入一次,在每个页面的beforeCreate生命周期混入。

    LsxmRequest.install = function (Vue) {
        Vue.mixin({
            beforeCreate: function () 
            {
                if (this.$options.apis) 
                {
                    console.log(this.$options.apis)
                    Vue._lsxmRequest = this.$options.apis
                }
            }
        })
        
        Object.defineProperty(Vue.prototype, '$lsxmApi', {
            get: function () 
            {
                return Vue._lsxmRequest.apis
            }
        })
    }
    
    export default LsxmRequest
    

    5、在config.js中实例化并自定义请求配置项(此处根据项目需要在头部加入token)与拦截器

    import LsxmRequest from './LsxmRequest'
    
    const lsxmRequest = new LsxmRequest()
    
    // 请求拦截器
    lsxmRequest.interceptors.request((request) => {
        if (uni.getStorageSync('token')) {
            request.header['token'] = uni.getStorageSync('token');
        }
        return request
    })
    
    // 响应拦截器
    lsxmRequest.interceptors.response((response) => {
        console.log('beforeRespone',response);
        // 超时重新登录
        if(response.data.isOverTime){
        uni.showModal({
                title:'提示',
                content:'您已超时,请重新登录!',
                showCancel:false,
                icon:'success',
                success:function(e){
                    if(e.confirm){
                        uni.redirectTo({
                            url: '/pages/login/login'
                        })
                    }
                }
            }); 
        }
        else
        {
            return response;
        }
    })
    
    // 设置默认配置
    lsxmRequest.setConfig((config) => {
        config.baseURL = 'http://xxxxx.com'
        
        if (uni.getStorageSync('token')) {
            config.header['token'] = uni.getStorageSync('token');
        }
        return config;
    })
    
    export default lsxmRequest
    

    6、main.js中引入,将apis挂载到Vue上

    import LsxmRequest from './service/LsxmRequest.js'
    import apis from './service/apis.js'
    import lsxmRequest from './service/config.js'
    Vue.use(LsxmRequest)
    Vue.prototype.baseDomain = lsxmRequest.getConfig().baseURL
    App.mpType = 'app'
    
    const app = new Vue({
        store,
        apis,
        ...App
    })
    app.$mount()
    

    7、需要添加接口时,只需在apis.js中添加接口即可(后续可将apis.js中的接口按照功能拆分,模块化管理)

    import lsxmRequest from './config.js'
    export default{
      apis:{
            //获取验证用户令牌
            getLoginToken(data){
                return lsxmRequest.post('/xxx/xxx/getLoginToken', data)
            },
            //登录
            login(data){
                return lsxmRequest.post('/xxx/xxx/login', data)
            }
            }
    }
    

    8、至此,页面中即可使用

    this.$lsxmApi.getLoginToken({}).then((resToken) => {
            console.log(resToken)
    }




  • 相关阅读:
    导入 eclipse 的android项目 layout不显示
    asp.net内容页如何获取母版页的控件
    java开发中一些常见的异常及问题总结
    js jquery 数组的合并 对象的合并
    svn“run 'cleanup' if it was interrupted“报错的解决方法
    导出oracle整个数据库
    @Transactional 异常不回滚
    mysql与oracle 长度区别
    table表格嵌套,边框重叠变粗
    easyui easyui-combotree 模糊查询
  • 原文地址:https://www.cnblogs.com/zs521/p/14283786.html
Copyright © 2011-2022 走看看