AWS Cognito报错ResourceNotFoundException:用户池客户端不存在求助
问题描述
已完成AWS Cognito用户池(User Pool)及应用客户端(App Client)配置,使用以下代码实现登录功能,但运行时抛出异常:"ResourceNotFoundException: User pool client **** does not exist"。已多次核对从Cognito控制台“App Integration”选项卡下“App client list”复制的ClientId,仍无法定位问题。
实现代码
import { AdminInitiateAuthCommand, AdminInitiateAuthCommandInput, CognitoIdentityProviderClient, AdminInitiateAuthRequest, AuthFlowType, ListUserPoolClientsCommand, ListUserPoolClientsRequest, } from '@aws-sdk/client-cognito-identity-provider'; import { COGNITO_APP_CLIENT_ID, COGNITO_REGION, COGNITO_USER_POOL_ID, COGNITO_CLIENT_SECRET } from '@/constants'; import crypto from 'crypto'; //@ts-ignore export default async function handler(req, res) { if (req.method !== 'POST') return res.status(405).send(); const hash = crypto .createHmac('SHA256', COGNITO_CLIENT_SECRET) .update(req.body.username + COGNITO_APP_CLIENT_ID) .digest('base64'); const params: AdminInitiateAuthRequest = { AuthFlow: AuthFlowType.ADMIN_USER_PASSWORD_AUTH, ClientId: COGNITO_APP_CLIENT_ID, UserPoolId: COGNITO_USER_POOL_ID, AuthParameters: { USERNAME: req.body.username, PASSWORD: req.body.password, SECRET_HASH: hash, }, }; const cognitoClient = new CognitoIdentityProviderClient({ region: COGNITO_REGION, }); const adminInitiateAuthCommand = new AdminInitiateAuthCommand(params); try { const response = await cognitoClient.send(adminInitiateAuthCommand); console.log(response); return res.status(response['$metadata'].httpStatusCode).json({ ...response.AuthenticationResult, }); } catch (err) { console.log(err); return ( res //@ts-ignore .status(err['$metadata'].httpStatusCode) //@ts-ignore .json({ message: err.toString() }) ); } }
排查步骤
验证用户池与客户端的归属关系
确认COGNITO_USER_POOL_ID对应的用户池,是你复制的ClientId所属的用户池。可进入Cognito控制台目标用户池的客户端详情页,查看URL中的用户池ID是否与配置值一致(URL格式:https://console.aws.amazon.com/cognito/v2/idp/userpools/[用户池ID]/app/clients/[客户端ID]/settings)。检查区域配置一致性
确保COGNITO_REGION与用户池所在AWS区域完全匹配(比如用户池在us-east-1,就不能填us-east-2)。Cognito资源是区域级的,跨区域调用会直接找不到资源。可在用户池“General settings”页面查看区域信息。确认客户端状态
回到“App client list”,检查对应客户端是否处于“Enabled”状态,且未被删除(删除后列表中不会显示该客户端)。误删除或禁用客户端都会导致调用时出现资源不存在的错误。验证Secret Hash生成逻辑
虽然报错指向客户端不存在,但Secret Hash生成错误也可能触发类似异常。确认:COGNITO_CLIENT_SECRET是对应客户端的正确密钥(仅在客户端创建时显示,未保存需重新生成);- 代码中
update(req.body.username + COGNITO_APP_CLIENT_ID)的拼接顺序正确(规则为用户名 + 客户端ID)。
通过API确认客户端存在性
临时添加以下代码到handler中,调用Cognito API列出目标用户池下的所有客户端,确认你的COGNITO_APP_CLIENT_ID在返回列表中:const listParams: ListUserPoolClientsRequest = { UserPoolId: COGNITO_USER_POOL_ID, MaxResults: 10 }; const listCommand = new ListUserPoolClientsCommand(listParams); const clientList = await cognitoClient.send(listCommand); console.log("Existing clients:", clientList.UserPoolClients?.map(c => c.ClientId));检查IAM权限(适用AWS服务运行场景)
如果代码运行在Lambda等AWS服务上,确保执行角色拥有cognito-idp:AdminInitiateAuth和cognito-idp:ListUserPoolClients权限。权限不足通常报AccessDeniedException,但也可作为排查项确认。
内容的提问来源于stack exchange,提问作者Alex Kleshchevnikov

