什么是鉴权

412 阅读4分钟

📍 小知识,大挑战!本文正在参与“程序员必备小知识”创作活动。

前言

鉴权作为前后端登录必不可少的一部分,作用可谓举足轻重,下面就来简单说说前后端常见的几种鉴权方式

Cookie

Cookie是某些网站为了辨明用户身份而存储在用户本地终端上的数据(通常经过加密),由用户客户端暂时或永久保存的信息

Cookie的本质是字符串,它以键值对的形式存储在客户端的硬盘或内存中(设置cookie过期时间存放在硬盘中,否则存放在内存中),通常,它用于判断两个请求是否来自于同一个浏览器,例如用户保持登录状态。

image.png

Cookie中的DomainPath定义了 Cookie 的作用域:即 Cookie 应该发送给哪些 URL。

Domain 标识指定了哪些主机可以接受 Cookie。如果不指定,默认为当前主机(不包含子域名)。如果指定了Domain,则一般包含子域名。

注意:Cookie一般用于存储用户登录信息,且大小不能超过4KB

Session

在Web开发中,通常使用session来完成会话跟踪,由于服务器分配一个唯一的sessionId作为客户端的cookie来作为标识,因此session的底层依赖Cookie技术

由于http请求是无状态的,也就是说服务器正常情况下是不知道是当前请求是来源于哪个客户端的,当客户端第一次请求时,服务端会开启一个会话来记录当前用户的状态,并向客户端返回一个记录当前会话的id---sessionId,当客户端下次访问时会在cookie中携带sessionId,服务端拿到sessionId找到对应的session。

在掘金页的Cookie中可以看到保存的sessionid:

image.png 为了防止服务器端的session过多导致内存溢出,web服务器默认会给每个session设置一个有效期,若有效期内客户端没有访问过该session,服务器就认为该客户端已离线并删除该session。

image.png

Token

Token是一个令牌,一般由用户信息、时间戳和算法加密的签名构成,用来唯一识别一个客户端。

token的优势

1.无状态、可扩展

2.支持移动设备

3.跨程序调用

4.安全

由于每一次请求都需要将token放在http headers中,我们可以在使用axios请求拦截器中将token携带在header中

if (store.getters.token) {
  config.headers['X-Token'] = getToken()
}
return config

Token鉴权大致流程

  1. 客户端携带用户名和密码登陆
  2. 服务端通过用户验证后会生成一个token发送给客户端
  3. 客户端收到token后保存在Cookie或local storage中
  4. 客户端需要请求数据时,在http请求头中携带token
  5. 服务端校验token成功后,返回数据给客户端 image.png

JWT

JWT(Json Web Token)是一个定义在RFC 7519的一种token规范,它定义了一种简洁的、自包含的协议格式,用于在通信双方传递json对象,传递的信息经过数字签名可以被验证和信任。JWT可以使用HMAC算法或使用RSA的公钥/私钥对来签名,防止被篡改。

image.png

JWT的优点

  • 基于json,易于解析
  • 可自定义内容,易扩展
  • 基于非对称算法和数字签名,安全性高

JWT的组成

JWT由Header(头部)、Payload(负载),Signature(签名)三部分组成,这三部分之间用.分隔,

Header通常使用常用的HS256RS512加密算法生成

image.png Payload用于传输需要的字段

image.png

signature是由算法与私有秘钥SECRET_KEY进行加密得到的字符串

image.png

通常使用local storage保存JWT

image.png

开始上手JWT

安装

npm i -S jsonwebtoken

使用(伪代码)

const jwt = require('jsonwebtoken')
const PRIVATE_KEY = 'secretkey'    // jwt私钥 自定义
const JWT_EXPIRED = 60 * 60    // 1小时

login(username, password).then(user => {
    if (!user || user.length === 0) {
      // 登陆失败
    } else {
      const token = jwt.sign(
        { username },
        PRIVATE_KEY,
        { expiresIn: JWT_EXPIRED }
      )
      // 发放token
    }
})

更多关于JWT可以查看JWT官网