二维码扫描登录是什么原理?

手机扫描 PC 端 or Web 端账号。

既然是登录认证,本质上就是要做两件事情:

  1. 告诉系统我是谁
  2. 向系统证明我是谁

例如,常见的账号密码登录,“账号”就是做 1,“密码”就是做 2。

再比如,手机号登录,“手机号”是做 1,“短信验证码”是做 2。

告诉系统我是谁

这件事比较好做,因为扫码时,手机肯定要已经登录一个账号 A,这样扫码的时候通过后台可以知道是账号 A 扫描了二维码,需要在 PC 端登录。

image-20200411114042619

向系统证明我是谁

用户并没有输入密码,或者验证码,那是怎么证明的呢?

基于 token 的认证机制

以账号密码登录为例:

image-20200411210556986

  1. 首次登录,客户端将账号密码和设备信息传递给服务端;

  2. 服务端将账号与设备进行绑定,存储在一个数据结构中:

{
	"accountId": '账号id',
  "deviceId": "登录的设备ID",
  "deviceType": "设备类型,如ios,android,pc等",
  ...
}
  1. 服务端生成一个 token,对应了上面这个账号和设备信息等,并将token返回给客户端;

  2. 客户端得到token后,需要进行本地保存,然后在每次发起请求的时的时候都带上这个token

  3. 服务端校验token,通过后返回 API 响应。

从这个流程中可以看到,客户端没有必要也不会保存账户密码,而是保存了token

那么,token被别人知道了咋办?

其实没关系,因为服务端验证还需要设备信息,这样,别人拿了另一台设备来访问,验证也是通不过的。

可以说,客户端登录的目的,就是去获取属于自己的token

同理,扫码登录 PC 端的本质,也是 PC 端去获取属于自己的token

二维码扫描登录原理

PC 端怎么去获取属于自己的token?不可能手机端直接把token分享给 PC 端,因为设备信息是唯一的。

先来看看扫描二维码的一般步骤:

  1. 手机端已登录,PC 端未登录
  2. PC 端展现二维码
  3. 手机端扫描二维码
  4. PC 端提示“已扫描,请在手机端确认”
  5. 手机端确认登录
  6. PC 端登录成功

生成二维码

image-20200411211121261

扫描状态

image-20200411211303084

那么为什么要生成临时 token呢?

临时token的特定在于,它只能用一次,用过就失效。

所以,给手机端返回临时token可以确保扫码与登录的两步操作是同一个手机端发出的。

登录

image-20200411211350141

1、二维码状态有三种:待扫描、已扫描待确认、已确认; 2、待扫描:PC 端携带设备信息向服务端发送请求,服务端生成二维码 ID 与设备信息进行绑定,将二维码 ID 返回给 PC 端,PC 端已二维码的形式显示二维码; 3、PC 端通过轮询的方式向服务端查询二维码的状态是否发生变化; 4、移动端扫描 PC 端二维码,获取到二维码 ID,移动端带二维码 ID+移动端身份信息(token)发送给服务端,服务端验证身份信息通过后,将二维码 ID 与身份信息绑定,并生成临时 token 返回给移动端,二维码状态变为已扫描待确认; 5、移动端确认登录,并携带临时 token 请求服务端,服务端验证临时 token 通过后,改变二维码状态为已确认并生成 PCtoken,PC 端通过轮询知二维码状态.当为已确认状态时,返回 PCtoken,后续 PC 端通过 token 可以返回 API;

总结

image-20200411212304473