共计 5608 个字符,预计需要花费 15 分钟才能阅读完成。
导语:因为 http 是无状态的,申请响应过程中不存储记录用户身份信息,所以就呈现了很多用户辨认存储用户身份的办法,比方 cookie,session,jwt。我最近做的一个接口服务应用了 jwt 来存储管理用户信息,相较于本地 cookie 存储,服务器端 session 存储,jwt 就变得比拟平安和节俭不便,本文就 jwt 在 node 服务中的应用办法做一个简略的总结。
目录
- jwt 简介
- 装置配置
- 封装办法
- 实战练习
本文从以上四个方面介绍 jwt 的应用。
jwt 简介
概念
JWT全称 JSON Web Token,它是一种凋谢规范 RFC 7519,定义了一种紧凑且自蕴含的形式,用于在各方之间作为 JSON 对象平安地传输信息。JWT 能够应用密钥或应用 RSA 或 ECDSA 的公钥 / 私钥对进行签名,能够对签名进行验证。
组成部分
jwt 签名令牌个别由三局部组成,别离是 Header(头部信息),Payload(载荷),Signature(签名),例如xxxxx.yyyyy.zzzzz
。
- header
个别是存储令牌的类型和签名算法,比方:
{
"alg": "HS256",
"typ": "JWT"
}
- Payload
个别是存储申明,也就是用户信息和附件数据,分为注册申明、公共申明和私人申明。
比方:
{
"sub": "1234567890",
"name": "John Doe",
"admin": true
}
- 签名
利用签名算法对 Header 和 Payload 进行签名
比方:
HMACSHA256(base64UrlEncode(header) + "." +
base64UrlEncode(payload),
secret)
那么一个规范的 jwt 签名令牌会是这样的eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c
。
利用场景
- 用户受权拜访
比方用户登录后,服务端下发一个 jwt 令牌给客户端,每次用户申请数据都在申请头外面携带此令牌,服务端验证通过后能够获取到数据,这种形式开销很小,并不需要服务端进行存储,而且还能够跨域应用。
- 信息替换
在各方之间存储加密信息,验证签名内容是否篡改。
安全性
因为令牌能够被拆解,外面的 header 和 Payload 能够被解析看到,所以尽量不要在 Payload 外面存储一些私密的信息。
装置配置
上面就在 node 中应用 jwt 做一下操作。
在 npm 网站,有很多的 jwt 包,你能够抉择你认为适合的。
搜寻 jwt
NAME | DESCRIPTION | AUTHOR | DATE | VERSION | KEYWORDS
jwt | JSON Web Token for… | =mattrobenolt | 2012-05-05 | 0.2.0 |
express-jwt | JWT authentication… | =woloski… | 2021-08-11 | 6.1.0 | auth authn authentication authz authorization http jwt token oauth express
jsonwebtoken | JSON Web Token… | =dschenkelman… | 2019-03-18 | 8.5.1 | jwt
jwt-decode | Decode JWT tokens,… | =jeff.shuman… | 2020-11-16 | 3.1.2 | jwt browser
passport-jwt | Passport… | =themikenichol… | 2018-03-13 | 4.0.0 | Passport Strategy JSON Web Token JWT
koa-jwt | Koa middleware for… | =stiang… | 2021-09-24 | 4.0.3 | auth authn authentication authz authorization http jwt json middleware token oauth permissions koa
jsrsasign | opensource free… | =kjur | 2021-12-01 | 10.5.1 | crypto cryptography Cipher RSA ECDSA DSA RSAPSS PKCS#1 PKCS#5 PKCS#8 private key public key CSR PKCS#10 hash function HMac ASN.1 certexpress-jwt-permissions | Express middleware… | =angryunicorn… | 2021-08-18 | 1.3.6 | express middleware JWT permissions authorization token security
njwt | JWT Library for… | =robertjd | 2021-12-03 | 1.2.0 | jwt
fastify-jwt | JWT utils for… | =starptech… | 2021-12-03 | 4.1.0 | jwt json token jsonwebtoken fastify
did-jwt | Library for Signing… | =simonas-notcat… | 2021-12-03 | 5.12.1 |
hapi-auth-jwt2 | Hapi.js… | =nelsonic | 2020-09-08 | 10.2.0 | Hapi.js Authentication Auth JSON Web Tokens JWT
auth0-lock | Auth0 Lock | =jeff.shuman… | 2021-11-02 | 11.31.1 | auth0 auth openid authentication passwordless browser jwt
jwks-rsa | Library to retrieve… | =jeff.shuman… | 2021-10-15 | 2.0.5 | jwks rsa jwt
restify-jwt-community | JWT authentication… | =frbuceta | 2021-12-05 | 1.1.21 | auth authentication authorization http jwt token oauth restify
did-jwt-vc | Create and verify… | =simonas-notcat… | 2021-11-23 | 2.1.8 |
jwt-service | A simple wrapper… | =nfroidure | 2021-11-01 | 8.0.0 | jwt knifecycle
angular-jwt | Library to help you… | =jeff.shuman… | 2019-03-20 | 0.1.11 |
@thream/socketio-jwt | Authenticate… | =divlo | 2021-07-23 | 2.1.1 | socket socket.io jwt
appstore-connect-jwt-gene | [![NPM](https://nod… | =poad | 2021-10-15 | 1.0.1 | jwt appstore
rator-core |
装置 jwt
我集体感觉这个 jsonwebtoken 很不错,本文就应用这个包。
npm i jsonwebtoken
常见用法
- 签名
签名语法:jwt.sign(payload, secretOrPrivateKey, [options, callback])
。
例如:
// 个别签名
var jwt = require('jsonwebtoken');
var token = jwt.sign({foo: 'bar'}, 'secret');
// 加私钥签名
var privateKey = fs.readFileSync('private.key');
var token = jwt.sign({foo: 'bar'}, privateKey, {algorithm: 'RS256'});
// 设置过期工夫
jwt.sign({data: 'bar'}, 'secret', {expiresIn: 60 * 60}); // 1h
- 验证
验证语法:jwt.verify(token, secretOrPublicKey, [options, callback])
例如:
// 个别验证
var decoded = jwt.verify(token, 'secret');
console.log(decoded.foo) // bar
// 公钥验证
var cert = fs.readFileSync('public.pem');
jwt.verify(token, cert, function(err, decoded) {console.log(decoded.foo) // bar
});
- 解码
解码语法:jwt.decode(token [, options])
例如:
var decoded = jwt.decode(token, {complete: true});
console.log(decoded.header);
console.log(decoded.payload);
封装办法
依据装置配置外面的办法,能够依据本人的须要进行二次封装,更加适宜本人的办法。
- 引入依赖包和配置
const jwt = require("jsonwebtoken");
const config = {
secret: '2021123456**',
time: 60 * 60,
}
- 签名
function create (data, time) {
let token = jwt.sign(data, config.secret, {
algorithm: "HS256",
expiresIn: time || config.time,
})
return token;
}
- 验证
function verify (token) {return jwt.verify(token, config.secret, function (err, decoded) {if (err) {
return {
code: 1,
msg: 'invalid',
data: null,
}
} else {
return {
code: 2,
msg: 'valid',
data: decoded,
}
}
})
}
- 解码
function decoded (token, complete = true) {
return jwt.decode(token, {complete,});
}
下面是比较简单的办法,如果你还想应用公钥私钥,能够用下面装置配置外面介绍的那样。
实战练习
通过下面的封装办法,能够来实战演练一下,是否无效。
- 新建一个文件夹
test
, 新建一个文件index.js
用于寄存测试案例,jwt.js
用于存储调用办法。
mkdir test
cd test
npm init -y
npm i jsonwebtoken
- jwt 办法
// jwt.js
const jwt = require('jsonwebtoken');
const config = {
secret: '2021123456', // 密钥
time: 60*60, // 过期工夫
}
// 创立签名令牌
function create (data, time) {
let token = jwt.sign(data, config.secret, {
algorithm: 'HS256',
expiresIn: time || config.time,
});
return token;
}
// 验证令牌
function verify (token) {return jwt.verify(token, config.secret, function (err, decoded) {if (err) {
return {
code: 1,
msg: 'invalid',
data: null,
}
} else {
return {
code: 2,
msg: 'valid',
data: decoded,
}
}
})
}
// 解码令牌
function decoded (token, complete = true) {
return jwt.decode(token, {complete,});
}
const token = {
create,
verify,
decoded,
}
module.exports = token;
- 创立 token, 验证 token,解码 token
// index.js
const jwt = require('./jwt');
// 生成令牌
let token = jwt.create({'id': 1, 'name': 'mark'}, 60*60*2);
console.log(token);
/*
eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.
eyJpZCI6MSwibmFtZSI6Im1hcmsiLCJpYXQiOjE2MzkxMDYyNzMsImV4cCI6MTYzOTExMzQ3M30.
20O1r0NVMf-j-9RwNcgls9ja0n1rGqSKN51_cRcvpE8
*/
// 验证令牌
let verifyRes = jwt.verify(token);
console.log(verifyRes);
/*
{
code: 2,
msg: 'valid',
data: {id: 1, name: 'mark', iat: 1639106273, exp: 1639113473}
}
*/
// 解码令牌
let deRes = jwt.decoded(token, true);
console.log(deRes);
/*
{header: { alg: 'HS256', typ: 'JWT'},
payload: {id: 1, name: 'mark', iat: 1639106273, exp: 1639113473},
signature: '20O1r0NVMf-j-9RwNcgls9ja0n1rGqSKN51_cRcvpE8'
}
*/
运行一下命令 node index.js
测试是否正确。
好了,以上就是 jwt 在 node 中的一些利用和实际办法!