Cognito
The Auth
construct is a higher level CDK construct that makes it easy to configure a Cognito User Pool and Cognito Identity Pool. Also, allows setting up Auth0, Facebook, Google, Twitter, Apple, and Amazon as authentication providers.
Examples
Using the minimal config
import { Cognito } from "sst/constructs";
new Cognito(stack, "Auth");
Configuring login
You can configure how a user can sign in to our application for our User Pool. For example, you might want a user to be able to sign in with their email or username. Or with their phone number.
There are two ways of setting this up.
User signs up with username and signs in with username or alias
A user signs up with a username. In addition to the username, you can optionally allow users to sign in with one or more of the following aliases:
Note that, the username that Cognito refers to, is an internally used user id. So in practice, you'll ask a user to create a new username, this is called the preferred username by Cognito.
- A verified email address
- A verified phone number
- A preferred username
These aliases can be changed after the user signs up.
To use this option, set the
login
prop to:new Cognito(stack, "Auth", {
login: ["email", "phone", "username", "preferredUsername"],
});User signs up and signs in with email or phone number instead of username
A user signs up with an email address or phone number as their username. You can choose whether to allow sign-up with only email addresses, only phone numbers, or either one.
Note that, the email or phone number that gets set as a username needs to be unique. This is because when Cognito refers to the username, it really refers to an internally used user id.
In addition, if a user signs up with an email address, they can only change it to another email address and not a phone number. The same applies if they sign up with a phone number. It cannot be changed to an email.
To use this option, set the
login
prop to:new Cognito(stack, "Auth", {
login: ["email", "phone"],
});
Configuring triggers
The Cognito User Pool can invoke a Lambda function for specific triggers.
Adding triggers
new Cognito(stack, "Auth", {
triggers: {
preAuthentication: "src/preAuthentication.main",
postAuthentication: "src/postAuthentication.main",
},
});
Specifying function props for all the triggers
new Cognito(stack, "Auth", {
defaults: {
function: {
timeout: 20,
environment: { tableName: table.tableName },
permissions: [table],
},
},
triggers: {
preAuthentication: "src/preAuthentication.main",
postAuthentication: "src/postAuthentication.main",
},
});
Configuring an individual trigger
Configure each Lambda function separately.
new Cognito(stack, "Auth", {
triggers: {
preAuthentication: {
handler: "src/preAuthentication.main",
timeout: 10,
environment: { bucketName: bucket.bucketName },
permissions: [bucket],
},
postAuthentication: "src/postAuthentication.main",
},
});
Note that, you can set the defaults.function
while using the FunctionProps
per trigger. The function
will just override the defaults.function
. Except for the environment
, the layers
, and the permissions
properties, it will be merged.
new Cognito(stack, "Auth", {
defaults: {
function: {
timeout: 20,
environment: { tableName: table.tableName },
permissions: [table],
},
},
triggers: {
preAuthentication: {
handler: "src/preAuthentication.main",
timeout: 10,
environment: { bucketName: bucket.bucketName },
permissions: [bucket],
},
postAuthentication: "src/postAuthentication.main",
},
});
So in the above example, the preAuthentication
function doesn't use the timeout
that is set in the defaults.function
. It'll instead use the one that is defined in the function definition (10 seconds
). And the function will have both the tableName
and the bucketName
environment variables set; as well as permissions to both the table
and the bucket
.
Attaching permissions for all triggers
Allow all the triggers to access S3.
const auth = new Cognito(stack, "Auth", {
triggers: {
preAuthentication: "src/preAuthentication.main",
postAuthentication: "src/postAuthentication.main",
},
});
auth.attachPermissionsForTriggers(["s3"]);
Attaching permissions for a specific trigger
Allow one of the triggers to access S3.
const auth = new Cognito(stack, "Auth", {
triggers: {
preAuthentication: "src/preAuthentication.main",
postAuthentication: "src/postAuthentication.main",
},
});
auth.attachPermissionsForTrigger("preAuthentication", ["s3"]);
Here we are referring to the trigger using the trigger key, preAuthentication
.
Identity Pool federation
Enabling federation with Auth0
new Cognito(stack, "Auth", {
identityPoolFederation: {
auth0: {
domain: "https://myorg.us.auth0.com",
clientId: "UsGRQJJz5sDfPQDs6bhQ9Oc3hNISuVif",
},
},
});
Enabling federation with Twitter
new Cognito(stack, "Auth", {
identityPoolFederation: {
twitter: {
consumerKey: "gyMbPOiwefr6x63SjIW8NN2d9",
consumerSecret: "qxld1zic5c2eyahqK3gjGLGQaOTogGfAgGh17MYOIcOUR9l2Nz",
},
},
});
Enabling federation with multiple social logins
new Cognito(stack, "Auth", {
identityPoolFederation: {
facebook: { appId: "419718329085014" },
apple: { servicesId: "com.myapp.client" },
amazon: { appId: "amzn1.application.24ebe4ee4aef41e5acff038aee2ee65f" },
google: {
clientId:
"38017095028-abcdjaaaidbgt3kfhuoh3n5ts08vodt3.apps.googleusercontent.com",
},
},
});
Attaching permissions for authenticated federation identity
const auth = new Cognito(stack, "Auth");
auth.attachPermissionsForAuthUsers(stack, [api, "s3"]);
Attaching permissions for unauthenticated federation identity
const auth = new Cognito(stack, "Auth");
auth.attachPermissionsForUnauthUsers(stack, [api, "s3"]);
Advanced examples
Configuring attributes
import {
StringAttribute,
NumberAttribute,
BooleanAttribute,
DateTimeAttribute,
} from "aws-cdk-lib/aws-cognito";
new Cognito(stack, "Auth", {
cdk: {
userPool: {
standardAttributes: {
fullname: { required: true, mutable: false },
address: { required: false, mutable: true },
},
customAttributes: {
gameId: new StringAttribute({ minLen: 5, maxLen: 15, mutable: false }),
participants: new NumberAttribute({ min: 1, max: 3, mutable: true }),
isCompleted: new BooleanAttribute({ mutable: true }),
startedAt: new DateTimeAttribute(),
},
},
},
});
Importing an existing User Pool
Override the internally created CDK UserPool
and UserPoolClient
instance.
import { UserPool, UserPoolClient } from "aws-cdk-lib/aws-cognito";
new Cognito(stack, "Auth", {
cdk: {
userPool: UserPool.fromUserPoolId(stack, "UserPool", "pool-id"),
userPoolClient: UserPoolClient.fromUserPoolClientId(
stack,
"UserPoolClient",
"pool-client-id"
),
},
});
Adding additional clients
You can create additional clients for the Cognito user pool.
const cognito = new Cognito(stack, "Auth");
cognito.cdk.userPool.addClient("anotherClient", {
authFlows: {
userPassword: true,
userSrp: true,
},
});
Sharing Auth across stacks
You can create the Auth construct in one stack, and attach permissions in other stacks. To do this, return the Auth construct from your stack function.
import { Cognito, StackContext } from "sst/constructs";
export function AuthStack({ stack }: StackContext) {
const auth = new Cognito(stack, "Auth");
return {
auth,
};
}
Then import the auth construct into another stack with use
and attach the permissions.
import { Api, StackContext } from "sst/constructs";
import { AuthStack } from "./AuthStack";
export function ApiStack({ stack }: StackContext) {
const { auth } = use(AuthStack);
const api = new Api(stack, "Api", {
routes: {
"GET /notes": "src/list.main",
"POST /notes": "src/create.main",
},
});
auth.attachPermissionsForAuthUsers(stack, [api]);
}
Constructor
new Cognito(scope, id, props)
Parameters
- scope Construct
- id string
- props CognitoProps
CognitoProps
defaults?
Type :
defaults.function?
Type : FunctionProps
The default function props to be applied to all the triggers in the UserPool. The
environment
,
permissions
and
layers
properties will be merged with per route definitions if they are defined.
new Cognito(stack, "Auth", {
defaults: {
function: {
timeout: 20,
environment: { topicName: topic.topicName },
permissions: [topic],
}
},
});
identityPoolFederation?
Type : boolean | CognitoIdentityPoolFederationProps
Default : Identity Pool created with the User Pool as the authentication provider
Configure the Cognito Identity Pool and its authentication providers.
login?
Type : Array<"email" | "phone" | "username" | "preferredUsername">
Default : ["username"]
Configure the different ways a user can sign in to our application for our User Pool. For example, you might want a user to be able to sign in with their email or username. Or with their phone number.
caution
You cannot change the login property once the User Pool has been created.
triggers?
Type : CognitoUserPoolTriggers
Default : No triggers
Configure triggers for this User Pool
new Cognito(stack, "Auth", {
triggers: {
preAuthentication: "src/preAuthentication.main",
postAuthentication: "src/postAuthentication.main",
},
});
cdk?
Type :
cdk.id?
Type : string
Allows you to override default id for this construct.
cdk.userPool?
Type : IUserPool | UserPoolProps
This allows you to override the default settings this construct uses internally to create the User Pool.
cdk.userPoolClient?
Type : IUserPoolClient | UserPoolClientOptions
This allows you to override the default settings this construct uses internally to create the User Pool client.
Properties
An instance of Cognito
has the following properties.
cognitoIdentityPoolId
Type : undefined | string
The id of the internally created
IdentityPool
instance.
id
Type : string
userPoolArn
Type : string
The ARN of the internally created Cognito User Pool.
userPoolClientId
Type : string
The id of the internally created Cognito User Pool client.
userPoolId
Type : string
The id of the internally created Cognito User Pool.
cdk
Type :
cdk.authRole
Type : Role
cdk.cfnIdentityPool?
Type : CfnIdentityPool
cdk.cfnIdentityPoolRoleAttachment?
Type : CfnIdentityPoolRoleAttachment
cdk.unauthRole
Type : Role
cdk.userPool
Type : IUserPool
cdk.userPoolClient
Type : IUserPoolClient
Methods
An instance of Cognito
has the following methods.
attachPermissionsForAuthUsers
attachPermissionsForAuthUsers(scope, permissions)
Parameters
- scope Construct
- permissions Permissions
Attaches the given list of permissions to the authenticated users. This allows the authenticated users to access other AWS resources.
auth.attachPermissionsForAuthUsers(stack, ["s3"]);
attachPermissionsForAuthUsers(permissions)
Parameters
- permissions Permissions
You are now required to pass in a scope as the first argument.
// Change
auth.attachPermissionsForAuthUsers(["s3"]);
// to
auth.attachPermissionsForAuthUsers(auth, ["s3"]);
attachPermissionsForTrigger
attachPermissionsForTrigger(triggerKey, permissions)
Parameters
- triggerKey
- permissions Permissions
attachPermissionsForTriggers
attachPermissionsForTriggers(permissions)
Parameters
- permissions Permissions
attachPermissionsForUnauthUsers
attachPermissionsForUnauthUsers(scope, permissions)
Parameters
- scope Construct
- permissions Permissions
Attaches the given list of permissions to the authenticated users. This allows the authenticated users to access other AWS resources.
auth.attachPermissionsForUnauthUsers(stack, ["s3"]);
attachPermissionsForUnauthUsers(permissions)
Parameters
- permissions Permissions
You are now required to pass in a scope as the first argument.
// Change
auth.attachPermissionsForUnauthUsers(["s3"]);
// to
auth.attachPermissionsForUnauthUsers(auth, ["s3"]);
bindForTrigger
bindForTrigger(triggerKey, constructs)
Parameters
- triggerKey
- constructs Array<BindingResource>
bindForTriggers
bindForTriggers(constructs)
Parameters
- constructs Array<BindingResource>
getFunction
getFunction(triggerKey)
Parameters
- triggerKey
CognitoAppleProps
servicesId
Type : string
CognitoAuth0Props
clientId
Type : string
domain
Type : string
CognitoAmazonProps
appId
Type : string
CognitoGoogleProps
clientId
Type : string
CognitoTwitterProps
consumerKey
Type : string
consumerSecret
Type : string
CognitoFacebookProps
appId
Type : string
CognitoUserPoolTriggers
createAuthChallenge?
Type : string | Function | FunctionProps
customEmailSender?
Type : string | Function | FunctionProps
customMessage?
Type : string | Function | FunctionProps
customSmsSender?
Type : string | Function | FunctionProps
defineAuthChallenge?
Type : string | Function | FunctionProps
postAuthentication?
Type : string | Function | FunctionProps
postConfirmation?
Type : string | Function | FunctionProps
preAuthentication?
Type : string | Function | FunctionProps
preSignUp?
Type : string | Function | FunctionProps
preTokenGeneration?
Type : string | Function | FunctionProps
userMigration?
Type : string | Function | FunctionProps
verifyAuthChallengeResponse?
Type : string | Function | FunctionProps
CognitoCdkCfnIdentityPoolProps
allowUnauthenticatedIdentities?
Type : boolean
CognitoIdentityPoolFederationProps
amazon?
Type : CognitoAmazonProps
apple?
Type : CognitoAppleProps
auth0?
Type : CognitoAuth0Props
facebook?
Type : CognitoFacebookProps
google?
Type : CognitoGoogleProps
twitter?
Type : CognitoTwitterProps
cdk?
Type :