身份认证
session 的身份验证流程
- 用户输入信息
- 服务器验证是否正确,如果正确就创建 session 并存入数据库
- 服务端向客户端返回带有 session 的 cookie
- 在接下来的每次前端请求中都会带 cookie 服务器吧 sessionID 与数据库中的相匹配
- 入伙退出登录,session 会在客户端和服务端都销毁
JWT 的身份验证流程
- 用户输入信息
- 服务器验证登录信息,如果正确返回一个已签名 token (加密字符串)
- 前端将 token 存储在客户端,一般存在 localStorage 中,但也存在 sessionStorage 和 cookie
- 接下来每次前端请求都会带上 token
- 服务器验证 token 如果 token 有效继续发送求情
- 如果退出,token 会在客户端销毁,而这一步和服务器无关
步骤
安装
jsonwebtoken:用于生成 token
express-jwt:用于验证 token
js
npm i jsonwebtoken express-jwt
- 发送请求,服务端生成 token
js
const jwt = require('jsonwebtoken')
const token = jwt.sign(
{ userName }, // 用户信息
'abc', // 秘钥
{ expiresIn: 60 } // 设置token的有效期
)
- 用户登录,客户端保存 token
js
localStorage.setItem('token(属性名))', response.data.token(属性值))
- 验证页面,发送 token 请求
js
// 验证用户是否登录
function isLogin() {
axios({
method: 'post',
url: '/users/isLogin',
// 请求头
headers: {
Authorization: 'Bearer ' + localStorage.token,
},
})
.then((response) => {
console.log(response.data)
})
.catch((error) => {
if (error.response.status == 401) {
alert('身份信息已过期,请从新登录')
location.href = './login.html'
}
})
}
isLogin()
- app.js 验证 token
js
var { expressjwt: expressJWT } = require('express-jwt') //解析JWT
app.use(
expressJWT({
secret: 'abc', // 生成 token 时配置的秘钥字符串
algorithms: ['HS256'], // 设置 jwt 的算法为 HS256
credentialsRequired: false, // 对于没有 token 的请求是否进行解析
}).unless({
path: ['/users/login', '/users/register', '/users/isAccess'], // 设置不需要验证 token 的路径
})
)
- 一级路径,验证是否登录
js
// 是否登录
router.post('/isLogin', async function (req, res, next) {
// 1. 获取到 token
const token = req.get('Authorization').split(' ')[1]
// 2. 解码 token
const { userName } = jwt.verify(token, 'abc')
res.send()
}
JWT 与 session 的区别
JWT 与 session 两种认证方法的区别有两个:
一是在于用户状态保存的位置,session 将用户状态保存在服务端,而 JWT 将用户状态保存在客户端
二是 session 依赖于 cookie 而实现,在每次请求是需要带上 cookie 取出响应字段与服务器端的警醒对比,而实现身份的认证,而 JWT 仅仅需要在 HTTP 的都不附上 token 由服务器 sheck signature 即可实现,无需担心 cookie 存在的 CORS 问题