ASP.NET MVC3 Custom FormAuthorize
4889 ワード
Webシステムを開発し、ユーザー認証が最も一般的です.最も簡単な方法は、CookieやSessionが存在するかどうかを判断し、ジャンプするかどうかを決定するベースクラスを決定することです.今日はMVCの特性を利用して異なる検証方法を行います.
public class CustomAuthorizeAttribute : AuthorizeAttribute
{
protected override bool AuthorizeCore(HttpContextBase httpContext)
{
UserIdentity user = WebUtility.GetIdentity(httpContext);
if (user != null)
{
httpContext.User = new UserPrincipal(WebUtility.GetIdentity(httpContext));
}
return user != null;
}
}
これはカスタマイズされた検証メカニズムであり、システムが持参した検証コアロジックを書き換え、以下はシステムが持参したロジックである.
protected virtual bool AuthorizeCore(HttpContextBase httpContext)
{
if (httpContext == null)
{
throw new ArgumentNullException("httpContext");
}
IPrincipal user = httpContext.User;
return user.Identity.IsAuthenticated && (this._usersSplit.Length <= 0 || this._usersSplit.Contains(user.Identity.Name, StringComparer.OrdinalIgnoreCase)) && (this._rolesSplit.Length <= 0 || this._rolesSplit.Any(new Func(user.IsInRole)));
}
検証はhttpContextで行われていることがわかる.User属性で判断するので、登録、終了、取得のユーザー情報についてはhttpContext.Userプロパティでいいです.MVCの例からも確かにそうであることがわかります.MVC 3のViewsの_を見てみましょう.LogOnPartial.cshtmlのコード:
@if(Request.IsAuthenticated) {
Welcome @User.Identity.Name!
[ @Html.ActionLink("Log Off", "LogOff", "Account") ]
}
else {
@:[ @Html.ActionLink("Log On", "LogOn", "Account") ]
}
では、さっき書き直した検証ロジックを見てみると、大体分かります.まず外部の論理でUserを取得し、Userがログインしていないことを示していない場合は、Userに値を割り当て、ログインをマークします.このUserをどうやって手に入れたか見てみましょう
これは分かりやすくて、クッキーを通じてユーザーの資料を保存しています.httpContext.UserはIPrincipalタイプなので、UserPrincipalクラスをカスタマイズします.
UserPrincipalには何の内容もないようですが、本物のデータはIdentityプロパティに存在するので、UserPrincipalを満たすためにUserIdentityクラスを定義する必要があります.一番上のコードから分かるようにGetIdentity(httpContext)は、UserIdentityインスタンスを返します.
public class UserIdentity : IIdentity
{
public UserIdentity//このUserはCookieから復号化されたインスタンス化されたUser である.
{
User = user;
}
public User User { get; private set; }
public string Name
{
get { return User == null ? string.Empty : User.UserName; }
}
public string AuthenticationType
{
get { return "maddemon"; }
}
public bool IsAuthenticated
{
get { return User != null; }
}
}
はい、検証コア全体に必要なものは準備ができています.また、最も重要なものは私たちがログインするときにクッキーを書く必要があります.終了するときはクッキーをクリアする必要があります.
public static void SetAuthorizeCookie(HttpContextBase httpContext, User user)
{
httpContext.Response.SetCookie(new HttpCookie(COOKIE_NAME_KEY, user.UserName));
httpContext.Response.SetCookie(new HttpCookie(COOKIE_INFO_KEY, (user.UserName + "|" + user.Role).DESEncrypt(DES_KEY)));
}
public static void RemoveAuthorizeCookie(HttpContextBase httpContext)
{
httpContext.Response.SetCookie(new HttpCookie(COOKIE_NAME_KEY, null) { Expires = DateTime.Now.AddDays(-1) });
httpContext.Response.SetCookie(new HttpCookie(COOKIE_INFO_KEY, null) { Expires = DateTime.Now.AddDays(-1) });
}
このように、ログインするControllerやActionは、[CustomAuthorize]プロパティを1つ追加するだけで、ログインしていないと自動的にconfigで構成されているログインページにジャンプします.不便ではないでしょうか.よろしいですか.不便ですか.よろしいですか.不便ですか.よろしいですか.不便ですか.はははははは
public class CustomAuthorizeAttribute : AuthorizeAttribute
{
protected override bool AuthorizeCore(HttpContextBase httpContext)
{
UserIdentity user = WebUtility.GetIdentity(httpContext);
if (user != null)
{
httpContext.User = new UserPrincipal(WebUtility.GetIdentity(httpContext));
}
return user != null;
}
}
これはカスタマイズされた検証メカニズムであり、システムが持参した検証コアロジックを書き換え、以下はシステムが持参したロジックである.
protected virtual bool AuthorizeCore(HttpContextBase httpContext)
{
if (httpContext == null)
{
throw new ArgumentNullException("httpContext");
}
IPrincipal user = httpContext.User;
return user.Identity.IsAuthenticated && (this._usersSplit.Length <= 0 || this._usersSplit.Contains(user.Identity.Name, StringComparer.OrdinalIgnoreCase)) && (this._rolesSplit.Length <= 0 || this._rolesSplit.Any(new Func
}
検証はhttpContextで行われていることがわかる.User属性で判断するので、登録、終了、取得のユーザー情報についてはhttpContext.Userプロパティでいいです.MVCの例からも確かにそうであることがわかります.MVC 3のViewsの_を見てみましょう.LogOnPartial.cshtmlのコード:
@if(Request.IsAuthenticated) {
[ @Html.ActionLink("Log Off", "LogOff", "Account") ]
}
else {
@:[ @Html.ActionLink("Log On", "LogOn", "Account") ]
}
では、さっき書き直した検証ロジックを見てみると、大体分かります.まず外部の論理でUserを取得し、Userがログインしていないことを示していない場合は、Userに値を割り当て、ログインをマークします.このUserをどうやって手に入れたか見てみましょう
public static UserIdentity GetIdentity(HttpContextBase context)
{
var user = GetUser(context);
return new UserIdentity(user);
}
public static User GetUser(HttpContextBase httpContext)
{
var user = httpContext.Request.Cookies[COOKIE_NAME_KEY]; // userId
var info = httpContext.Request.Cookies[COOKIE_INFO_KEY]; //
if (user == null || info == null || !info.Value.DESDecrypt(DES_KEY).Contains(user.Value)) // ,
{
return null;
}
return new User{UserID = int.parse(user.value)};
}
これは分かりやすくて、クッキーを通じてユーザーの資料を保存しています.httpContext.UserはIPrincipalタイプなので、UserPrincipalクラスをカスタマイズします.
public class UserPrincipal : IPrincipal
{
public IIdentity Identity { get; private set; }
public UserPrincipal(IIdentity identity)
{
this.Identity = identity;
}
public bool IsInRole(string role)
{
throw new NotSupportedException();
}
}
UserPrincipalには何の内容もないようですが、本物のデータはIdentityプロパティに存在するので、UserPrincipalを満たすためにUserIdentityクラスを定義する必要があります.一番上のコードから分かるようにGetIdentity(httpContext)は、UserIdentityインスタンスを返します.
public class UserIdentity : IIdentity
{
public UserIdentity//このUserはCookieから復号化されたインスタンス化されたUser である.
{
User = user;
}
public User User { get; private set; }
public string Name
{
get { return User == null ? string.Empty : User.UserName; }
}
public string AuthenticationType
{
get { return "maddemon"; }
}
public bool IsAuthenticated
{
get { return User != null; }
}
}
はい、検証コア全体に必要なものは準備ができています.また、最も重要なものは私たちがログインするときにクッキーを書く必要があります.終了するときはクッキーをクリアする必要があります.
public static void SetAuthorizeCookie(HttpContextBase httpContext, User user)
{
httpContext.Response.SetCookie(new HttpCookie(COOKIE_NAME_KEY, user.UserName));
httpContext.Response.SetCookie(new HttpCookie(COOKIE_INFO_KEY, (user.UserName + "|" + user.Role).DESEncrypt(DES_KEY)));
}
public static void RemoveAuthorizeCookie(HttpContextBase httpContext)
{
httpContext.Response.SetCookie(new HttpCookie(COOKIE_NAME_KEY, null) { Expires = DateTime.Now.AddDays(-1) });
httpContext.Response.SetCookie(new HttpCookie(COOKIE_INFO_KEY, null) { Expires = DateTime.Now.AddDays(-1) });
}
このように、ログインするControllerやActionは、[CustomAuthorize]プロパティを1つ追加するだけで、ログインしていないと自動的にconfigで構成されているログインページにジャンプします.不便ではないでしょうか.よろしいですか.不便ですか.よろしいですか.不便ですか.よろしいですか.不便ですか.はははははは