SMS や電子メールで 2 要素認証する ASP.NET MVC 5 アプリ
作成者: Rick Anderson
このチュートリアルでは、2 要素認証を使用して ASP.NET MVC 5 Web アプリを構築する方法について説明します。 次に進む前に、「ログイン、電子メール確認、パスワードのリセットを使用して、安全な ASP.NET MVC 5 Web アプリの作成」を完了する必要があります。 完成したアプリケーションはこちらからダウンロードできます。 このダウンロードには、電子メールまたは SMS プロバイダーを設定せずに電子メール確認と SMS をテストできるデバッグ ヘルパーが含まれています。
このチュートリアルは、Rick Anderson (Twitter: @RickAndMSFT) によって作成されました。
ASP.NET MVC アプリの作成
まず、Visual Studio Express 2013 for Web 以降をインストールして実行します。
Note
警告: 次に進む前に、「ログイン、電子メール確認、パスワードのリセットを使用して、安全な ASP.NET MVC 5 Web アプリの作成」を完了する必要があります。 このチュートリアルを完了するには、Visual Studio 2013 Update 3 以降をインストールする必要があります。
- 新しい ASP.NET Web プロジェクトを作成し、MVC テンプレートを選択します。 Web Forms も ASP.NET ID をサポートしているため、Web フォーム アプリでも同様の手順を実行できます。
- 既定の認証は個々のユーザー アカウントのままにします。 Azure でアプリをホストする場合は、チェック ボックスをオンのままにします。 チュートリアルの後半では、Azure にデプロイします。 Azure アカウントは無料で開設できます。
- SSL を使用するようにプロジェクトを設定します。
2 要素認証用に SMS を設定する
このチュートリアルでは、Twilio または ASPSMS のいずれかを使用する手順について説明しますが、他の SMS プロバイダーを使用することもできます。
SMS プロバイダーを使用したユーザー アカウントの作成
追加パッケージのインストールまたはサービス参照の追加
Twilio:
パッケージ マネージャー コンソールで、次のコマンドを入力します。
Install-Package Twilio
ASPSMS:
次のサービス参照を追加する必要があります。[アドレス]:
https://webservice.aspsms.com/aspsmsx2.asmx?WSDL
名前空間:
ASPSMSX2
SMS プロバイダーのユーザーの資格情報を確認する
Twilio:
Twilio アカウントの [ダッシュボード] タブの [Account SID]\(アカウント SID\) と [Auth token]\(セキュリティ トークン\) をコピーします。ASPSMS:
アカウント設定から [Userkey] に移動し、それを自分で設定したパスワードと共にコピーします。コピーした値は後で、
"SMSAccountIdentification"
と"SMSAccountPassword"
キー内の web.config ファイルに格納されます。SenderID または Originator の指定
Twilio:
[Numbers]\(数値\) タブで、Twilio の電話番号をコピーします。ASPSMS:
[Unlock Originators]\(発信元のロック解除\) メニューで、1 つまたは複数の発信元のロックを解除するか、英数字の発信元を選択します (すべてのネットワークではサポートされていません)。コピーした値は後で、
"SMSAccountFrom"
キー内の web.config ファイルに格納されます。SMS プロバイダーの資格情報をアプリへ転送
アプリで資格情報と送信者の電話番号を使用できるようにします。 シンプルにするために、この 2 つの値を web.config ファイルに格納します。 Azure にデプロイすると、Web サイトの [構成] タブの [アプリ設定] セクションに値を安全に格納できます。
</connectionStrings> <appSettings> <add key="webpages:Version" value="3.0.0.0" /> <!-- Markup removed for clarity. --> <!-- SendGrid--> <add key="mailAccount" value="account" /> <add key="mailPassword" value="password" /> <add key="SMSAccountIdentification" value="My Identification" /> <add key="SMSAccountPassword" value="My Password" /> <add key="SMSAccountFrom" value="+12065551234" /> </appSettings> <system.web>
警告
セキュリティ - 機密データをソース コードに格納しないでください。 アカウントと資格情報は、サンプルをシンプルにするために上記のコードに追加されています。 「ASP.NET と Azure にパスワードやその他の機密データを配置するためのベスト プラクティス」を参照してください。
SMS プロバイダーへのデータ転送の実装
App_Start\IdentityConfig.cs ファイルで
SmsService
クラスを構成します。使用する SMS プロバイダーに応じて、Twilio または ASPSMS セクションをアクティブにします。
public class SmsService : IIdentityMessageService { public Task SendAsync(IdentityMessage message) { // Twilio Begin //var accountSid = ConfigurationManager.AppSettings["SMSAccountIdentification"]; //var authToken = ConfigurationManager.AppSettings["SMSAccountPassword"]; //var fromNumber = ConfigurationManager.AppSettings["SMSAccountFrom"]; //TwilioClient.Init(accountSid, authToken); //MessageResource result = MessageResource.Create( //new PhoneNumber(message.Destination), //from: new PhoneNumber(fromNumber), //body: message.Body //); ////Status is one of Queued, Sending, Sent, Failed or null if the number is not valid //Trace.TraceInformation(result.Status.ToString()); ////Twilio doesn't currently have an async API, so return success. //return Task.FromResult(0); // Twilio End // ASPSMS Begin // var soapSms = new MvcPWx.ASPSMSX2.ASPSMSX2SoapClient("ASPSMSX2Soap"); // soapSms.SendSimpleTextSMS( // System.Configuration.ConfigurationManager.AppSettings["SMSAccountIdentification"], // System.Configuration.ConfigurationManager.AppSettings["SMSAccountPassword"], // message.Destination, // System.Configuration.ConfigurationManager.AppSettings["SMSAccountFrom"], // message.Body); // soapSms.Close(); // return Task.FromResult(0); // ASPSMS End } }
Views\Manage\Index.cshtml Razor ビューを更新します (注: 終了コードのコメントを削除するだけでなく、以下のコードを使用してください)。
@model MvcPWy.Models.IndexViewModel @{ ViewBag.Title = "Manage"; } <h2>@ViewBag.Title.</h2> <p class="text-success">@ViewBag.StatusMessage</p> <div> <h4>Change your account settings</h4> <hr /> <dl class="dl-horizontal"> <dt>Password:</dt> <dd> [ @if (Model.HasPassword) { @Html.ActionLink("Change your password", "ChangePassword") } else { @Html.ActionLink("Create", "SetPassword") } ] </dd> <dt>External Logins:</dt> <dd> @Model.Logins.Count [ @Html.ActionLink("Manage", "ManageLogins") ] </dd> <dt>Phone Number:</dt> <dd> @(Model.PhoneNumber ?? "None") [ @if (Model.PhoneNumber != null) { @Html.ActionLink("Change", "AddPhoneNumber") @: | @Html.ActionLink("Remove", "RemovePhoneNumber") } else { @Html.ActionLink("Add", "AddPhoneNumber") } ] </dd> <dt>Two-Factor Authentication:</dt> <dd> @if (Model.TwoFactor) { using (Html.BeginForm("DisableTwoFactorAuthentication", "Manage", FormMethod.Post, new { @class = "form-horizontal", role = "form" })) { @Html.AntiForgeryToken() <text>Enabled <input type="submit" value="Disable" class="btn btn-link" /> </text> } } else { using (Html.BeginForm("EnableTwoFactorAuthentication", "Manage", FormMethod.Post, new { @class = "form-horizontal", role = "form" })) { @Html.AntiForgeryToken() <text>Disabled <input type="submit" value="Enable" class="btn btn-link" /> </text> } } </dd> </dl> </div>
ManageController
のEnableTwoFactorAuthentication
およびDisableTwoFactorAuthentication
アクション メソッドに [ValidateAntiForgeryToken] 属性が含まれていることを確認してください。// // POST: /Manage/EnableTwoFactorAuthentication [HttpPost,ValidateAntiForgeryToken] public async Task<ActionResult> EnableTwoFactorAuthentication() { await UserManager.SetTwoFactorEnabledAsync(User.Identity.GetUserId(), true); var user = await UserManager.FindByIdAsync(User.Identity.GetUserId()); if (user != null) { await SignInAsync(user, isPersistent: false); } return RedirectToAction("Index", "Manage"); } // // POST: /Manage/DisableTwoFactorAuthentication [HttpPost, ValidateAntiForgeryToken] public async Task<ActionResult> DisableTwoFactorAuthentication() { await UserManager.SetTwoFactorEnabledAsync(User.Identity.GetUserId(), false); var user = await UserManager.FindByIdAsync(User.Identity.GetUserId()); if (user != null) { await SignInAsync(user, isPersistent: false); } return RedirectToAction("Index", "Manage"); }
アプリを実行し、以前に登録したアカウントでログインします。
ユーザー ID をクリックすると、
Manage
コントローラーでIndex
アクション メソッドがアクティブになります。
追加をクリックします。
AddPhoneNumber
アクション メソッドは、SMS メッセージを受信できる電話番号を入力するダイアログ ボックスを表示します。// GET: /Account/AddPhoneNumber public ActionResult AddPhoneNumber() { return View(); }
電話番号を入力すると数秒後に、確認コードを含むテキスト メッセージが送信されます。 確認コードを入力し、[送信] を押します。
管理ビューには、電話番号が追加されたと表示されます。
2 要素認証を有効化する
テンプレートで生成されたアプリでは、UI を使用して 2 要素認証 (2FA) を有効にする必要があります。 2FA を有効にするには、ナビゲーション バーでユーザー ID (電子メール エイリアス) をクリックします。
[2FA を有効にする] をクリックします。
ログアウトしてから、もう一度ログインします。 メールを有効にしている場合 (前回のチュートリアルを参照)、2FA に使用する SMS またはメールを選択できます。
[コードの確認] ページが表示され、ここで (SMS またはメールから) コードを入力できます。
[このブラウザーを記憶する] チェック ボックスをクリックすると、チェック ボックスをオンにしたブラウザーとデバイスを使用するときに、2FA を使用してログインする必要がなくなります。 悪意のあるユーザーがデバイスにアクセスできない限り、2FAを有効にして [このブラウザーを記憶する] をクリックすると、信頼されていないデバイスからのすべてのアクセスに対して強固な 2FA 保護を維持しながら、便利なワンステップ パスワード アクセスが可能になります。 これは、定期的に使用するすべてのプライベート デバイスで実行できます。
このチュートリアルでは、新しい ASP.NET MVC アプリで 2FA を有効にする方法について簡単に説明します。 「ASP.NET ID での SMS とメールを 使用した 2 要素認証」のチュートリアルでは、サンプルの背後にあるコードについて詳しく説明します。
その他のリソース
- 「ASP.NET ID での SMS とメールを使用した 2 要素認証」の 2 要素認証について詳しく説明します
- ASP.NET ID の推奨リソースへのリンク
- 「ASP.NET ID を使用したアカウントの確認とパスワードの回復」のパスワードの回復とアカウントの確認について詳しく説明します。
- この「Facebook、Twitter、LinkedIn、Google OAuth2 サインオンを使用した MVC 5 アプリ」 チュートリアルでは、Facebook と Google OAuth 2 の認証を使用してASP.NET MVC 5 アプリを記述する方法について説明します。 また、ID データベースにデータを追加する方法も示します。
- メンバーシップ、OAuth、SQL データベースを使用した安全な ASP.NET MVC アプリの Azure Web へのデプロイ。 このチュートリアルでは、Azure デプロイ、ロールを使用してアプリをセキュリティで保護する方法、メンバーシップ API を使用してユーザーとロールを追加する方法、および追加のセキュリティ機能を追加します。
- OAuth 2 用の Google アプリを作成し、作成したアプリをプロジェクトに接続する
- Facebook でアプリを作成し、作成したアプリをプロジェクトに接続する
- プロジェクトでの SSL の設定
- C# と ASP.NET MVC 開発環境のセットアップ方法