从PC/移动端跳转到网页端时TOKEN失效导致验证失败处理

以前处理过一个BUG,在其他端口点击跳转到网页端时,用户继续操作时没有权限上传失败、或没有浏览权限跳转到404页面

这个问题的是因为在跳转的过程中token没有传递过来,为了解决这个问题,写了一个跳转页面,接收加密过的用户id、sessionkey、url

在此页面进行权限验证并存入缓存,成功则跳转到url,废话不多说,上代码:

//服务端
<?php
//加密解密服务
require("common/aes.php");

// 定义项目路径
defined('API_ROOT') || define('API_ROOT', dirname(__FILE__) . '/..');
define('VERSION', 'test'); // develop=>开发,test=>测试,product=>正式

// 引入composer
require_once API_ROOT . '/vendor/autoload.php';

// 时区设置
date_default_timezone_set('Asia/Shanghai');
session_start();
$userid = $_GET['u'];
$sessionKey = $_GET['s'];
$go = $_GET['g'];

if (isset($userid) && strlen($userid) > 0 && isset($sessionKey) && strlen($sessionKey) > 0 && isset($go) && strlen($go) > 0) {
    $des = new TripleAES();
    $userid = (int)trim($des->Decrypt($userid));
    $sessionKey = trim($des->Decrypt($sessionKey));
    $go = trim($des->Decrypt($go));

    $checkErrMsg = "";
    $data = DoUserLogin($userid, "", $sessionKey, $checkErrMsg) or die('你当前已离线,请重新登录在刷新重试!' . $userid . '--' . $sessionKey . '---' . $go);
    $nulstr = strstr($go, chr(0));
    if ($nulstr) {
        $go = substr($go, 0, strlen($go) - strlen($nulstr));
    }
    header("Location: " . $go);
} else {
    die('你当前已离线,请重新登录在刷新重试!');
}
//验证并缓存用户数据
function DouserLogin($userid, $password, $sessionKey, &$checkErrMsg)
{

    try {
        $client = \GrpcServer\ClientFactory::createClient(
            'tokencheck.TokenCheck', VERSION
        );
        $req = new \Cfwf\Micro_service\Tokencheck\CheckUserTokenWhenClientAccessRequest();
        $req->setUserid($userid);
        $req->setToken($sessionKey);
        $req->setOs(1);
        list($data) = $client->CheckUserTokenWhenClientAccess($req)->wait();
        $lists = $data->toArray();
        if ($lists['result'] != 1) {
            return false;
        } else {
            $request['os'] = 1;
            $request['user_id'] = $userid;
            $request['token'] = $sessionKey;
            $request['web_level'] = 0;
            $AccountGrpc = new \Common\Domain\AccountGrpc();
            $data = $AccountGrpc->setLoginUserInfo($request, VERSION);
            $_SESSION['loginUserInfo'] = $data;
            return $data;
        }
    } catch (\Exception $e) {
        return false;
    }
}

?>

跳转到新页面的时候,发现有时还是没有权限,经过检查,前端把token存在在浏览器缓存了,刚跨平台跳转当然不会有浏览器缓存,所以在前端请求前需要把token存入浏览器缓存内。

我在vue的钩子方法内,首先调用请求到接口获取用户数据,保证后续的请求都拿到了 token,还是直接上代码。

...
  created() {
    this.id = this.$route.query.id; // 栏目id
    this.a_id = this.$route.query.a_id; // 活动id
    this.getLoginInfo();
  },
.....
  methods: {
    // 获取登录数据
    //这个接口在白名单内,无需token验证
    async getLoginInfo() {
      const data = {
        s: "Common.Account.getLoginUserInfo",
      };
      //调用接口
      let response = await api.post(url.httpUrl, data);
      const res = response.data.data;
      const isLogin = api.eventListener(res);
      this.user_id = localStorage.getItem("ms_userid");
      this.uploadUrl = url.uploadPath; // 文件上传地址
      this.uploadData = {
        UserId: localStorage.getItem("ms_userid"),
        SessionKey: localStorage.getItem("ms_token"),
        OS: 4,
        CheckCode: api.randomString(40),
      };
      this.options = {
        target: url.uploadPath, // 上传地址
        testChunks: false,
        singleFile: false, // 启用单个文件上传。上传一个文件后,第二个文件将超过现有文件,第一个文件将被取消。
        chunkSize: "1048576" * 1, //分块大小 单位(M)
        query: {
          //传参
          UserId: localStorage.getItem("ms_userid"),
          SessionKey: localStorage.getItem("ms_token"),
          OS: 4,
          PluginType: 1,
        },
      };
      this.function1();
    },
},
...
//api.js内方法
    // 监听登录状态做出相应处理,返回是否登录
    eventListener(res) {
        if (res) {
            localStorage.setItem("ms_username", res.username);
            localStorage.setItem("ms_userid", res.userid);
            localStorage.setItem("ms_userface", res.userface);
            localStorage.setItem("ms_schoolid", res.schoolid);
            localStorage.setItem("ms_identity", JSON.stringify(res.identity));
            localStorage.setItem("ms_userAuth", JSON.stringify(res.userAuth));
            localStorage.setItem("ms_schoolname", res.schoolname);
            localStorage.setItem("ms_token", res.token);
            localStorage.setItem("ms_token_endtime", res.token_endtime);
            return true;
        } else {
            //清除缓存
            this.clearLoginInfo();
            return false;
        }

    },
   //api.js 内封装的post请求
    post(url, data) {
        if (!data.userid) {
            data.userid = localStorage.getItem("ms_userid") ? localStorage.getItem("ms_userid") : 1;
        }
        //前端请求携带的token
        data.token = localStorage.getItem("ms_token");
        return axios({
            method: 'post',
            url,
            data: qs.stringify(data),
            timeout: 30000,
            headers: {}
        }).then(function (response) {
            if (response.data.ret != 200) {
                v.$notify({
                    message: "当前页面部分功能暂时不可用,请稍后再试。",
                    offset: 100
                });
                return false;
            }
            return response;
        }
        ).catch(function (error) {
            console.log(error);
            // 网络异常引发的错误
        });
    },

至此,这个因为权限已经解决了。

 

 

 

 

 

 

 

 

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值