---
title: "Cognito MFAの設定手順：TOTP・SMS・メールの有効化と必須化の判断"
url: "https://www.issoh.co.jp/tech/details/18510/"
published: 2026-10-18
updated: 2026-10-18
categories: ["AWS"]
publisher: "株式会社一創"
---

# Cognito MFAの設定手順：TOTP・SMS・メールの有効化と必須化の判断

Amazon CognitoのMFA（多要素認証）は、ユーザープール単位でOFF・OPTIONAL・ONの3段階を選び、TOTP（認証アプリ）・SMS・メールの3方式から使う要素を有効にして設定します。この記事では、AWS CLIでの有効化、自作画面でTOTPを登録させるSDKコード、SMSのサンドボックスと支出上限、端末紛失やパスワードリセットとの衝突まで、2026年10月時点の公式ドキュメントの仕様に沿って手順を示します。最後に、業務システムと会員サービスでどの方式を必須にするかを条件に基づいて判断する構成です。

## まとめ：Cognito MFAはTOTPを軸に設定し、SMSは送信上限と費用を先に確かめる

結論から書くと、新規のユーザープールではTOTPを有効にし、業務システムならON（必須）、一般会員サービスならOPTIONAL（任意）から始めるのが扱いやすい構成です。TOTPは追加の送信基盤も費用もかからず、Liteプランから使えます。

SMSは手軽に見えて、サンドボックス解除、月1ドルの初期支出上限、日本語本文のパート課金、SMSポンピング対策と、本番前に片付ける項目が多い方式です。メールMFAはEssentials以上のプランと自前のAmazon SESが前提になります。どの方式を選んでも、パスワードリセットの送信先とMFAの送信先を同じにできない制約があるため、`email`と`phone_number`の扱いを設計段階で決めておく必要があります。

## Cognito MFAで選べる3方式と機能プラン・送信基盤の前提を確認する

ユーザープールの土台がまだ無い場合は、[Cognitoで認証基盤を実装する手順：ユーザープール構築からJWT検証まで](https://www.issoh.co.jp/tech/details/17445/)でプールとアプリクライアントを作ってから本稿の設定に進んでください。MFAの設定は作成後のプールにも追加できます。

### TOTP・SMS・メールの3方式を機能プランと送信基盤の違いで比較する

3方式の違いは、必要な[機能プラン](https://docs.aws.amazon.com/cognito/latest/developerguide/cognito-sign-in-feature-plans.html)と、コードを届ける仕組みの有無に集約されます。新規プールの既定プランはEssentialsです。

| 方式          | 必要なプラン       | 送信基盤                   | 追加費用       |
| ----------- | ------------ | ---------------------- | ---------- |
| TOTP（認証アプリ） | Lite以上       | 不要                     | なし         |
| SMS         | Lite以上       | End User Messaging SMS | 通数（パート数）課金 |
| メール         | Essentials以上 | 自前のAmazon SES          | SESの送信料金   |

TOTPはHMAC-SHA1で生成するコードだけを受け付け、SHA-256で生成したコードは`Code mismatch`エラーになると[TOTPの公式ガイド](https://docs.aws.amazon.com/cognito/latest/developerguide/user-pool-settings-mfa-totp.html)に明記されています。ハードウェアトークンには対応していません。物理キーを使いたいなら、MFAではなくパスキー（WebAuthn）の枠組みで検討することになります。

### MFAが掛かるのはローカルユーザーだけで外部IdP経由は対象外になる

Cognitoの[MFAの公式ガイド](https://docs.aws.amazon.com/cognito/latest/developerguide/user-pool-settings-mfa.html)によると、追加要素を求めるのはユーザープールにパスワードを持つローカルユーザーだけです。Entra IDやGoogleなどとフェデレーションしたユーザーの認証はIdP側に委ねられ、Cognitoは追加要素を出しません。社員はSAML連携、取引先はローカルユーザーという混在構成では、社員側のMFAはIdPの条件付きアクセスで掛ける必要があります。

もう1点、初回サインインの扱いにも注意が要ります。MFAを必須にしていても、新規ユーザーの初回はサインアップ時の確認コードを第2要素とみなしてトークンが発行され、追加要素の登録は2回目以降に求められます。

## MFAの強制レベルをOFF・OPTIONAL・ONから選んでユーザープールに反映する

強制レベルと有効にする方式は、コンソールの「サインイン」メニューにある多要素認証の編集画面か、[SetUserPoolMfaConfig](https://docs.aws.amazon.com/cognito-user-identity-pools/latest/APIReference/API%5FSetUserPoolMfaConfig.html) APIで設定します。

### 必須と任意で変わるサインイン時の挙動とマネージドログインの促し方

ONにすると、全ユーザーがMFAを登録しない限りサインインできません。マネージドログインは未登録のユーザーに方式の選択と登録を自動で促します。OPTIONALでは、マネージドログインは登録を促さず、コードを求める対象は優先方式を登録済みのユーザーだけです。任意にする場合、登録を勧める画面と登録手順はアプリ側で作ることになります。

Cognitoの脅威保護（Plusプラン）の適応認証で、リスクが高いサインインにだけMFAを求めたい場合、選ぶ設定はOPTIONALです。公式ガイドは、適応認証の応答を完全機能モードで使う場合はMFAを任意にするよう定めています。MFAコードの入力に5回失敗すると、通常のサインイン失敗と同じ指数的なロックアウトが始まります。

### AWS CLIで既存ユーザープールのTOTPを有効にして任意で始める手順

既存のプールにTOTPだけを有効にして任意で始める、AWS CLIのset-user-pool-mfa-configの使用例です。オプション名は[AWS CLIリファレンス](https://docs.aws.amazon.com/cli/latest/reference/cognito-idp/set-user-pool-mfa-config.html)で確認できます。

```
# TOTP（認証アプリ）を有効にし、MFAを任意（OPTIONAL）にする
aws cognito-idp set-user-pool-mfa-config \
  --user-pool-id ap-northeast-1_EXAMPLE \
  --software-token-mfa-configuration Enabled=true \
  --mfa-configuration OPTIONAL

# 反映結果を確かめる
aws cognito-idp get-user-pool-mfa-config \
  --user-pool-id ap-northeast-1_EXAMPLE
```

メールMFAを足すときは`--email-mfa-configuration`に件名と本文（コードの位置は`{####}`）を渡します。Liteプランのプールで指定すると`FeatureUnavailableInTierException`が返るため、先にコンソールの機能プラン画面でEssentialsへ切り替えてください。CLIの`update-user-pool`で`--user-pool-tier`を変える方法もありますが、このAPIは指定しなかった設定を既定値に戻すため、現行の設定をすべて渡す必要があります。

### 必須化するとパスキーやワンタイムコードのサインインと両立しない制約

MFAをONにしたプールでは、メールやSMSのワンタイムコードを第1要素にするパスワードレスサインインを併用できません。選択式サインインで提示される要素も、パスワード系だけに限定される仕様です。例外は、パスキーの`FactorConfiguration`を`MULTI_FACTOR_WITH_USER_VERIFICATION`にした場合で、ユーザー検証付きのパスキーがそれ単独でMFA要件を満たします。パスワードレスを将来入れる予定があるなら、ONにする前にこの組み合わせを決めておく方が手戻りは少なくなります。パスキーの有効化手順と、MFAを任意にしたプールで起きる衝突の条件は[Cognitoのパスキー実装手順：WebAuthnサインインの有効化とSDKでの登録・認証](https://www.issoh.co.jp/tech/details/18516/)で整理しています。

## TOTPを自作画面で登録させるAssociateSoftwareTokenからの実装手順

マネージドログインを使うなら、QRコードの表示から検証までCognitoが自動で行います。ここでは自作のログイン画面からAWS SDK for JavaScript v3で登録させる場合の処理の流れを示す構成です。TOTPの仕組みそのものは[OTPとは？HOTP／TOTPの生成アルゴリズムと実装](https://www.issoh.co.jp/tech/details/13455/)で解説しています。

### AssociateSoftwareTokenで秘密鍵を取得しQRコードを作る

[AssociateSoftwareToken](https://docs.aws.amazon.com/cognito-user-identity-pools/latest/APIReference/API%5FAssociateSoftwareToken.html)は、サインイン済みユーザーのアクセストークンか、`MFA_SETUP`チャレンジで受け取ったセッション文字列のどちらかで認可します。戻り値の`SecretCode`を認証アプリ用のotpauth形式のURIに埋め込み、QRコードにして表示します。

```
import {
  CognitoIdentityProviderClient,
  AssociateSoftwareTokenCommand,
} from "@aws-sdk/client-cognito-identity-provider";

const client = new CognitoIdentityProviderClient({ region: "ap-northeast-1" });

// サインイン済みならAccessToken、MFA_SETUPチャレンジ中ならSessionを渡す
export async function startTotpSetup({ accessToken, session, username }) {
  const res = await client.send(
    new AssociateSoftwareTokenCommand(
      accessToken ? { AccessToken: accessToken } : { Session: session }
    )
  );
  const issuer = encodeURIComponent("ExampleApp");
  const label = encodeURIComponent(`ExampleApp:${username}`);
  // 認証アプリが読み取るURI。これをQRコード化して画面に出す
  const uri = `otpauth://totp/${label}?secret=${res.SecretCode}&issuer=${issuer}`;
  return { uri, session: res.Session };
}
```

Sessionで呼んだ場合は、戻り値にも新しい`Session`が入ります。次の検証ではその値を使ってください。秘密鍵はログやエラー通知に出さない扱いにします。

### TOTPコードの照合と優先方式の設定で認証アプリの登録を確定させる

ユーザーが認証アプリに表示された6桁を入力したら、`VerifySoftwareToken`で照合します。Cognitoが時計のずれを考慮して受け付けるのは、前後30秒のコードです。成功後、[SetUserMFAPreference](https://docs.aws.amazon.com/cognito-user-identity-pools/latest/APIReference/API%5FSetUserMFAPreference.html)でTOTPを優先方式にします。

```
import {
  VerifySoftwareTokenCommand,
  SetUserMFAPreferenceCommand,
} from "@aws-sdk/client-cognito-identity-provider";

export async function finishTotpSetup({ accessToken, code }) {
  const v = await client.send(
    new VerifySoftwareTokenCommand({
      AccessToken: accessToken,
      UserCode: code,
      FriendlyDeviceName: "業務用スマートフォン",
    })
  );
  if (v.Status !== "SUCCESS") throw new Error("TOTPコードが一致しません");

  // TOTPを有効化し、優先するMFA方式に設定する
  await client.send(
    new SetUserMFAPreferenceCommand({
      AccessToken: accessToken,
      SoftwareTokenMfaSettings: { Enabled: true, PreferredMfa: true },
    })
  );
}
```

プール側でTOTPを有効にしていないと、関連付けの段階で`SoftwareTokenMFANotFoundException`が返ります。開発環境と本番環境でMFA設定がずれていると、この例外で初めて気付くことが多いため、IaCで両環境の設定を揃えておくと安全です。

### サインイン時のSOFTWARE\_TOKEN\_MFAとMFA\_SETUPチャレンジへの応答

登録済みユーザーが`InitiateAuth`でパスワード認証を通ると、応答に`SOFTWARE_TOKEN_MFA`チャレンジが返ります。`RespondToAuthChallenge`で`SOFTWARE_TOKEN_MFA_CODE`にコードを入れて応答すればトークンが発行されます。

必須のプールで未登録のユーザーに返るチャレンジは`MFA_SETUP`です。この場合はアクセストークンがまだ無いので、チャレンジのセッションを使って前述の関連付けと検証を行い、`VerifySoftwareToken`が返したセッションで`MFA_SETUP`に応答します。複数方式を有効にしていると、未選択のユーザーには`SELECT_MFA_TYPE`が返る点も、画面遷移の設計に含めておきます。

## SMS MFAで費用と到達性を詰まらせないための送信設定と上限の管理

CognitoのSMSは、2024年11月からAWS End User Messaging SMSを通じて送られます。[SMS設定の公式ガイド](https://docs.aws.amazon.com/cognito/latest/developerguide/user-pool-sms-settings.html)は、新規プールではSNSを経由しないdirect pathを使うよう案内しています。

### IAMロールの信頼ポリシーにExternalIdを入れてSMS送信を許可する

CognitoはIAMロールを引き受けてSMSを送ります。MFA用のSMSでは、信頼ポリシーの`sts:ExternalId`条件が必須で、プールのSMS設定の`ExternalId`と同じ値にする必要があります。コンソールの作成ウィザードで作ったロールは自動で揃いますが、既存ロールを流用すると揃いません。

```
{
  "Version": "2012-10-17",
  "Statement": [
    {
      "Effect": "Allow",
      "Principal": { "Service": "cognito-idp.amazonaws.com" },
      "Action": "sts:AssumeRole",
      "Condition": {
        "StringEquals": {
          "sts:ExternalId": "a1b2c3d4-5678-90ab-cdef-EXAMPLE22222",
          "aws:SourceAccount": "111122223333"
        },
        "ArnLike": {
          "aws:SourceArn": "arn:aws:cognito-idp:ap-northeast-1:111122223333:userpool/ap-northeast-1_EXAMPLE"
        }
      }
    }
  ]
}
```

direct pathなら権限ポリシーは`sms-voice:SendTextMessage`、SNS経由なら`sns:Publish`を付けます。値がずれていると`InvalidSmsRoleTrustRelationshipException`になります。いったんSMSを設定したプールでは、SMSをMFA方式から外せなくなる点も覚えておいてください。

### サンドボックスと月1ドルの支出上限が本番の認証を止める落とし穴

リージョンで初めてSMSを使うと、アカウントはSMSサンドボックスに入ります。サンドボックス中は検証済みの宛先にしか送れず、利用者の電話番号には届きません。さらに新規アカウントに設定されている支出上限は、月1.00ドルです。上限に達するとSMSが止まり、SMS MFAのユーザーはサインインできなくなります。本番公開の前に、サンドボックス解除と上限引き上げの申請をサポートセンターで済ませておく必要があります。

プールにSMS設定を保存した時点で、Cognitoは動作確認のテストSMSを内部の番号へ送り、これも課金対象になります。開発環境で設定を何度も作り直すと、気付かないうちに上限を消費していることがあります。

### 日本語のSMS本文に掛かるパート課金とSMSポンピング詐欺への備え

SMSの料金は宛先の国ごとの単価×通数で決まり、単価は[End User Messagingの料金ページ](https://aws.amazon.com/end-user-messaging/pricing/)で国を選んで確認します。注意したいのは通数の数え方です。[文字数制限の公式ガイド](https://docs.aws.amazon.com/sms-voice/latest/userguide/sms-limitations-character.html)によると、GSM文字集合の外にある文字を1字でも含むと1通は70字までになり、超えると67字ずつのパートに分割され、パート数で課金されます。日本語の本文は丁寧に書くほど2パートになりやすいので、「認証コード {####}（5分以内に入力）」のように短くまとめるのが費用面で効きます。

もう1つの費用リスクが、攻撃者が高単価の国の番号でサインアップを繰り返し、確認SMSを大量に送らせるSMSポンピングです。AWSは[セキュリティブログ](https://aws.amazon.com/blogs/security/reduce-risks-of-user-sign-up-fraud-and-sms-pumping-with-amazon-cognito-user-pools/)で、サインアップ時のCAPTCHA、WAFのBot Control、pre sign-up Lambdaでの電話番号種別の確認、End User Messaging SMSの保護設定（Protect）による国単位のブロックを対策として挙げています。ブロックされたメッセージは課金されないため、国内利用者だけのサービスなら日本以外への送信をProtectで止めておくのが手堅い対処です。

## 運用で詰まるMFAの復旧設計と端末記憶・WAF設定で確認する注意点

MFAは設定した日より、利用者が端末を失くした日に問題が表面化します。サポート窓口に問い合わせが来てから考えるのでは遅いので、復旧経路は有効化と同時に決めます。

### パスワードリセットとMFAで同じ宛先を使えない制約と必須属性の設定

CognitoはMFAとパスワードリセットのコードを同じメールアドレスや電話番号に送りません。メールMFAを優先方式にしたユーザーはメールでリセットコードを受け取れず、SMS MFAなら同様にSMSで受け取れません。リセット経路が無いユーザーがパスワードを忘れると、`InvalidParameterException`が返って自己解決できなくなります。

この状態を避けるには、`email`と`phone_number`を両方とも必須属性にするか、アカウント復旧設定を「メール優先、使えなければSMS」のように2経路にします。TOTPを主な方式にすれば、メールをリセット専用に回せるため、この衝突自体が起きにくくなります。リセット処理の実装は[Amazon Cognitoとは？料金・できること・使い方をCLIとコード例で解説](https://www.issoh.co.jp/tech/details/3108/)の注意点と合わせて確認してください。ForgotPasswordによる自己解決型と管理者リセットの実装手順全体は[Cognitoのパスワードリセット実装：ForgotPasswordと管理者リセット・ロックアウト設計](https://www.issoh.co.jp/tech/details/18514/)で解説しています。

### 端末紛失時のAdminDeleteSoftwareTokenと記憶済みデバイスでの省略

認証アプリを入れたスマートフォンを紛失した場合、管理者は本人確認のうえで`AdminDeleteSoftwareToken`を呼んでTOTPを削除します。必須のプールでほかに使える方式が無ければ、次回サインイン時に`MFA_SETUP`が返り、新しい端末で登録し直す流れになります。SMS MFAも有効な場合に切り替わる先は、SMS MFAです。

毎回のコード入力を減らしたい場合は、[記憶済みデバイス](https://docs.aws.amazon.com/cognito/latest/developerguide/amazon-cognito-user-pools-device-tracking.html)を使うと、信頼した端末ではMFAの代わりにデバイス認証（`DEVICE_SRP_AUTH`）で通せます。ただしマネージドログインはデバイス記憶を提供しないため、自作画面とSRPライブラリでの実装が前提です。記憶の期限を30日や90日で切る処理もアプリ側で持つことになります。

### WAFのCAPTCHAルールがTOTP登録を壊す問題とヘッダーでの除外

ユーザープールにAWS WAFのWeb ACLを関連付け、CAPTCHAアクションのルールを入れていると、マネージドログインでのTOTP登録が回復できないエラー「Request not allowed due to WAF captcha.」で失敗します。登録処理が裏で呼ぶ`AssociateSoftwareToken`と`VerifySoftwareToken`にCAPTCHAが掛かるためです。SMS MFAは影響を受けません。

対処は、CAPTCHAルールのスコープから`x-amzn-cognito-operation-name`ヘッダーの値が上記2つのリクエストを外すことです。Web ACLの関連付けとルール設計の手順は[API GatewayにAWS WAFを関連付ける手順：Web ACLのルール設計・WCU計算とCognito保護](https://www.issoh.co.jp/tech/details/18481/)で扱っています。

## Cognito MFAの方式選択と必須化を判断する条件と見送るべき場面

ここまでの仕様を踏まえ、どの方式をどの強さで掛けるかを言い切ります。MFAの一般的な方式比較は[多要素認証（MFA）とは？3要素と実装方式・耐フィッシングMFAをコード付きで解説](https://www.issoh.co.jp/tech/details/13314/)にまとめています。

### 業務システムはTOTP必須、会員サービスは任意と適応認証から始める

社員や取引先が使う業務システムで、利用者を管理側が把握できるなら、TOTPをONで始めます。費用ゼロ、送信基盤不要、プランを問わない、の3点が揃う方式はTOTPだけです。管理者は端末紛失時の削除手順だけを運用に組み込めば足ります。

一般消費者向けの会員サービスでは、ONにすると登録時の離脱が増えます。この場合はOPTIONALにして、決済や個人情報の変更など重要な操作の前に登録を勧める形がよいでしょう。予算がPlusプランに届くなら、適応認証でリスクの高いサインインにだけMFAを求める構成が、利便性と防御の釣り合いを取りやすくなります。

### SMS MFAを採用しない条件と外部IdPへ委ねるべきケース

SMSは、利用者の多くが認証アプリを入れられない層である場合に限って補助として使い、単独の方式にはしません。Cognitoの公式ガイド自身が、電話番号は持ち主が変わりうるためSMSはベストプラクティスではないと書いています。海外の番号を受け付けるサービスでSMSを有効にするなら、送信先国の制限をかけるまで公開しないことを勧めます。

社員の認証をEntra IDやGoogle Workspaceで既に管理している組織では、Cognito側でMFAを作り込まず、IdPのMFAに委ねる方が二重管理を避けられます。Cognitoはフェデレーションユーザーに追加要素を出さないため、そもそも設定が効きません。Entra IDとSAMLで連携する組み方は、[Cognito SAML連携の手順：Entra IDでSSOを組む設定と属性マッピング](https://www.issoh.co.jp/tech/details/18512/)にまとめています。方式の選定や既存IdPとの統合を含めて認証基盤を設計したい場合は、[認証基盤・ID管理システム開発](https://www.issoh.co.jp/service/system/identity/)でご相談いただけます。

## よくある質問

Cognito MFAの設定と運用で、実装前によく確認される点をまとめました。

### MFAをONにした後でOPTIONALやOFFに戻せますか？

SetUserPoolMfaConfig APIの`MfaConfiguration`は`OFF`・`ON`・`OPTIONAL`のいずれも指定でき、既存プールの設定変更として扱われます。ただし、いったんSMSを設定したプールではSMSをMFA方式から外せません。また、ONの間に登録したTOTPは、プール側でTOTPを無効にしても登録済みのユーザーは引き続き使えます。戻す前に、利用者に案内する内容と、登録済み要素の扱いを決めておいてください。

### Google AuthenticatorやMicrosoft Authenticatorは使えますか？

使えます。CognitoのTOTPは、HMAC-SHA1で6桁のコードを生成する一般的な認証アプリに対応しています。Google AuthenticatorやMicrosoft Authenticatorは既定でこの方式です。SHA-256で生成する設定のアプリでは`Code mismatch`になるため、独自の認証アプリを作る場合はアルゴリズムをSHA-1に合わせてください。ハードウェアトークンはMFAとしては使えません。

### メールMFAが選択肢に出てこないのはなぜですか？

原因は3つのどれかです。1つ目は機能プランがLiteのままであること。メールMFAはEssentials以上が必要です。2つ目は、メール送信をCognitoの既定の送信機能のまま使っていること。自前のAmazon SESから送る設定に切り替える必要があります。3つ目は、アカウント復旧を「メールのみ」にしていることです。MFAとリセットの宛先は同じにできないため、この組み合わせではメールMFAを有効にできません。

### MFAのコードはどのくらいの時間有効ですか？

SMSとメールで送るコードは、アプリクライアントに設定した「認証フローセッションの時間」の間だけ有効です。設定に使うのは、コンソールのアプリクライアント編集画面か、`UpdateUserPoolClient`です。TOTPは認証アプリ側で30秒ごとに切り替わり、Cognitoは前後30秒のずれまで受け付けます。入力に5回失敗するとロックアウトが始まる点も、エラーメッセージの文言に反映しておくと問い合わせが減ります。

### マネージドログインと自作画面のどちらでMFAを実装すべきですか？

MFAを必須にして標準的な画面で足りるなら、マネージドログインが登録から入力まで自動で処理するため、実装量が大きく減ります。任意のMFAで登録を勧める画面が必要な場合や、記憶済みデバイスでMFAを省略したい場合は、自作画面とSDKでの実装が必要です。マネージドログインの見た目の調整は[AWS Cognito Hosted UI（マネージドログイン）のカスタマイズ・日本語化と実装手順](https://www.issoh.co.jp/tech/details/3441/)を参照してください。

## 関連記事

- [Cognitoで認証基盤を実装する手順：ユーザープール構築からJWT検証まで](https://www.issoh.co.jp/tech/details/17445/)：MFAの前提になるユーザープールとトークン検証の全体像。
- [Amazon Cognito（コグニート）とは？料金・できること・使い方をCLIとコード例で解説](https://www.issoh.co.jp/tech/details/3108/)：機能プランごとの料金とCognitoの基本。
- [多要素認証（MFA）とは？3要素と実装方式・耐フィッシングMFAをコード付きで解説](https://www.issoh.co.jp/tech/details/13314/)：製品に依存しないMFA方式の比較と耐フィッシング性。
- [OTPとは？HOTP／TOTPの生成アルゴリズムと実装・SMS OTPの限界を実装視点で解説](https://www.issoh.co.jp/tech/details/13455/)：TOTPのアルゴリズムとSMS OTPの弱点。
- [二段階認証とは？二要素認証・多要素認証との違いと企業の導入判断を解説](https://www.issoh.co.jp/column/details/13268/)：二段階認証と多要素認証の違いと導入判断。

---

出典: [Cognito MFAの設定手順：TOTP・SMS・メールの有効化と必須化の判断](<https://www.issoh.co.jp/tech/details/18510/>)（株式会社一創）
