サービスの認証にCognitoユーザープールを使用する際、確認コードや、初回ログインパスワードなどをメールでお知らせする場合があると思います。
Cognitoのデフォルト設定だとこんなメールが届きます。
Your confirmation code is 927173
Your username is xxxx and temporary password is xxxxxx.
このメールタイトル、本文をカスタマイズする方法です。
カスタムメッセージが設定できるイベント
公式ドキュメントからの抜粋です。
以下がカスタムメッセージが設定できるイベントの一覧です。
AWS Lambda トリガーのリクエストおよびレスポンスパラメータ
triggerSource 値 | トリガーイベント |
---|---|
CustomMessage_AdminCreateUser | カスタムメッセージ – 新規ユーザーに一時パスワードを送信するため. |
CustomMessage_ResendCode | カスタムメッセージ – 既存ユーザーに確認コードを再送するため. |
CustomMessage_ForgotPassword | カスタムメッセージ - 忘れたパスワードのリクエスト用の確認コードを送信するため. |
CustomMessage_UpdateUserAttribute | カスタムメッセージ - ユーザーの E メールまたは電話番号が変更されると、このトリガーは確認コードをそのユーザーに自動的に送信します。他の属性には使用できません。 |
CustomMessage_VerifyUserAttribute | カスタムメッセージ – ユーザーが手動で新しい E メールや電話番号の認証コードをリクエストすると、このトリガーからユーザーに認証コードが送信されます。 |
CustomMessage_Authentication | カスタムメッセージ - 認証時に MFA コードを送信するため. |
今回はtriggerSource値がCustomMessage_AdminCreateUserの場合(Cognitoユーザープールのポリシーに**「管理者のみにユーザーの作成を許可する」**を設定していて、管理者がユーザーを作成した際にユーザーに送信されるメール)のカスタマイズを例にします。
手順
- Lambdaファンクションの作成
- Cognitoユーザープールに1.で作成したファンクションを登録
1. Lambdaファンクションの作成
Python3.6での例です。
ファンクションのIAMロールにはCloudwatchログ出力権限の付与だけでOKです。以下IAMポリシーの例です。
{
"Version": "2012-10-17",
"Statement": [
{
"Action": [
"logs:CreateLogGroup",
"logs:CreateLogStream",
"logs:PutLogEvents"
],
"Resource": [
"*"
],
"Effect": "Allow"
}
]
}
Lambdaファンクションで受け取るイベントをログ出力するとこのような感じ。
{
"version": "1",
"region": "ap-northeast-1",
"userPoolId": "ap-northeast-1_xxxxxxxxx",
"userName": "hogee",
"callerContext": {
"awsSdkVersion": "aws-sdk-js-2.176.0",
"clientId": "CLIENT_ID_NOT_APPLICABLE"
},
"triggerSource": "CustomMessage_AdminCreateUser",
"request": {
"userAttributes": {
"sub": "bf6e9c66-0a69-476e-bfd8-724d38e6555f",
"cognito:email_alias": "hoge@example.com",
"email_verified": "True",
"cognito:user_status": "FORCE_CHANGE_PASSWORD",
"name": "hoge",
"email": "hoge@example.com"
},
"codeParameter": "{####}",
"usernameParameter": "{username}"
},
"response": {
"smsMessage": "None",
"emailMessage": "None", # ここをカスタムした本文に変える
"emailSubject": "None" # ここをカスタムしたタイトルに変える
}
}
このイベントをそのままreturn event
とするとデフォルト設定が適用されたメールが送られます。カスタマイズするにはresponse
のフィールド内をカスタマイズしたい内容に書き換えてリターンします。
# -*- coding:utf-8 -*-
def handler(event, context):
if event['triggerSource'] == 'CustomMessage_AdminCreateUser':
customed_event = custom_message_admin_create_user(event)
return customed_event
def custom_message_admin_create_user(event):
email_message = '''
{username} 様
<br>
<br>
管理者から招待されました。
<br>
<br>
ログインメールアドレス:{mail}
<br>
初回ログインパスワード:{password}
'''.format(username='{username}',
mail=event['request']['userAttributes']['email'],
password='{####}')
event['response']['emailSubject'] = '仮パスワード発行のお知らせ'
event['response']['emailMessage'] = email_message
return event
{username}
にユーザーネーム、{####}
にパスワードが入ってメールが送信されることになります。
triggerSourceによって本文に含めなくてはいけないコードパラメータは異るため先ほどの公式ドキュメントで確認してください。
triggerSourceがCustomMessage_AdminCreateUser
の場合、メッセージ本文に{username}
と{####}
が入っていないとエラーになります。
もし追加で他のカスタムメッセージイベントにも対応したい場合、handler()
で
elif event['triggerSource'] == 'CustomMessage_ForgotPassword':
customed_event = custom_message_forgot_password(event)
とやると対応できます。
2. Cognitoユーザープールに1.で作成したファンクションを登録
Lambdaファンクション作成後はCognitoユーザープールのコンソールにいき、トリガー→カスタムメッセージから作成したLambdaファンクションを指定します。
serverless frameworkではこのようになります。
<略>
functions:
cognitoCustomMessage:
handler: functions/cognito_custom_message.handler
role: CognitoCustomMessageRole
events:
- cognitoUserPool:
pool: UserPool
trigger: CustomMessage
resources:
Resources:
CognitoUserPoolUserPool:
<以下略>
設定後、アプリケーションからユーザーを登録してみると、
カスタマイズされたメールが届きました。
以上です。