ユニバーサルログインに対するMFA選択をカスタイズする
Auth0は多要素認証(MFA)でユーザーアクセスを確保するための様々な要素をサポートしています。ポストログイン
を使用することで、MFAフローをカスタマイズし、指定要素または要素のシーケンスでユーザーにチャレンジできます。ユーザーやその所属する組織に関するコンテキスト情報を使用して、より個別化された体験を作成することも可能です。例えば、特定の組織への所属やユーザーに割り当てられた役割に基づいて、特定の要素でユーザーにチャレンジするようにフローをカスタマイズすることができます。
仕組み
アクションを使用して、MFAフローをカスタマイズできます。具体的には、ログインフローのポストログイン
トリガーを、以下の認証APIメソッドを使用して変更できます:
challengeWith
:ワンタイムパスワード(OTP)といった要素または、ユーザー認証に使用する必要のある要素を指定します。このメソッドはデフォルトのチャレンジをユーザーに提示し、オプションでファクターピッカーを提供して、異なる認証方法を選択できるようにします。challengeWithAny
:メールやOTPといった、ユーザーが認証時に選択できるファクターのグループを設定します。デフォルトで、この方法は、次の条件に従って、ユーザーに特定のチャレンジではなく、ファクターピッカーを提示します:複数のファクターが指定された場合、ファクターピッカーはユーザーに表示されます。
ユーザーが指定ファクターの一つ(または提供されたファクターが一つ)にのみに登録した場合、ファクターピッカーはスキップされます。
ユーザーがどの指定ファクターにも登録していない場合、コマンドは失敗します。
これらの方法を組み合わせて、必要に応じてMFAフローをカスタマイズできます。役割や以前使用したファクターなどのユーザーメタデータをこれらの方法に組み込むことで、よりカスタマイズされたフローを作成できます。
コマンドでMFAチャレンジを選択する際には、以下のファクターやenrolledFactors
の値を使用できます。enrolledFactors
は、ユーザーのアカウントに関連付けられたアクティブなファクターのリストを表します。
otp
email
push-notification
otpFallback
phone
preferredMethod: voice
preferredMethod: sms
preferredMethod: both
webauthn-platform
webauthn-roaming
event.authentication.methods
の配列には、方法の名前がmfa
タイプに設定されている場合に type
フィールドが含まれています。タイプは上記のenrolledFactors
のtype
フィールドで使用されるファクター値と一致する文字列です。MFAチャレンジが実行されると、methods
にはname:mfa
のオブジェクトが含まれ、 type
がそのチャレンジに使用されるファクターに設定されます。methods
はアクションが開始されたときにのみ更新されます。チャレンジの結果を見るには、methods
がフローの次のアクションにアクセスされていなければなりません。
詳しくは、以下のリソースをご確認ください:
シーケンス化されたフローとコンテキストに基づくフロー
challengeWith
やchallengeWithAny
コマンドを使用することで、コンテキスト情報を活用してユーザーに提示する最適なチャレンジやチャレンジのシリーズを決定できます。具体的には以下のものを活用できます:
シーケンス化されたフロー:ユーザーに対して、特定の順序に並べた、一連の異なる要素でチャレンジを行います。
コンテキストに基づくフロー:フロー内での以前のチャレンジに基づいて、次にどの要素でユーザーにチャレンジするかを決定します。
これらのフローを説明するために、次の例を考えてみましょう:
// ACTION 1
exports.onExecutePostLogin = async (event, api) => {
api.authentication.challengeWithAny([{ type: 'phone'}, { type: 'push-notification' }]);
}
// ============================================
// ACTION 2
// Decide based on what the user did in the previous action
exports.onExecutePostLogin = async (event, api) => {
if(event.authentication.methods.find(m => m.type === 'phone') && event.authorization?.roles.includes('admin')) {
api.authentication.challengeWith({ type: 'push-notification' });
}
}
Was this helpful?
このシナリオでは、アクション1でユーザーはまず、challengeWithAny
コマンドを通じてSMSでチャレンジされます。次に、アクション2ではユーザーはプッシュ通知でチャレンジされます。これは、ユーザーがAdminロールを持っており、SMSチャレンジも完了しているからです。
このフローでは、次の理由から、ユーザーをどの要素でチャレンジするかを決定することができます:
フローがアクション1実行後に停止するため。
ユーザーがアクション1で促されたMFAフローを完了するため。
アクション2の
event.authentication.methods.type
は、以前のMFAチャレンジからの情報を入力します。このフローは、アクション1からのコンテキストに基づく情報を使用して、 アクション2の実行に進みます。
この例は、アクション内でリダイレクトを使用するのと似た体験を提供しますが、 challengeWith
およびchallengeWithAny
コマンドを使用することで、以下のような独自の利点があります:
フローは各コマンド後に停止するため、以降のアクションで使用できるユーザー情報を蓄積できます。比較すると、リダイレクトはフローの最終コマンドとして一度だけ発生します。
MFAは、
challengeWith
やchallengeWithAny
コマンドを含む各アクションが実行された後にトリガーされます。リダイレクトの場合、MFAはパイプラインの最終アクションとして実行されます。
注意:アクションを実行するこの方法は、 challengeWith
またはchallengeWithAny
を含むものにしか適用されません。その他の目的を果たすアクションに影響はありません。
開始する前に
MFAフローをカスタマイズする前に、まず、テナントでMFAを有効にし、ユーザーに適切な要素に登録するように促します。
テナントの準備をする
はじめに、テナントでMFAを設定し、アクション設定を使用して、MFA要素のカスタマイズを有効にします。[Auth0 Dashboard]の [セキュリティ]>[多要素認証] から、1つ以上の要素を設定し、MFAポリシーを定義することができます。
フローのカスタマイズには、[追加設定]セクションのアクショントグルを使用して、[MFA要素のカスタマイズ]を有効にする必要があります。この設定が無効になっている場合、カスタマイズされたフローは、正常に作動しません。
![[Auth0 Dashboard]>[Security(セキュリティ)]>[MFA(多要素認証)]>[Additional Settings(追加設定)]](http://images.ctfassets.net/cdy7uua7fh8z/2hv0ELTkkka3t230SXfxw/3df4a2e61198f7c2cfbf6864df592b39/MFA_-_Actions_toggle_-_Japanese.png)
要素にユーザーを登録する
MFAが構成されると、有効にした1つ以上の要素にユーザーを登録するようにしてください。ユーザーは、ポストログイン
アクションコマンドにチャレンジされる前にAuthenticatorに登録する必要があります。
ユーザーがサインアップまたはテナントで作成された後、Management APIのauthentication-methodsエンドポイントを使用して登録を作成する必要があります。または、Auth0 Dashboardのプロファイルページから直接ユーザーの登録を管理することができます。
MFAフローをカスタマイズする
テナントの準備が整ったら、ポストログイン
アクションを作成して、MFAフローをカスタマイズできます。以下が、そのステップとユースケース例になります。
ポストログインアクションを作成する
[Auth0 Dashboard]で、[アクション]>[フロー]に移動し、 [ログイン]を選択します。
追加アクションの下の、[カスタム]を選択し、[アクションの作成]を選択します。
アクションの作成のポップアップでの表示:
アクションの名前を入力します。
トリガーとして、 ログイン/ポストログインを選択します。
ランタイムには、Node 18(推奨)を使用します。
正確性のために、ポップアップをご確認ください。その後、 [作成]を選択します。
作成後、コードエディターが
onPostExecute
コマンドを表示します。カスタムコードまたはコードサンプルをコマンドに追加します。コマンドの準備が整ったら、[導入]を選択します。
成功した導入通知で[フローの追加]を選択します。
注意:通知が閉じられている場合、コードエディターの上の[フローに戻る]を選択します。
新しいコマンドを「アクションの追加」パネルから、ログインフローにドラッグアンドドロップします。その後、[適用]を選択します。
アクションに追加の更新を行う場合、[アクション]>[ライブラり]>[カスタム]に移動し、コマンドを選択します。その後、必要な時にコードの更新と再導入ができます。
ポストログインアクションをテストする
コマンドが適切に機能するように、Auth0 Dashboardを通じてアクションをテストできます:
[認証]>[認証プロファイル]に移動します。
[試す]を選択し、新しいタブでログインプロンプトのサンプルを開きます。
資格情報を入力し、新しいMFAフローをテストします。
フローが成功したら、確認画面が表示されます。問題が生じたら,、Auth0 Dashboardの[アクション]>[ライブラリ]>[カスタム]に移動し、コードを更新することができます。
ユースケース例
以下の例では、MFAフローをカスタマイズする際の一般的なユースケースを示しています。
現在の登録を使用して、チャレンジ方法を決定する
次のサンプルは、ユーザーが以下のファクターに登録されている場合にMFAでチャレンジを行います。
ワンタイムパスワード(OTP)
Phone(電話番号)
exports.onExecutePostLogin = async (event, api) => {
api.authentication.challengeWithAny([{type: 'otp'}, {type: 'phone'}]);
}
Was this helpful?
ロールを使用して、チャレンジ方法を決定する
次のサンプルは、すべてのユーザーに対してOTPでチャレンジを行います。ユーザーがAdminロールを持ち、アプリケーションへのより高いレベルのアクセスが必要な場合、ステップアップ認証の一環として追加の要素でチャレンジされます。
exports.onExecutePostLogin = async (event, api) => {
api.authentication.challengeWith({type: 'otp'});
const isAdmin = event.authorization?.roles.includes('admin');
if(isAdmin) {
api.authentication.challengeWith({type: 'phone'});
}
}
Was this helpful?
メタデータを使用して、チャレンジ方法を決定する
この例では、MFA要素は組織レベルで有効になっています。このサンプルはメタデータの異なるカテゴリーを使用して、個々のユーザーに対する正しいチャレンジを決定します:
Organizationメタデータ:指定要素などのOrganizationレベルデータは、Organizationに対して有効になっています。
ユーザーメタデータ:ユーザープロファイルに関連づいた電話番号を持っているかどうかなどの、ユーザーレベルのデータ。
exports.onExecutePostLogin = async (event, api) => {
const orgFactors = event.organization?.metadata.factors.split(',') ?? [];
// Get the intersection of factors available for the user and factors enabled for the org
const availableFactors = orgFactors.filter(f => event.user?.enrolledFactors?.some(ef => ef.type === f));
// Prefer push if available
if(availableFactors.includes('push-notification')) {
api.authentication.challengeWith({ type: 'push-notification' });
return;
}
// If the user has a verified phone number and the organization
// allows for SMS and email, prefer SMS and allow email as a fallback
// if available
if(event.user.phone_number &&
event.user.phone_verified &&
availableFactors.includes('phone')) {
if(availableFactors.includes('email')) {
api.authentication.challengeWith({ type: 'phone' }, {
additionalFactors: [{
type: 'email'
}]
});
} else {
api.authentication.challengeWith({ type: 'phone' });
}
return;
}
// If push-notifications and/or phone couldn't be prioritized, fallback to email if
// enabled for the org, otherwise fail.
if(availableFactors.includes('email')) {
api.authentication.challengeWith({ type: "email" });
return;
}
api.access.deny("No MFA factors available for this org + user");
};
Was this helpful?
ユーザーが別の認証方法を選択できるようにします。
より柔軟な体験を提供するために、MFAチャレンジの一部としてユーザーに他の方法を試すリンクを提示することができます。このリンクにより、ユーザーはデフォルトチャレンジの代わりに別の認証方法を選択することができます。
そのためには、アクションコードにadditionalFactors
パラメーターを含めてください。このパラメーターをすべてのユーザーに対して指定の要素に設定するか、enrolledFactors
を使用してユーザーに好みの要素を選択させることができます。
指定要素
次のサンプルでは、デフォルトで、OTPでユーザーにチャレンジを行います。必要であれば、ユーザーは「他の方法を試す」リンクにアクセスし、代わりにメールで認証することができます。
exports.onExecutePostLogin = async (event, api) => {
api.authentication.challengeWith({ type: 'otp' },
{ additionalFactors: [{type: 'email'}] })
};
Was this helpful?
登録済み要素
次のサンプルでは、デフォルトで、OTPでユーザーにチャレンジを行います。必要であれば、ユーザーは「他の方法を試す」リンクにアクセスし、その他の登録済み要素の1つで認証することができます。
exports.onExecutePostLogin = async (event, api) => {
const enrolledFactors = event.user.enrolledFactors.map((f) => ({type: f.type}));
api.authentication.challengeWith({ type: 'otp' },
{ additionalFactors: enrolledFactors })
};
Was this helpful?
Adaptive MFAを使用して、ユーザーにチャレンジを行うタイミングを決定する
次のサンプルでは、Adaptive MFAを使用して、ユーザーにチャレンジを行うべきかどうかを決定します。
Adaptive MFAは、ログイン取引中のリスクを評価し、適切な場合に追加の検証をユーザーに求めることで、不正者からテナントを保護する柔軟なMFAポリシーです。
この場合、ユーザーが認識されていないデバイスからログインし、全体的な信頼スコアが低いまたは中程度の場合にMFAが求められます。
/**
* Handler that will be called during the execution of a PostLogin flow.
*
* @param {Event} event - Details about the user and the context in which they are logging in.
* @param {PostLoginAPI} api - Interface whose methods can be used to change the behavior of the login.
*/
exports.onExecutePostLogin = async (event, api) => {
if (event.authentication?.riskAssessment?.assessments.NewDevice) {
// Example condition: prompt MFA only based on the NewDevice
// confidence level, this will prompt for MFA when a user is logging in
// from an unknown device.
let shouldPromptMfa;
switch (event.authentication.riskAssessment.assessments.NewDevice.confidence) {
case 'low':
case 'medium':
shouldPromptMfa = true;
break;
case 'high':
shouldPromptMfa = false;
break;
case 'neutral':
// When this assessor has no useful information about the confidence,
// do not prompt MFA.
shouldPromptMfa = false;
break;
}
// It only makes sense to prompt for MFA when the user has at least one
// enrolled MFA factor.
const canPromptMfa = event.user.enrolledFactors?.length > 0;
if (shouldPromptMfa && canPromptMfa) {
const enrolledFactors = event.user.enrolledFactors.map((f) => ({type: f.type}));
api.authentication.challengeWithAny(enrolledFactors);
}
}
};
Was this helpful?
アクションを使用して、ユーザーにチャレンジを行う
ログインフローの ポストログイン
を修正することで、アクションを使用して、MFAをカスタマイズできます。この例では、認証と preferredMethod:'both'
のphone
方法を使用します。は、ユーザーのアカウントに関連付けられたアクティブなMFA要素を示します。詳しくは、アクションのトリガー: ポストログイン - イベントオブジェクトを参照してください。
api.authentication.challengeWith({
type: 'phone',
options: { preferredMethod: 'both'}
});
Was this helpful?
トラブルシューティング
カスタマイズされたMFAフローでエラーや予期しない結果が発生した場合は、以下の情報を使用して問題を特定し解決するのに役立ててください。
テナントログ
テナントログを通じて、カスタマイズされたMFAフローを監視できます。
テナントログは、Auth0 Dashboardの[モニタリング]>[ログ]から利用可能です。その他に、Management APIを使用して、ログを取得します。
予期しない動作が発生した場合は、次のイベントコードのテナントログを確認して、詳細情報を得てください。
シナリオ | イベントコード | エラーの説明 |
---|---|---|
ユーザーに多要素認証が求められますが、要求されたいずれの要素もチャレンジに使用できません。この場合、ユーザーはMFAを完了できません。 | mfar | このシナリオでは、次のエラーメッセージが表示されます: An MFA challenge is used in a PostLogin action but the requested factors are not properly set up.To perform MFA, enable the requested factors and ensure the user is enrolled with them.(PostLoginアクションはMFAチャレンジを使用していますが、要求された要素が適切にセットアップされていません。MFAを実行するには、要求された要素を有効にして、ユーザーがそれらで登録していることを確認してください。) |
ユーザーに多要素認証が求められますが、要求された要素の1つがチャレンジに使用できません。この場合、ユーザーは要求されている別の要素を使ってMFAを完了することができます。 | w | このシナリオでは、次のエラーメッセージが表示されます: An MFA challenge is used in a PostLogin action, but the requested factor {factor name} is not properly set up.Enable the requested factor and ensure the user is enrolled with it.(PostLoginアクションはMFAチャレンジを使用していますが、要求された要素の{factor name}が適切にセットアップされていません。要求された要素を有効にして、ユーザーがそれを使って登録していることを確認してください。) |
トラブルシューティングのチェックリスト
以下のチェックリストは、カスタマイズされたMFAフローに関する一般的な問題を特定し解決するための追加の提案を提供します。
「アクションでMFA要素をカスタマイズする」トグルを有効にする必要があります。
[Auth0 Dashboard]>[セキュリティ]>[多要素認証]に移動し、[追加設定]セクションのトグルが有効になっていることを確認してください。
アクションで参照されるファクターは、テナントで有効にする必要があります。
コードを確認する:[Auth0 Dashboard]>[アクション]>[ライブラリ]>[カスタム]に移動し、アクションコードを確認します。参照されたすべての要素が、ユースケースに適用可能であることを確認してください。
要素を確認する:[Auth0 Dashboard]>[セキュリティ]>[多要素認証]に移動し、アクションで参照されたすべての要素が有効になっていることを確認してください。
ユーザーはアクションで参照された要素に登録されている必要があります。
エラーが発生した場合は、対象ユーザーの詳細を確認し、適切なファクターに登録されていることを確認してください。[Auth0 Dashboard]>[ユーザー管理]>[ユーザー]に移動し、リストからユーザーの名前を選択します。
[詳細]タブの[多要素認証]セクションを確認し、ユーザーの登録を確認します。ユーザーが登録されていない場合、このセクションで利用可能な「登録の招待状を送る」リンクを使用できます。
または、[Raw JSON(生JSON)]タブでユーザーの登録状況を確認してください。この情報は、Management APIを使用することでも取得できます。ただし、APIには、メール認証リンクを介して設定されたメール要素のような自動登録された認証手段は表示されないことに注意が必要です。
ユーザーが適切な要素に登録されていない場合、Management APIのauthentication-methodsエンドポイントを使用して、登録を作成できます。Auth0 Dashboardのユーザーのプロファイルページを通じて、ユーザーの登録を直接管理することもできます。
アクションが導入され、パイプラインに保存されていることを確認してください。
[Auth0 Dashboard]>[アクション]>[ライブラリ]>[カスタム]に移動します。リストからアクションを見つけ、ステータスが「導入済み」になっていることを確認してください。異なるステータスが表示 されている場合、アクションにアクセスし、コードを確認したのち,右上の[導入]をクリックします。
[Auth0 Dashboard]>[アクション]>[ライブラリ]>[フロー]に移動し、 [ログイン]を選択します。アクションがフローに表示されていることを確認してください。表示されていない場合、[アクションの追加]パネルの[カスタム]タブにアクセスし、ログインフローにアクションをドラッグアンドドロップします。その後、[適用]を選択します。
ポストログイン
アクションが最新バージョンにアップグレードされていることを確認してください。[Auth0 Dashboard]>[アクション]>[ライブラリ]>[カスタム]に移動し、アクションを選択します。アクションが古い場合、アクションの更新を促す黄色のバナーが表示されます。バナーが表示された場合、[更新]を選択します。
Deploy CLIを使用する際には、
ポストログイン
アクションの最新バージョンを指定して導入することもできます。詳しくは、「Deploy CLIを構成する」をご覧ください。