Node.js 上 Token 鉴权常用的是 passport,它可以自定义校验策略,但如果你是用 express 框架,又只是解析 JWT 这种简单需求,可以尝试下 express-jwt 这个中间件。

关于 JWT

JWT 全称 JSON Web Token,是代替传统 session 认证的解决方案。其原理是服务端生成一个包含用户唯一标识的 JSON 对象,颁发给客户端。客户端请求需要权限的接口时,只要把这个 JSON 再原样发回给服务端,服务器通过解析就可识别用户。

它通常是这个样子:

eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJzdWIiOiIxMjM0NTY3ODkwIiwibmFtZSI6IkpvaG4gRG9lIiwiaWF0IjoxNTE2MjM5MDIyfQ.SflKxwRJSMeKKF2QT4fwpMeJf36POk6yJV_adQssw5c

这个 JSON 对象通过 . 分成三段,包含了请求头(加密算法)、负载信息(如 userId、过期时间),还有通过服务端密钥生成的签名来保证不被篡改。

这种机制使服务端不再需要存储 Token,因此是非常轻量的用户认证方案。并且对于微服务这种需要不同服务间共用 Token 的跨域认证,JWT 是目前的首选。

关于 express-jwt

express-jwt 是 Node.js 的一个开源库,由 ID 认证服务提供商 auth0 开发,是专用于 express 框架下解析 JWT 的中间件。

它使用非常简单,而且会自动把 JWT 的 payload 部分赋值于 req.user,方便逻辑部分调用。

开始使用

安装

npm install express-jwt

加入中间件

const expressJWT = require('express-jwt')app.use(expressJWT({secret: 'secret12345'  // 签名的密钥 或 PublicKey
}).unless({path: ['/login', '/signup']  // 指定路径不经过 Token 解析
}))

生成 Token

生成 Token 的方式依然使用 jsonwebtoken,比如将下列代码加入到登录接口的返回部分:

const jwt = require('jsonwebtoken')app.post('/login', function (req, res) {// 注意默认情况 Token 必须以 Bearer+空格 开头const token = 'Bearer ' + jwt.sign({_id: user._id,admin: user.role === 'admin'},'secret12345',{expiresIn: 3600 * 24 * 3})res.json({status: 'ok',data: { token: token }})
})

获取解析内容

当收到带 Token 的请求,如果解析成功,就可以在路由回调里通过 req.user 来访问:

app.get('/protected', function (req, res) {if (!req.user.admin)return res.sendStatus(401)res.sendStatus(200)
})

req.user 实际就是 JWT 的 payload 部分:

{_id: '5dbbc7daaf7dfe003680ba39',admin: true,iat: 1572587484,exp: 1573192284
}

解析失败

如果解析失败,会抛出 UnauthorizedError,可以通过后置中间件来捕获:

app.use(function (err, req, res, next) {if (err.name === 'UnauthorizedError') {   res.status(401).send('invalid token')}
})

修改结果字段

默认解析结果会赋值在 req.user,也可以通过 requestProperty 来修改:

app.use(jwt({secret: 'secret12345',requestProperty: 'auth'
}))

允许无 Token 请求

当接口允许不带 Token 和带 Token 两种状态的访问时(比如文章详情登录后判断点赞),可以通过 credentialsRequired: false 来对无 Token 请求不进行解析和抛出异常。

app.use(jwt({secret: 'secret12345',credentialsRequired: false
}))

自定义解析

通过 getToken 也可以自定义一些解析逻辑,比如使用其他 Header 字段,自定义抛出异常等:

app.use(jwt({secret: 'secret12345',credentialsRequired: false,getToken: function fromHeaderOrQuerystring (req) {if (req.headers.authorization && req.headers.authorization.split(' ')[0] === 'Bearer') {return req.headers.authorization.split(' ')[1]} else if (req.query && req.query.token) {return req.query.token}return null}
}))

吊销 Token

在 JWT 机制中,由于 Token 通常不进行存储,如果想吊销某一条 Token,一般都是通过被动的方式。

常用的方式是建立某个字段的黑名单(比如 TokenId),对所有 Token 进行过滤,express-jwt 专门提供了回调来处理这种情况:

const jwt = require('express-jwt')
const blacklist = require('./blacklist')let isRevokedCallback = function(req, payload, done){let issuer = payload.isslet tokenId = payload.jtiblacklist.getRevokedToken(issuer, tokenId, function(err, token){if (err) { return done(err) }return done(null, !!token)  // 第二个参数为 true 则不通过})
}app.use(jwt({secret: 'secret12345',isRevoked: isRevokedCallback
}))

更多用法可以查看 官方文档


Node.js 使用 express-jwt 解析 JWT相关推荐

  1. 如何使用Node.js,Express和MongoDB设置GraphQL服务器

    by Leonardo Maldonado 莱昂纳多·马尔多纳多(Leonardo Maldonado) 如何使用Node.js,Express和MongoDB设置GraphQL服务器 (How to ...

  2. 用node.js和express.js和jade搭建轻型cms系统

    http://cnodejs.org/topic/4f16442ccae1f4aa270010bf 前言: 我们主要做的是iphone/ipad程序,但关注node.js很久,因为我们多少总是要做网站 ...

  3. 使用 Node.js、Express、AngularJS 和 MongoDB 构建一个Web程序

    为什么80%的码农都做不了架构师?>>>    使用 Node.js.Express.AngularJS 和 MongoDB 构建一个实时问卷调查应用程序 2014 年 3 月 20 ...

  4. Installing Node.js and Express on Ubuntu

    Installing Node.js and Express on Ubuntu 1. 在nodejs官网上下载Linux Binaries(已经包含了npm): 2. 安装Node.js 下载后解压 ...

  5. node.js安装express(零起点搭建本地测试服务器)- 教程篇

    (含图文教程.代码对比,等)node.js安装express(零起点搭建本地测试服务器)- 教程篇 原教程 · 参考地址 执行step3之后,结果截图 · 如下图2 : 之后,执行step4,截图如下 ...

  6. Node.js框架Express与MySQL数据库的学习笔记

    一.数据库的基本概念 1.什么是数据库 数据库(database)是用来组织.存储和管理数据的仓库. 2.常见的数据库及分类 常见的数据库有:MySQL 数据库.Oracle 数据库(收费).SQL ...

  7. node.js(八 --- express)

    EXPRESS 重要的模块 body-parser: node.js中间件,用于处理JSON,Text和URL编码的数据: cookie-parser:这就是一个解析Cookie的工具.通过req.c ...

  8. 【前端——Node.js】:Express、数据库与身份认证

    一.Express 1.express路由 (1)路由 路由就是映射关系.在Express中,路由是指客户端的请求与服务器处理函数之间的映射关系 (2)路由匹配的过程 (3)模块化路由 为了方便对路由 ...

  9. Node.js之 express写后端接口

    参考 https://blog.csdn.net/studysinklc/article/details/103166451 一 1 首先,新建一个Node.js项目,在项目目录下安装express ...

  10. 使用Node.js的Express框架搭建和开发项目

    在搭建项目前,需要安装node.js,npm node.js安装方法 ,npm安装方法 接下来我们来创建express项目 1.选择项目安装目录 假如选择D:\projects\node\blog作为 ...

最新文章

  1. Lagrange equation
  2. Handle类的用法
  3. windows密钥连接linux,windows使用密钥登录linux
  4. 一步步编写操作系统 46 用c语言编写内核3
  5. TensorFlow 基本操作
  6. springframework: Transactional注解和@EnableTransactionManagement
  7. CUDA内存分配、释放、传输,固定内存
  8. CentOS7安装Mono和MonoDevelop
  9. Netty工作笔记0033---Netty概述
  10. 火星人敏捷接开发手册 2011-09-12
  11. 程序员如何从初中级历练为高级开发者?
  12. java编译是用javac吗_用java自带工具javac和java编译运行java程序
  13. 基于umi写一个用户管理CRUD
  14. 00截断上传绕过_Getshell | 文件上传绕过整理
  15. 12种无线接入方式简析
  16. 收集UE4 优化Tips
  17. bios error 装系统acpi_重装系统遇到bios acpi错误。
  18. 热烈庆祝《Java多线程》上线啦!
  19. (极详细版)python计算分位点方法
  20. 随笔——Docker学习笔记

热门文章

  1. 单点登录,不要老盯着cas-server了,你还可以选择keycloak
  2. 在Windows/Mac电脑上将CAF转换为AIFF的教程
  3. java excel导入jsp_jsp页面导入excel文件的步骤及配置
  4. 【vscode】image view插件 用于预览图片
  5. php获取cookie过期时间,如何获取cookie的过期时间
  6. 使用MySQL数据库
  7. Pandas数据分析实战 — 复购率指标计算
  8. 史上最全SQL学习指南(教程+实例+练习题)
  9. #P07751. 龟兔赛跑
  10. 北斗赋能,无人划线小车让智慧施工升级