You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

寻求Node.js/Express中对接AWS Cognito认证的靠谱NPM包

我太懂这种在AWS文档迷宫里绕到崩溃的感觉了——之前做Node.js/Express项目集成Cognito认证时,踩过跟你一模一样的坑:要么示例跑不起来、逻辑残缺,要么被迫加polyfill、转前端方案,完全不符合后端路由处理的需求。折腾了好几天,终于整理出一套纯后端、开箱即用的方案,亲测能跑,分享给你:

Node.js/Express + AWS Cognito 后端认证完整实现

1. 依赖选择(无冗余,纯Node环境支持)

直接用AWS官方SDK v3(比v2更轻量化),搭配JWT验证工具:

npm install @aws-sdk/client-cognito-identity-provider jsonwebtoken jwks-rsa

2. 核心代码实现

(1)Token验证中间件(保护后端路由)

创建middleware/auth.js,用来验证前端传来的Cognito ID Token:

const jwt = require('jsonwebtoken');
const jwksClient = require('jwks-rsa');

// 替换成你的Cognito配置
const COGNITO_REGION = '你的区域(比如us-east-1)';
const USER_POOL_ID = '你的用户池ID(比如us-east-1_xxxxxxxxx)';
const CLIENT_ID = '你的应用客户端ID';

const jwksClientInstance = jwksClient({
  jwksUri: `https://cognito-idp.${COGNITO_REGION}.amazonaws.com/${USER_POOL_ID}/.well-known/jwks.json`
});

// 从Cognito获取公钥用于验证JWT
function getSigningKey(header, callback) {
  jwksClientInstance.getSigningKey(header.kid, (err, key) => {
    const signingKey = key.getPublicKey();
    callback(null, signingKey);
  });
}

// 验证Token的中间件
exports.verifyCognitoToken = (req, res, next) => {
  const authHeader = req.headers.authorization;
  if (!authHeader || !authHeader.startsWith('Bearer ')) {
    return res.status(401).json({ message: '请提供有效认证Token' });
  }

  const token = authHeader.split(' ')[1];
  jwt.verify(token, getSigningKey, {
    audience: CLIENT_ID,
    issuer: `https://cognito-idp.${COGNITO_REGION}.amazonaws.com/${USER_POOL_ID}`,
    algorithms: ['RS256']
  }, (err, decodedUser) => {
    if (err) {
      return res.status(403).json({ message: 'Token无效或已过期' });
    }
    req.user = decodedUser; // 把解析后的用户信息挂载到请求对象
    next();
  });
};

(2)登录接口(后端发起Cognito认证)

创建controllers/authController.js,实现用户名密码登录:

const { CognitoIdentityProviderClient, InitiateAuthCommand } = require('@aws-sdk/client-cognito-identity-provider');

// 替换成你的Cognito配置
const COGNITO_REGION = '你的区域';
const CLIENT_ID = '你的应用客户端ID';

const cognitoClient = new CognitoIdentityProviderClient({ region: COGNITO_REGION });

// 登录接口
exports.login = async (req, res) => {
  const { username, password } = req.body;
  if (!username || !password) {
    return res.status(400).json({ message: '请输入用户名和密码' });
  }

  const authParams = {
    AuthFlow: 'USER_PASSWORD_AUTH', // 确保用户池客户端已开启该认证流程
    ClientId: CLIENT_ID,
    AuthParameters: {
      USERNAME: username,
      PASSWORD: password
    }
  };

  try {
    const command = new InitiateAuthCommand(authParams);
    const authResult = await cognitoClient.send(command);
    res.json({
      accessToken: authResult.AuthenticationResult.AccessToken,
      idToken: authResult.AuthenticationResult.IdToken,
      refreshToken: authResult.AuthenticationResult.RefreshToken
    });
  } catch (error) {
    res.status(400).json({ message: error.message || '登录失败,请检查用户名密码' });
  }
};

(3)Express路由配置

在主文件app.js里整合:

const express = require('express');
const authController = require('./controllers/authController');
const { verifyCognitoToken } = require('./middleware/auth');

const app = express();
app.use(express.json());

// 公开登录接口
app.post('/api/auth/login', authController.login);

// 受保护路由:必须携带有效Token才能访问
app.get('/api/protected', verifyCognitoToken, (req, res) => {
  res.json({
    message: '成功访问受保护资源',
    userInfo: {
      username: req.user.username,
      email: req.user.email
    }
  });
});

app.listen(3000, () => {
  console.log('服务器运行在http://localhost:3000');
});

3. 关键避坑点

  • 确保你的Cognito用户池客户端开启了USER_PASSWORD_AUTH认证流程(在控制台「应用客户端设置」里勾选)
  • 不要用前端的Cognito SDK在后端跑,会有依赖兼容问题,直接用AWS SDK v3的Cognito客户端
  • Token验证时,audience必须匹配应用客户端ID,issuer必须匹配用户池的域名,否则会验证失败
  • 这套代码不需要polyfill或webpack,Node 16+版本直接就能运行

我当初也是翻了一堆残缺示例,自己踩坑整理出这套方案,亲测稳定能用,你可以直接拿去改配置试试。

内容的提问来源于stack exchange,提问作者gMoney

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.20 08:24:11