如何使用 aws-amplify 验证 node/express 中的 accessToken?
How to verify accessToken in node/express using aws-amplify?
我在我的前端 React 应用程序上使用 AWS amplify 进行用户身份验证。
我的 React 应用直接与 amplify 通信,无需任何后端(节点服务器)交互。
我有一个用 node/express 编写的 REST API。我想使用放大来确保 API。
目前,我正计划将访问令牌从我的 React 应用程序传递到我的节点服务器。但是我找不到一种方法可以在后端使用 amplify 验证此令牌。
aws-amplify 包是否提供任何功能,我可以在其中传递访问令牌来验证它?
类似于Auth.verifyToken(<access_token>)
很遗憾,官方aws-amplify SDK 中没有这样的方法。
在做了很多研究之后,我不得不为此编写自己的中间件。这并不像看起来那么困难,但唯一困难的部分是从庞大的 AWS 文档中收集正确的信息。
我已经编写了这个中间件来实现相同的目的,希望这对您有所帮助
import axios from 'axios'
import awsconfig from '../../aws-exports';
const COGNITO_URL = `https://cognito-idp.${awsconfig.aws_project_region}.amazonaws.com/`;
const authentication = async (req, res, next) => {
try {
const accessToken = req.headers.authorization.split(" ")[1];
const { data } = await axios.post(
COGNITO_URL,
{
AccessToken: accessToken
},
{
headers: {
"Content-Type": "application/x-amz-json-1.1",
"X-Amz-Target": "AWSCognitoIdentityProviderService.GetUser"
}
}
)
req.user = data;
next();
} catch (error) {
return res.status(401).json({
message: 'Auth failed'
});
}
};
export default authentication;
此中间件获取授权 header 并使用 AWS Cognito REST 验证传入的 accessToken API。
为了在您的 front-end 上获取 accessToken,您可以这样做:
const { accessToken: { jwtToken } } = await Auth.currentSession();
这个 jwtToken
是您的 accessToken,您可以将它发送到您的 Authorization
header,然后使用我编写的中间件在后端验证它。
AWS 实际上对此有很好的记录。我写了一个关于我编写的中间件的要点,用于在我的 express.js 服务器中验证 AWS Cognito 令牌。
本质上,当您在 Amazon 中创建用户池时,AWS 会创建一个 JSON Web 密钥 (JWK)。 JWT 包含一个 public 密钥,您可以使用它来验证 JWT 的签名。
处于高水平 Javascript:
import jwt from "jsonwebtoken";
const authToken = getJwtFromHeader(request);
// please remember to verify the "iss" claim and "exp" claim!
validateAuthToken(authToken);
// convert a jwk to a PEM for use by OpenSSL or crypto
const jwk = getJwkFromAWS();
const pem = jwkToPem(jwk);
// verify the signature of the token using the public key from AWS
await jwt.verify(authToken, pem, {algorithms: ['RS256']}, (err, decoded) =>{
console.log('decoded', decoded);
// TODO -- verify claims from decoded token
});
我的 GIST 完整 express.js 实现:
https://gist.github.com/fourgates/92dc769468497863168417c3524e24dd
AWS 资源:
https://github.com/awslabs/aws-support-tools/tree/master/Cognito/decode-verify-jwt
https://docs.aws.amazon.com/cognito/latest/developerguide/amazon-cognito-user-pools-using-tokens-verifying-a-jwt.html
遗憾的是,aws-amplify SDK 不提供该功能。出于这个原因,我创建了一个 npm package 来处理它。
工作原理
包公开:
authenticate
:一个 Express 中间件,可以添加到任何需要针对 Cognito 用户池进行身份验证的路由。
authenticationError
:一个 Express 错误处理程序,负责处理由 authenticate
中间件生成的任何身份验证错误。
JWTValidator
:一个 class,可以实例化以验证 Cognito 发布的 JWT。如果您需要自定义身份验证和错误处理逻辑,这将很有用。 authenticate
中间件在内部使用它。
包含的功能
- JWT 签名验证。
- JWT 声明验证。
- 确认令牌未过期。
- 验证观众 (aud) 声明是否与有效的声明之一相匹配
配置中提供的受众。
- 验证颁发者 (iss) 声明对配置的用户有效
池.
- 验证 token_use 声明是否与有效令牌使用之一匹配
配置中提供。
- 按照 JWT 签名密钥中的描述支持 JWK 轮换
旋转线程.
- 能够为本地测试设置自定义 PEMS,而无需
创建用户池。
基本用法
// app.js
'use strict';
const express = require('express');
const { authenticate, authenticationError } = require('aws-cognito-express');
const app = express();
// Add the authentication middleware.
app.use(authenticate({
region: 'us-east-2',
userPoolId: 'us-east-2_6IfDT7ZUq',
tokenUse: ['id', 'access'],
audience: ['55plsi2cl0o267lfusmgaf67pf']
}));
// Protected route.
app.get('/articles', (req, res, next) => {
console.log('JWT payload: ', req.cognito);
});
// Add the authentication error handler.
app.use(authenticationError());
module.exports = app;
有关更高级的用例,请查看文档 here。
我在我的前端 React 应用程序上使用 AWS amplify 进行用户身份验证。 我的 React 应用直接与 amplify 通信,无需任何后端(节点服务器)交互。
我有一个用 node/express 编写的 REST API。我想使用放大来确保 API。
目前,我正计划将访问令牌从我的 React 应用程序传递到我的节点服务器。但是我找不到一种方法可以在后端使用 amplify 验证此令牌。
aws-amplify 包是否提供任何功能,我可以在其中传递访问令牌来验证它?
类似于Auth.verifyToken(<access_token>)
很遗憾,官方aws-amplify SDK 中没有这样的方法。 在做了很多研究之后,我不得不为此编写自己的中间件。这并不像看起来那么困难,但唯一困难的部分是从庞大的 AWS 文档中收集正确的信息。
我已经编写了这个中间件来实现相同的目的,希望这对您有所帮助
import axios from 'axios'
import awsconfig from '../../aws-exports';
const COGNITO_URL = `https://cognito-idp.${awsconfig.aws_project_region}.amazonaws.com/`;
const authentication = async (req, res, next) => {
try {
const accessToken = req.headers.authorization.split(" ")[1];
const { data } = await axios.post(
COGNITO_URL,
{
AccessToken: accessToken
},
{
headers: {
"Content-Type": "application/x-amz-json-1.1",
"X-Amz-Target": "AWSCognitoIdentityProviderService.GetUser"
}
}
)
req.user = data;
next();
} catch (error) {
return res.status(401).json({
message: 'Auth failed'
});
}
};
export default authentication;
此中间件获取授权 header 并使用 AWS Cognito REST 验证传入的 accessToken API。
为了在您的 front-end 上获取 accessToken,您可以这样做:
const { accessToken: { jwtToken } } = await Auth.currentSession();
这个 jwtToken
是您的 accessToken,您可以将它发送到您的 Authorization
header,然后使用我编写的中间件在后端验证它。
AWS 实际上对此有很好的记录。我写了一个关于我编写的中间件的要点,用于在我的 express.js 服务器中验证 AWS Cognito 令牌。
本质上,当您在 Amazon 中创建用户池时,AWS 会创建一个 JSON Web 密钥 (JWK)。 JWT 包含一个 public 密钥,您可以使用它来验证 JWT 的签名。
处于高水平 Javascript:
import jwt from "jsonwebtoken";
const authToken = getJwtFromHeader(request);
// please remember to verify the "iss" claim and "exp" claim!
validateAuthToken(authToken);
// convert a jwk to a PEM for use by OpenSSL or crypto
const jwk = getJwkFromAWS();
const pem = jwkToPem(jwk);
// verify the signature of the token using the public key from AWS
await jwt.verify(authToken, pem, {algorithms: ['RS256']}, (err, decoded) =>{
console.log('decoded', decoded);
// TODO -- verify claims from decoded token
});
我的 GIST 完整 express.js 实现: https://gist.github.com/fourgates/92dc769468497863168417c3524e24dd
AWS 资源:
https://github.com/awslabs/aws-support-tools/tree/master/Cognito/decode-verify-jwt https://docs.aws.amazon.com/cognito/latest/developerguide/amazon-cognito-user-pools-using-tokens-verifying-a-jwt.html
遗憾的是,aws-amplify SDK 不提供该功能。出于这个原因,我创建了一个 npm package 来处理它。
工作原理
包公开:
authenticate
:一个 Express 中间件,可以添加到任何需要针对 Cognito 用户池进行身份验证的路由。authenticationError
:一个 Express 错误处理程序,负责处理由authenticate
中间件生成的任何身份验证错误。JWTValidator
:一个 class,可以实例化以验证 Cognito 发布的 JWT。如果您需要自定义身份验证和错误处理逻辑,这将很有用。authenticate
中间件在内部使用它。
包含的功能
- JWT 签名验证。
- JWT 声明验证。
- 确认令牌未过期。
- 验证观众 (aud) 声明是否与有效的声明之一相匹配 配置中提供的受众。
- 验证颁发者 (iss) 声明对配置的用户有效 池.
- 验证 token_use 声明是否与有效令牌使用之一匹配 配置中提供。
- 按照 JWT 签名密钥中的描述支持 JWK 轮换 旋转线程.
- 能够为本地测试设置自定义 PEMS,而无需 创建用户池。
基本用法
// app.js
'use strict';
const express = require('express');
const { authenticate, authenticationError } = require('aws-cognito-express');
const app = express();
// Add the authentication middleware.
app.use(authenticate({
region: 'us-east-2',
userPoolId: 'us-east-2_6IfDT7ZUq',
tokenUse: ['id', 'access'],
audience: ['55plsi2cl0o267lfusmgaf67pf']
}));
// Protected route.
app.get('/articles', (req, res, next) => {
console.log('JWT payload: ', req.cognito);
});
// Add the authentication error handler.
app.use(authenticationError());
module.exports = app;
有关更高级的用例,请查看文档 here。