メールアドレスの更新やユーザー パスワードのリセットなど、一部のユーザー管理操作では、ユーザーにメールが送信されます。これらのメールには、そのユーザー管理操作を完了またはキャンセルするためのリンクが含まれます。ユーザー管理のメールはデフォルトで、プロジェクトの Firebase Hosting ドメインの URL でホストされているウェブページである、アクション ハンドラにリンクします。
デフォルトのアクション ハンドラの代わりに、カスタム処理を行うアクション ハンドラを自分のウェブサイトに統合するために、メール アクション ハンドラを自作してホストすることもできます。
次のユーザー管理操作では、ユーザーがメールのアクション ハンドラを使用してアクションを完了する必要があります。
- パスワードのリセット
- メールアドレスの変更の取り消し - ユーザーが自分のアカウントのメインのメールアドレスを変更すると、その変更を元に戻せるよう、元のアドレスにメールが送信されます。
- メールアドレスの確認
Firebase プロジェクトのメール アクション ハンドラをカスタマイズするには、リクエストの妥当性を検証し、リクエストを完了するウェブページを Firebase JavaScript SDK で作成しホストする必要があります。その後、Firebase プロジェクトのメール テンプレートをカスタマイズして、カスタム アクション ハンドラにリンクする必要があります。
メール アクション ハンドラのページを作成する
Firebase はユーザー管理のメールを生成する際、アクション ハンドラの URL にいくつかのクエリ パラメータを追加します。次に例を示します。
https://example.com/usermgmt?mode=resetPassword&oobCode=ABC123&apiKey=AIzaSy...&lang=fr
これらのパラメータは、完了しようとしているユーザー管理タスクを指定しています。メール アクション ハンドラのページでは、次のクエリ パラメータを処理する必要があります。
パラメータ モード 完了するユーザー管理操作。次のいずれかの値です。
resetPasswordrecoverEmailverifyEmail
oobCode リクエストを識別し、検証するためのワンタイム コード apiKey 利便性のために提供される Firebase プロジェクトの API キー continueUrl URL を使用して状態をアプリに戻す方法を提供するオプションの URL。これは、パスワード リセットとメール確認モードに関係します。パスワード リセットのメールまたは確認メールを送信するときは、 ActionCodeSettingsオブジェクトを続行 URL で指定して、このパラメータを使用できるようにする必要があります。これにより、ユーザーはメール アクション後に中断したところから続行できます。lang ユーザーのロケールを表す省略可能な BCP47 言語タグです(例:
fr)。この値を使用して、ローカライズされたメールのアクション ハンドラのページをユーザーに提供できます。Firebase コンソールを使用してローカライズを設定できます。また、メール アクションをトリガーする前に対応するクライアント API を呼び出すことによって、動的にローカライズを設定することもできます。たとえば、JavaScript では次のように使用します。
firebase.auth().languageCode = 'fr';一貫したユーザー エクスペリエンスのために、メールのアクション ハンドラのローカライズが、メール テンプレートのものと一致することを確認してください。
次の例は、ブラウザベースのハンドラ内でクエリ パラメータを処理する方法を示しています(また、同様のロジックを使用して Node.js アプリケーションとしてハンドラを実装できます)。
Web
import { initializeApp } from "firebase/app"; import { getAuth } from "firebase/auth"; document.addEventListener('DOMContentLoaded', () => { // TODO: Implement getParameterByName() // Get the action to complete. const mode = getParameterByName('mode'); // Get the one-time code from the query parameter. const actionCode = getParameterByName('oobCode'); // (Optional) Get the continue URL from the query parameter if available. const continueUrl = getParameterByName('continueUrl'); // (Optional) Get the language code if available. const lang = getParameterByName('lang') || 'en'; // Configure the Firebase SDK. // This is the minimum configuration required for the API to be used. const config = { 'apiKey': "YOUR_API_KEY" // Copy this key from the web initialization // snippet found in the Firebase console. }; const app = initializeApp(config); const auth = getAuth(app); // Handle the user management action. switch (mode) { case 'resetPassword': // Display reset password handler and UI. handleResetPassword(auth, actionCode, continueUrl, lang); break; case 'recoverEmail': // Display email recovery handler and UI. handleRecoverEmail(auth, actionCode, lang); break; case 'verifyEmail': // Display email verification handler and UI. handleVerifyEmail(auth, actionCode, continueUrl, lang); break; default: // Error: invalid mode. } }, false);
Web
document.addEventListener('DOMContentLoaded', () => { // TODO: Implement getParameterByName() // Get the action to complete. var mode = getParameterByName('mode'); // Get the one-time code from the query parameter. var actionCode = getParameterByName('oobCode'); // (Optional) Get the continue URL from the query parameter if available. var continueUrl = getParameterByName('continueUrl'); // (Optional) Get the language code if available. var lang = getParameterByName('lang') || 'en'; // Configure the Firebase SDK. // This is the minimum configuration required for the API to be used. var config = { 'apiKey': "YOU_API_KEY" // Copy this key from the web initialization // snippet found in the Firebase console. }; var app = firebase.initializeApp(config); var auth = app.auth(); // Handle the user management action. switch (mode) { case 'resetPassword': // Display reset password handler and UI. handleResetPassword(auth, actionCode, continueUrl, lang); break; case 'recoverEmail': // Display email recovery handler and UI. handleRecoverEmail(auth, actionCode, lang); break; case 'verifyEmail': // Display email verification handler and UI. handleVerifyEmail(auth, actionCode, continueUrl, lang); break; default: // Error: invalid mode. } }, false);
最初に
verifyPasswordResetCodeでアクション コードを確認することによって、パスワードのリセット リクエストを処理し、その後ユーザーから新しいパスワードを取得して、それをconfirmPasswordResetに渡します。次に例を示します。Web
import { verifyPasswordResetCode, confirmPasswordReset } from "firebase/auth"; function handleResetPassword(auth, actionCode, continueUrl, lang) { // Localize the UI to the selected language as determined by the lang // parameter. // Verify the password reset code is valid. verifyPasswordResetCode(auth, actionCode).then((email) => { const accountEmail = email; // TODO: Show the reset screen with the user's email and ask the user for // the new password. const newPassword = "..."; // Save the new password. confirmPasswordReset(auth, actionCode, newPassword).then((resp) => { // Password reset has been confirmed and new password updated. // TODO: Display a link back to the app, or sign-in the user directly // if the page belongs to the same domain as the app: // auth.signInWithEmailAndPassword(accountEmail, newPassword); // TODO: If a continue URL is available, display a button which on // click redirects the user back to the app via continueUrl with // additional state determined from that URL's parameters. }).catch((error) => { // Error occurred during confirmation. The code might have expired or the // password is too weak. }); }).catch((error) => { // Invalid or expired action code. Ask user to try to reset the password // again. }); }
Web
function handleResetPassword(auth, actionCode, continueUrl, lang) { // Localize the UI to the selected language as determined by the lang // parameter. // Verify the password reset code is valid. auth.verifyPasswordResetCode(actionCode).then((email) => { var accountEmail = email; // TODO: Show the reset screen with the user's email and ask the user for // the new password. var newPassword = "..."; // Save the new password. auth.confirmPasswordReset(actionCode, newPassword).then((resp) => { // Password reset has been confirmed and new password updated. // TODO: Display a link back to the app, or sign-in the user directly // if the page belongs to the same domain as the app: // auth.signInWithEmailAndPassword(accountEmail, newPassword); // TODO: If a continue URL is available, display a button which on // click redirects the user back to the app via continueUrl with // additional state determined from that URL's parameters. }).catch((error) => { // Error occurred during confirmation. The code might have expired or the // password is too weak. }); }).catch((error) => { // Invalid or expired action code. Ask user to try to reset the password // again. }); }
最初に
checkActionCodeでアクション コードを検証することによって、メールアドレスの変更取消しを処理し、その後、applyActionCodeでユーザーのメールアドレスを復元します。次に例を示します。Web
import { checkActionCode, applyActionCode, sendPasswordResetEmail } from "firebase/auth"; function handleRecoverEmail(auth, actionCode, lang) { // Localize the UI to the selected language as determined by the lang // parameter. let restoredEmail = null; // Confirm the action code is valid. checkActionCode(auth, actionCode).then((info) => { // Get the restored email address. restoredEmail = info['data']['email']; // Revert to the old email. return applyActionCode(auth, actionCode); }).then(() => { // Account email reverted to restoredEmail // TODO: Display a confirmation message to the user. // You might also want to give the user the option to reset their password // in case the account was compromised: sendPasswordResetEmail(auth, restoredEmail).then(() => { // Password reset confirmation sent. Ask user to check their email. }).catch((error) => { // Error encountered while sending password reset code. }); }).catch((error) => { // Invalid code. }); }
Web
function handleRecoverEmail(auth, actionCode, lang) { // Localize the UI to the selected language as determined by the lang // parameter. var restoredEmail = null; // Confirm the action code is valid. auth.checkActionCode(actionCode).then((info) => { // Get the restored email address. restoredEmail = info['data']['email']; // Revert to the old email. return auth.applyActionCode(actionCode); }).then(() => { // Account email reverted to restoredEmail // TODO: Display a confirmation message to the user. // You might also want to give the user the option to reset their password // in case the account was compromised: auth.sendPasswordResetEmail(restoredEmail).then(() => { // Password reset confirmation sent. Ask user to check their email. }).catch((error) => { // Error encountered while sending password reset code. }); }).catch((error) => { // Invalid code. }); }
applyActionCodeの呼び出しで、メールアドレスの確認を処理します。次に例を示します。Web
function handleVerifyEmail(auth, actionCode, continueUrl, lang) { // Localize the UI to the selected language as determined by the lang // parameter. // Try to apply the email verification code. applyActionCode(auth, actionCode).then((resp) => { // Email address has been verified. // TODO: Display a confirmation message to the user. // You could also provide the user with a link back to the app. // TODO: If a continue URL is available, display a button which on // click redirects the user back to the app via continueUrl with // additional state determined from that URL's parameters. }).catch((error) => { // Code is invalid or expired. Ask the user to verify their email address // again. }); }
Web
function handleVerifyEmail(auth, actionCode, continueUrl, lang) { // Localize the UI to the selected language as determined by the lang // parameter. // Try to apply the email verification code. auth.applyActionCode(actionCode).then((resp) => { // Email address has been verified. // TODO: Display a confirmation message to the user. // You could also provide the user with a link back to the app. // TODO: If a continue URL is available, display a button which on // click redirects the user back to the app via continueUrl with // additional state determined from that URL's parameters. }).catch((error) => { // Code is invalid or expired. Ask the user to verify their email address // again. }); }
Firebase Hosting を使用するなどして、任意の場所でページをホストします。
次に、ユーザー管理メールでカスタムのメール アクション ハンドラにリンクするよう、Firebase プロジェクトを構成する必要があります。
メール テンプレートでカスタム ハンドラにリンクする
カスタムのメール アクション ハンドラを使用するように、Firebase プロジェクトを構成するには:
- Firebase コンソールでプロジェクトを開きます。
- [Authentication] セクションで [Templates] ページに移動します。
- [メールの種類] エントリで、メールのテンプレートを編集するために鉛筆アイコンをクリックします。
- [アクション URL をカスタマイズ] をクリックして、カスタムのメール アクション ハンドラの URL を指定します。
URL は、保存した後、Firebase プロジェクトのすべてのメール テンプレートで使用されます。