欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页  >  IT编程

浅析微信扫码登录原理(小结)

程序员文章站 2022-10-08 13:39:06
微信扫码登录原理解析 扫码登录是现在流行的登录方式,使用这种方式及其方便,而且安全 扫码登录流程 原理 获取唯一的uuid, 以及包含uid信息的二维码...

微信扫码登录原理解析

扫码登录是现在流行的登录方式,使用这种方式及其方便,而且安全

扫码登录流程

浅析微信扫码登录原理(小结)

原理

获取唯一的uuid, 以及包含uid信息的二维码

浅析微信扫码登录原理(小结)

// 获取uuid
 getuuid: function() {
  var e = t.defer();
  return window.qrlogin = {},
  $.ajax({
   url: i.api_jslogin,
   datatype: "script"
  }).done(function() {
   200 == window.qrlogin.code ? e.resolve(window.qrlogin.uuid) : e.reject(window.qrlogin.code)
  }).fail(function() {
   e.reject()
  }),
  e.promise
 }

浏览器轮询服务器,获取扫码状态

// 查看扫码状态
checklogin: function(e, a) {
 var n = t.defer()
  , a = a || 0;
 return window.code = 0,
 window.checkloginpromise = $.ajax({
  url: i.api_login + "?loginicon=true&uuid=" + e + "&tip=" + a + "&r=" + ~new date,
  datatype: "script",
  timeout: 35e3
 }).done(function() {
  new regexp("/" + location.host + "/");
  if (window.redirect_uri && window.redirect_uri.indexof("/" + location.host + "/") < 0)
   return void (location.href = window.redirect_uri);
  var e = {
   code: window.code,
   redirect_uri: window.redirect_uri,
   useravatar: window.useravatar
  };
  n.resolve(e)
 }).fail(function() {
  n.reject()
 }),
 n.promise
}

根据服务器返回的扫码状态,进行相应的操作

408 扫码超时 如果手机没有扫码或没有授权登录,服务器会阻塞约25s,然后返回状态码 408 -> 前端继续轮询

浅析微信扫码登录原理(小结)

浅析微信扫码登录原理(小结)

400 二维码失效 大约5分钟的时间内不扫码,二维码失效

浅析微信扫码登录原理(小结)

201 已扫码 如果手机已经扫码,服务器立即返回状态码和用户的基本信息 (window.code=201,window.code.useravator="..."),-> 前端继续轮询

浅析微信扫码登录原理(小结)

200 已授权 如果手机点击了确认登录,服务器返回200及token -> 前端停止轮询, 获取到token,重定向到目标页

浅析微信扫码登录原理(小结)

// 根据服务器返回的扫码状态,进行相应的操作
function o(c) {
 switch (c.code) {
 case 200:
  t.newloginpage(c.redirect_uri).then(function(t) {
   var o = t.match(/<ret>(.*)<\/ret>/)
    , r = t.match(/<script>(.*)<\/script>/)
    , c = t.match(/<skey>(.*)<\/skey>/)
    , s = t.match(/<wxsid>(.*)<\/wxsid>/)
    , l = t.match(/<wxuin>(.*)<\/wxuin>/)
    , d = t.match(/<pass_ticket>(.*)<\/pass_ticket>/)
    , f = t.match(/<message>(.*)<\/message>/)
    , u = t.match(/<redirecturl>(.*)<\/redirecturl>/);
   return u ? void (window.location.href = u[1]) : o && "0" != o[1] ? (alert(f && f[1] || "登陆失败"),
   i.report(i.auth_fail_count, 1),
   void location.reload()) : (e.$emit("newloginpage", {
    ret: o && o[1],
    skey: c && c[1],
    sid: s && s[1],
    uin: l && l[1],
    passticket: d && d[1],
    code: r
   }),
   void (a.getcookie("webwx_data_ticket") || n.report(n.reporttype.cookieerror, {
    text: "webwx_data_ticket 票据丢失",
    cookie: document.cookie
   })))
  });
  break;
 case 201:
  e.isscan = !0,
  n.report(n.reporttype.timing, {
   timing: {
    scan: date.now()
   }
  }),
  t.checklogin(e.uuid).then(o, function(t) {
   !t && window.checkloginpromise && (e.isbrokennetwork = !0)
  });
  break;
 case 408:
  t.checklogin(e.uuid).then(o, function(t) {
   !t && window.checkloginpromise && (e.isbrokennetwork = !0)
  });
  break;
 case 400:
 case 500:
 case 0:
  var s = a.getcookie("refreshtimes") || 0;
  s < 5 ? (s++,
  a.setcookie("refreshtimes", s, .5),
  document.location.reload()) : e.isneedrefresh = !0;
  break;
 case 202:
  e.isscan = !1,
  e.isassociationlogin = !1,
  a.setcookie("login_frequency", 0, 2),
  window.checkloginpromise && (window.checkloginpromise.abort(),
  window.checkloginpromise = null ),
  r()
 }
 e.code = c.code,
 e.useravatar = c.useravatar,
 a.log("get code", c.code)
}

总结

  • 轮询采用的是jsonp的形式,排除了跨域问题
  • 轮询采用的后台根据扫码情况阻塞前台请求,优化轮询及减少前端的无效轮询

以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持。