Cognito password-less login
To implement a password-less solution with Cognito until recently it was necessary to take care of sending the code and verifying it via Cognito triggers and using custom authentication.
Recently and I would say finally, Cognito has added support natively via some simple User Pool configuration.
UserPool
The default user pool configuration is “AllowedFirstAuthFactors”, this allows you to specify a new EMAIL_OTP
value (or SMS_OTP
) to activate the password-less flow via OTP.
UserPool:
Type: AWS::Cognito::UserPool
Properties:
UserPoolName: !Sub "${Project}-${Environment}"
UserPoolTier: ESSENTIALS
DeletionProtection: ACTIVE
AutoVerifiedAttributes:
- "email"
UsernameAttributes:
- "email"
Schema:
- Name: email
AttributeDataType: String
Mutable: true
Required: true
MfaConfiguration: "OFF"
Policies:
SignInPolicy:
AllowedFirstAuthFactors:
- PASSWORD
- EMAIL_OTP
AccountRecoverySetting:
RecoveryMechanisms:
- Name: "verified_email"
Priority: 1
EmailAuthenticationMessage: "Your code is {####}"
EmailAuthenticationSubject: "My Auth Server"
VerificationMessageTemplate:
EmailMessage: "Your verification code is {####}"
EmailSubject: "Your verification code"
DefaultEmailOption: "CONFIRM_WITH_CODE"
Frontend implementation
Install Amplify auth
module, you don’t need the entire library
npm install @aws-amplify/auth
Import the auth
module and configure it
import { Auth } from '@aws-amplify/auth'
Auth.configure({
region: "eu-south-1",
userPoolId: "eu-south-1_xxxxxxxxxxx",
userPoolWebClientId: "xxxxxxxxxxxxxxxxxxxxxxxxx",
})
Send the login request requesting an OTP:
import { signIn} from 'aws-amplify/auth'
await signIn({
username: email.value,
options: {
authFlowType: 'USER_AUTH',
preferredChallenge: 'EMAIL_OTP'
}
})
Sending back to Cognito the OTP to finalize the login:
import { confirmSignIn } from 'aws-amplify/auth'
await confirmSignIn({
challengeResponse: code.value
})
And it’s done! The user is now logged in.