我一直试图使用AWS认知和API网关& Lambda (Python)实现无密码身份验证。
我遵循了以下文章:https://medium.com/digicred/password-less-authentication-in-cognito-cafa016d4db7 https://medium.com/@pjatocheseminario/passwordless-api-using-cognito-and-serverless-framework-7fa952191352
我已经配置了Cognito (接受CUSTOM_AUTH),添加了Lambdas,并创建了API端点:
/sign-up
/initiate-auth (aka initiate login)
/respond-to-auth-challenge (aka (verify login)当调用initiateAuth时,我收到以下响应:调用InitiateAuth操作时发生错误(NotAuthorizedException):不正确的用户名或密码。“
我使用的是CUSTOM_AUTH,它不需要密码,而且用户名肯定是正确的,因为它实际上启动了身份验证流程,并且我收到了一个代码,但是由于boto3没有响应会话,所以不能继续身份验证。
我就是这么称呼科尼图的:
res = cognito.initiate_auth(
ClientId=client_id,
AuthFlow="CUSTOM_AUTH",
AuthParameters={
"USERNAME": email,
"PASSWORD": random_password
}
)这可能是我错过的小东西,但我想不出是什么。
发布于 2020-12-01 05:35:35
我面临着同样的错误,我认为错误信息是误导性的。当您没有正确地响应在创建-8月-挑战λ,您将得到这个错误。所以确保所有的东西都在你的灯笼里。
发布于 2021-01-04 22:14:30
您的客户端代码看起来不错,我的代码中有ClientId参数,但是如果您的代码没有引发异常,那么它应该是可以的。除非您在创建应用程序客户端时检查了Generate client secret选项。如果是这样的话,那么您必须在SECRET_HASH中传入AuthParameters,如下所示:
import hmac
import hashlib
import base64
def get_secret_hash(email, client_id, client_secret):
"""
A keyed-hash message authentication code (HMAC) calculated using
the secret key of a user pool client and username plus the client
ID in the message.
"""
message = email + client_id
client_secret = str.encode(client_secret)
dig = hmac.new(client_secret, msg=message.encode('UTF-8'), digestmod=hashlib.sha256).digest()
return base64.b64encode(dig).decode()
client.admin_initiate_auth(
UserPoolId=COGNITO_USER_POOL_ID,
ClientId=CLIENT_ID,
AuthFlow='CUSTOM_AUTH',
AuthParameters={
'USERNAME': email,
'SECRET_HASH': get_secret_hash(email, CLIENT_ID, CLIENT_SECRET) # Omit if secret key option is disabled.
},
) 接下来,重复检查以下内容:
在App clients > * > Auth Flows Configuration下,是否为客户端启用了ALLOW_CUSTOM_AUTH选项?
在App integration > App client settings > * > Enabled Identity Providers下,您的用户池是否被选中?
如果您有正确的认知设置,而您的代码仍然不能工作,那么可能是lambda代码。您可能知道这一点,但是对于没有密码的自定义auth,您需要使用3个lambda触发器:Define Auth Challenge、Create Auth Challenge和Verify Auth Challenge。
自定义auth lambdas事件按以下顺序触发:
可以将
的其余部分
def lambda_handler(event, context):
if event['triggerSource'] == 'DefineAuthChallenge_Authentication':
event['response']['challengeName'] = 'CUSTOM_CHALLENGE'
event['response']['issueTokens'] = False
event['response']['failAuthentication'] = False
if event['request']['session']: # Needed for step 4.
# If all of the challenges are answered, issue tokens.
event['response']['issueTokens'] = all(
answered_challenge['challengeResult'] for answered_challenge in event['request']['session'])
return eventdef lambda_handler(event, context):
if event['triggerSource'] == 'CreateAuthChallenge_Authentication':
if event['request']['challengeName'] == 'CUSTOM_CHALLENGE':
event['response']['privateChallengeParameters'] = {}
event['response']['privateChallengeParameters']['answer'] = 'YOUR CHALLENGE ANSWER HERE'
event['response']['challengeMetadata'] = 'AUTHENTICATE_AS_CHALLENGE'
return event那么你的客户必须对挑战做出回应:
client.respond_to_auth_challenge(
ClientId=CLIENT_ID,
ChallengeName='CUSTOM_CHALLENGE',
Session=session,
ChallengeResponses={
'USERNAME': email,
'ANSWER': 'Extra Protection!',
'SECRET_HASH': get_secret_hash(email, CLIENT_ID, CLIENT_SECRET) # Omit if secret key option is disabled.
}
) def lambda_handler(event, context):
if event['triggerSource'] == 'VerifyAuthChallengeResponse_Authentication':
if event['request']['challengeAnswer'] == event['request']['privateChallengeParameters']['answer']:
event['response']['answerCorrect'] = True
return eventevent['response']['issueTokens']设置为True以返回令牌(步骤1中显示的代码),或发出另一个挑战以保持重复步骤1-3.最后,确保您的用户池也启用了大小写不敏感选项。而且,如果用户处于FORCE_CHANGE_PASSWORD状态,我也无法准确地回忆起FORCE_CHANGE_PASSWORD流是否工作。如果用户处于该状态,则尝试使用sdk设置永久密码,将状态设置为CONFIRMED。
https://stackoverflow.com/questions/63861311
复制相似问题