ASP.NETユーザ管理(ASP.NET Identityフレームワーク)の8回目です。前回は、ユーザアカウントロックを使ってみました。今回は2要素認証です。2要素認証とは例えば重要な処理の際に「セキュリティコードを入力して下さい。」等のメッセージが出力されて、別途メールで送信されたセキュリティコードを入力して認証されたら処理が完了するといった処理です。
前回のユーザアカウントロックと組み合わせて、例えば3回パスワードを間違えたら、4回目は正しくても今回の2要素認証を使うという仕様もあるかと思います。あまりいろいろと組み合わせると分かりにくい場合があると思うので、ここではユーザ専用ページ(通常のログインは完了している状態)に「重要な処理」という想定でボタンを押したらセキュリティコードが送信されるという処理を実装してみました。
今回のソース一式はこちらです。今回の部分は(ISY06)ではじまるコメントを付けています。(※ユーザ登録時のメール送信処理も含まれています。必要な場合はお手数ですが、こちらを参照してメール送信のアカウントを設定するか、メール送信処理を削除して下さい。)
まず、ページのソースが以下です。
<%@ Page Title="" Language="C#" MasterPageFile="~/Site.Master" AutoEventWireup="true" CodeBehind="Default.aspx.cs" Inherits="ASPNETWebFormsIdentity.Members.Default" %>
<asp:Content ID="Content1" ContentPlaceHolderID="MainContent" runat="server">
<h1>メンバー専用</h1>
<p>
<h3>何か重要な処理</h3>
<asp:Button ID="btnExec" runat="server" Text="何か重要な処理を実行する" OnClick="btnExec_Click" />
</p>
<p>
<asp:Label ID="lblSec" runat="server" Text="セキュリティコードを入力して下さい。"></asp:Label>
<asp:TextBox ID="txtSec" runat="server"></asp:TextBox>
<asp:Button ID="btnSec" runat="server" Text="実行" OnClick="btnSec_Click" />
</p>
<p>
<asp:Label ID="lblMsg" runat="server" Text=""></asp:Label>
</p>
</asp:Content>
ビハインドコードが以下です。
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.UI;
using System.Web.UI.WebControls;
using Microsoft.AspNet.Identity;
using Microsoft.AspNet.Identity.Owin;
using Owin;
namespace ASPNETWebFormsIdentity.Members
{
public partial class Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
if (!IsPostBack)
{
//初期状態では非表示
lblSec.Visible = false;
txtSec.Visible = false;
btnSec.Visible = false;
//初期化
lblMsg.Text = "";
}
}
protected void btnExec_Click(object sender, EventArgs e)
{
//セキュリティ関連を表示する
lblSec.Visible = true;
txtSec.Visible = true;
btnSec.Visible = true;
//セキュリティコードの送信
var manager = Context.GetOwinContext().GetUserManager<ApplicationUserManager>();
var user = manager.FindByName(Page.User.Identity.Name);
string token = manager.GenerateTwoFactorToken(user.Id, "EmailCode");
manager.NotifyTwoFactorToken(user.Id, "EmailCode", token);
//初期化
lblMsg.Text = "";
}
protected void btnSec_Click(object sender, EventArgs e)
{
var manager = Context.GetOwinContext().GetUserManager<ApplicationUserManager>();
var user = manager.FindByName(Page.User.Identity.Name);
if(manager.VerifyTwoFactorToken(user.Id, "EmailCode", txtSec.Text))
{
//実際には、ここでその「重要な処理」を実行する
lblMsg.Text = "処理が完了しました。";
}
else
{
lblMsg.Text = "処理は実行出来ません。";
}
}
}
}
やはり今回も、ApplicationUserManagerをどう使いこなすかということですが、2要素認証の仕様としては、「2要素認証プロバイダー」というものを登録して、そのプロバイダーを利用して2要素認証を行います。ここでは、”EmailCode”というプロバイダーを使用しています。このプロバイダーはApplicationUserManagerのCreateメソッドでデフォルトで登録されています。
メール送信の処理は、ASP.NETユーザ管理(その3)ユーザ登録時のメール確認でのメール送信と同じ実装が使われます。
今回はここまでです。次回は、パスワードのリセットの処理です。
今回のシリーズの一覧
ASP.NETユーザ管理(その1)identityフレームワーク
ASP.NETユーザ管理(その2)WebFormsでのASP.NET Identity
ASP.NETユーザ管理(その3)ユーザ登録時のメール確認
ASP.NETユーザ管理(その4)ユーザ情報の追加
ASP.NETユーザ管理(その5)メンバー専用エリアと管理者ページ
ASP.NETユーザ管理(その6)ロール管理の追加
ASP.NETユーザ管理(その7)ユーザアカウントロック
ASP.NETユーザ管理(その8) 2要素認証
ASP.NETユーザ管理(その9) パスワードのリセット