静默登录 处理token过期后的无缝连接请求 解决方案

405 阅读1分钟

如题 ,在移动端开发经常遇到静默登录的情况。如果有登录页的项目还好。没有登录页,并且不能跳转到首页的就必须要拦截请求才能处理了。

这样做以后启动项目时并不需要去主动登录,触发需要登录的接口就可以直接静默处理了

封装请求

//记录登录状态
let inLogin = false 
async function fetchPromise(params) {
    // 获取本地存储的token
  let token = (await $utils.getStore('token')).data
  return new Promise((resolve, reject) => {
    $fetch
      .fetch({
        url: baseUrl + params.url,
        method: params.method,
        data: params.data,
        header: {
          "X-Token": "Bearer " + token || '',
        },
      })
      .then(async (response) => {
        const result = response.data;
        const content = JSON.parse(result.data);
        //收集token相关的状态码
        let goLoginList = [410000, 410001, 410002]
        let statuTime = null;
        // 如果接口状态为410000 重新静默登录并且重新请求
        if (goLoginList.includes(content.status)) {
          // 如果是登录中,请求等待,登录结束再重新请求
          if (inLogin) {
            statuTime = setInterval(() => { 
              if (!inLogin) {
                fetchPromise(params).then(res => {
                  resolve(res)
                })
                clearInterval(statuTime)
                statuTime = null
              }
            }, 100)
          } else {
          // 开始登录
            inLogin = true
            $utils.logins(fetchPromise, params).then(res => {
            //结束登录
              inLogin = false
              resolve(res)
            })
          }
        } else if (content.status == 200) {
          // 如果请求里面有token
          if (content.data && content.data.token) $utils.setStore('token', content.data.token)   
          //  拿出数据
          let data = content.data ? content.data : ''
          resolve(data)
        } else {
          reject(content)
          if (content.msg) $utils.showToast(content.msg)
        }
      })
      .catch((error) => {
        reject(error)
      })
  })
}

这里是登录方法 在登录方法里面保存登录状态


function logins(fn,v) {
    // 开始登录状态
  return new Promise(resFn=>{
    device.getId({
      type:['device', 'mac'],
      success: function (data) {
        $apis.login.silent_login({ device_id: data.device}).then(()=>{
          // 更新用户信息
          updateUserinfo();
          // 触发登录时请求存储并调用
          if(v){fn(v).then(resFn)}
        })
      },
      fail: function () {
        showToast('请授权获取设备信息后重新打开')
        setTimeout(() => {
          router.push({
            uri: 'hap://settings/permissions'
          })
        }, 1000)
      }
    })
  })
}

感觉不是很理想,希望看一下大家的思路分享