Fastify 是一个基于 Node.js 的快速和低开销的 Web 框架,它被设计为构建高效的 RESTful API。在实际开发中,我们通常需要为我们的应用程序添加访问控制和身份验证功能,以确保只有经过授权的用户才能访问我们的 API。在本文中,我们将介绍如何为 Fastify 实现访问控制和身份验证。
访问控制
访问控制是一种安全机制,用于限制对系统或资源的访问。在 Fastify 中,我们可以使用插件来实现访问控制。
fastify-auth 插件
fastify-auth 是一个 Fastify 插件,它提供了一种简单的方法来实现基于 JSON Web Token(JWT)的身份验证和访问控制。
首先,我们需要安装 fastify-auth 插件:
npm install fastify-auth
然后,我们可以在 Fastify 应用程序中注册 fastify-auth 插件:
const fastify = require('fastify')() fastify.register(require('fastify-auth'))
现在,我们可以使用 fastify.auth() 方法来定义我们的路由需要进行身份验证:
fastify.get('/private', { preValidation: fastify.auth([fastify.verifyJWT]) }, async (request, reply) => { return { secret: 'This is a secret message' } })
在上面的代码中,我们使用 fastify.auth() 方法定义了一个需要进行身份验证的路由。该路由的 preValidation 选项指定了需要使用的验证函数。
fastify-jwt 插件
fastify-jwt 是一个 Fastify 插件,它提供了一种简单的方法来生成和验证 JSON Web Token(JWT)。
首先,我们需要安装 fastify-jwt 插件:
npm install fastify-jwt
然后,我们可以在 Fastify 应用程序中注册 fastify-jwt 插件:
const fastify = require('fastify')() fastify.register(require('fastify-jwt'), { secret: 'supersecret' })
在上面的代码中,我们使用 fastify-jwt 插件设置了一个密钥。该密钥将用于生成和验证 JWT。
现在,我们可以使用 fastify.jwt.sign() 方法生成 JWT:
const token = fastify.jwt.sign({ username: 'alice' })
在上面的代码中,我们使用 fastify.jwt.sign() 方法生成了一个包含用户名“alice”的 JWT。
然后,我们可以在需要进行身份验证的路由中使用 fastify.verifyJWT() 方法来验证 JWT:
fastify.get('/private', { preValidation: fastify.auth([fastify.verifyJWT]) }, async (request, reply) => { const decoded = await request.jwtVerify() return { secret: 'This is a secret message', username: decoded.username } })
在上面的代码中,我们使用 fastify.verifyJWT() 方法验证了 JWT,并从 JWT 中提取了用户名。
身份验证
身份验证是一种安全机制,用于确认用户的身份。在 Fastify 中,我们可以使用插件来实现身份验证。
fastify-auth 插件
fastify-auth 插件不仅可以用于访问控制,还可以用于身份验证。
首先,我们需要安装 fastify-auth 插件(如果还没有安装):
npm install fastify-auth
然后,我们可以在 Fastify 应用程序中注册 fastify-auth 插件:
const fastify = require('fastify')() fastify.register(require('fastify-auth'))
现在,我们可以使用 fastify.decorate() 方法来添加一个验证函数:
-- -------------------- ---- ------- -------------------------------- ----- -------- --------- ------ - ----- ------ - ----------------------------- -- --------- ----- --- -------------- ------------- -------- ----- -------- ------ - -------------- -- -- ------- --- --------- ----- --- -------------- ------------- -------- --- - ----- ------- - ----- ------------------------- ------------ - ------- - ----- ----- - ----- --- -------------- ------- - --展开代码
在上面的代码中,我们使用 fastify.decorate() 方法添加了一个名为 authenticate 的验证函数。该函数从请求头中提取 JWT,并验证 JWT 的有效性。
现在,我们可以在需要进行身份验证的路由中使用 fastify.authenticate() 方法来调用验证函数:
fastify.get('/private', { preValidation: fastify.authenticate }, async (request, reply) => { return { secret: 'This is a secret message', username: request.user.username } })
在上面的代码中,我们使用 fastify.authenticate() 方法调用了 authenticate 验证函数,并从 JWT 中提取了用户名。
示例代码
下面是一个完整的示例代码,演示了如何为 Fastify 实现访问控制和身份验证:
-- -------------------- ---- ------- ----- ------- - -------------------- ----------------------------------------- ---------------------------------------- - ------- ------------- -- -------------------------------- ----- -------- --------- ------ - ----- ------ - ----------------------------- -- --------- ----- --- -------------- ------------- -------- ----- -------- ------ - -------------- -- -- ------- --- --------- ----- --- -------------- ------------- -------- --- - ----- ------- - ----- ------------------------- ------------ - ------- - ----- ----- - ----- --- -------------- ------- - -- ---------------------- ----- --------- ------ -- - ------ - -------- ----- -- - ------ -------- - -- ----------------------- - -------------- -------------------- -- ----- --------- ------ -- - ------ - ------- ----- -- - ------ --------- --------- --------------------- - -- -------------------- ----- -- - -- ----- - ------------------ --------------- - ------------------- --------- -- ---- ------ --展开代码
在上面的代码中,我们定义了两个路由:/public 和 /private。/public 路由是公共路由,不需要进行身份验证。/private 路由是需要进行身份验证的私有路由。
我们首先使用 fastify-auth 和 fastify-jwt 插件注册了 Fastify 应用程序。然后,我们使用 fastify.decorate() 方法添加了一个名为 authenticate 的验证函数。最后,我们定义了两个路由,并在 /private 路由中使用了 authenticate 验证函数。
现在,您可以运行上面的代码,并使用 curl 命令测试 API:
# 发送 GET 请求到 /public 路由 curl http://localhost:3000/public # 发送 GET 请求到 /private 路由(未经身份验证) curl http://localhost:3000/private # 发送 GET 请求到 /private 路由(经过身份验证) curl -H "Authorization: Bearer eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJ1c2VybmFtZSI6ImFsaWNlIiwiaWF0IjoxNTE2MjM5MDIyfQ.MvN0oWd7bN9-9y1d3sZz8W1KpJZwGJZ0oYvz8gRrT-4" http://localhost:3000/private
如果您发送未经身份验证的 GET 请求到 /private 路由,您将得到以下响应:
{ "statusCode": 401, "error": "Unauthorized", "message": "Missing authorization header" }
如果您发送经过身份验证的 GET 请求到 /private 路由,您将得到以下响应:
{ "secret": "This is a secret message", "username": "alice" }
这证明了我们已经成功地为 Fastify 实现了访问控制和身份验证。
来源:JavaScript中文网 ,转载请注明来源 https://www.javascriptcn.com/post/67da2ce1a941bf71341ea207