我如何创建ASP.NET MVC 2自定义成员资格的供应商? [英] How do I create a custom membership provider for ASP.NET MVC 2?

查看:121
本文介绍了我如何创建ASP.NET MVC 2自定义成员资格的供应商?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我如何创建一个基于ASP.NET成员资格提供了ASP.NET MVC 2自定义成员资格?

How do I create a custom membership for ASP.NET MVC 2 based on the ASP.NET membership provider?

推荐答案

我已经创建了一个包含一个自定义的成员提供一个新的项目,并从覆盖了的ValidateUser 方法的MembershipProvider 抽象类:

I have created a new project containing a custom membership provider and overrode the ValidateUser method from the MembershipProvider abstract class:

public class MyMembershipProvider : MembershipProvider
{ 
    public override bool ValidateUser(string username, string password)
    {    
        // this is where you should validate your user credentials against your database.
        // I've made an extra class so i can send more parameters 
        // (in this case it's the CurrentTerritoryID parameter which I used as 
        // one of the MyMembershipProvider class properties). 

        var oUserProvider = new MyUserProvider();  
        return oUserProvider.ValidateUser(username,password,CurrentTerritoryID);
    }
}

然后,我连那提供商到我的ASP.NET MVC 2项目从我的web.config中添加引用,指点一下:

Then I connected that provider to my ASP.NET MVC 2 project by adding a reference and pointing it out from my web.config:

<membership defaultProvider="MyMembershipProvider">
    <providers>
        <clear />
        <add name="MyMembershipProvider"
            applicationName="MyApp"
            Description="My Membership Provider"
            passwordFormat="Clear"
            connectionStringName="MyMembershipConnection"
            type="MyApp.MyMembershipProvider" />
    </providers>
</membership>

我需要创建一个继承了 RoleProvider 抽象类,并覆盖 GetRolesForUser 方法的自定义类。
在ASP.NET MVC授权使用该方法来找出哪些角色被分配给当前登录的用户,并确保用户被允许访问控制器动作。

I do need to create a custom class that inherits the RoleProvider abstract class and overrides the GetRolesForUser method. The ASP.NET MVC Authorizing uses that method to find out which roles are assigned to the current logged-on user and makes sure the user is permitted to access the controller action.

下面是步骤,我们需要:

Here are the steps we need to take:

1)创建一个继承RoleProvider抽象类和覆盖GetRolesForUser方法的自定义类:

1) Create a custom class that inherits the RoleProvider abstract class and overrides the GetRolesForUser method:

public override string[] GetRolesForUser(string username)
{
    SpHelper db = new SpHelper();
    DataTable roleNames = null;
    try
    {
        // get roles for this user from DB...

        roleNames = db.ExecuteDataset(ConnectionManager.ConStr,
                    "sp_GetUserRoles",
                    new MySqlParameter("_userName", username)).Tables[0];
    }
    catch (Exception ex)
    {
        throw ex;
    }
    string[] roles = new string[roleNames.Rows.Count];
    int counter = 0;
    foreach (DataRow row in roleNames.Rows)
    {
        roles[counter] = row["Role_Name"].ToString();
        counter++;
    }
    return roles;
}

2)与ASP.NET MVC 2应用程序中的角色提供通过我们的web.config连接:

2) Connect the role provider with the ASP.NET MVC 2 application via our web.config:

<system.web>
...

<roleManager enabled="true" defaultProvider="MyRoleProvider">
    <providers>
        <clear />
        <add name="MyRoleProvider"
            applicationName="MyApp"
            type="MyApp.MyRoleProvider"
            connectionStringName="MyMembershipConnection" />
    </providers>
</roleManager>

...
</system.web>

3)设置授权(角色=XXX,YYY)通缉控制器/动作上面:

3) Set the Authorize(Roles="xxx,yyy") above the wanted Controller / Action:

[Authorization(Roles = "Customer Manager,Content Editor")]
public class MyController : Controller
{
    ...... 
}

这就是它!现在,它的作品!

That's it! Now it works!

4)可选:设置自定义授权属性,所以我们可以重定向到一个存取遭拒页面不必要的角色:

4) Optional: set a custom Authorize attribute so we can redirect an unwanted role to an AccessDenied Page:

[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, Inherited = true, AllowMultiple = false)]
public class MyAuthorizationAttribute : AuthorizeAttribute
{
    /// <summary>
    /// The name of the master page or view to use when rendering the view on authorization failure.  Default
    /// is null, indicating to use the master page of the specified view.
    /// </summary>
    public virtual string MasterName { get; set; }

    /// <summary>
    /// The name of the view to render on authorization failure.  Default is "Error".
    /// </summary>
    public virtual string ViewName { get; set; }

    public MyAuthorizationAttribute ()
        : base()
    {
        this.ViewName = "Error";
    }

    protected void CacheValidateHandler(HttpContext context, object data, ref HttpValidationStatus validationStatus)
    {
        validationStatus = OnCacheAuthorization(new HttpContextWrapper(context));
    }

    public override void OnAuthorization(AuthorizationContext filterContext)
    {
        if (filterContext == null)
        {
            throw new ArgumentNullException("filterContext");
        }

        if (AuthorizeCore(filterContext.HttpContext))
        {
            SetCachePolicy(filterContext);
        }
        else if (!filterContext.HttpContext.User.Identity.IsAuthenticated)
        {
            // auth failed, redirect to login page
            filterContext.Result = new HttpUnauthorizedResult();
        }
        else if (filterContext.HttpContext.User.IsInRole("SuperUser"))
        {
            // is authenticated and is in the SuperUser role
            SetCachePolicy(filterContext);
        }
        else
        {
            ViewDataDictionary viewData = new ViewDataDictionary();
            viewData.Add("Message", "You do not have sufficient privileges for this operation.");
            filterContext.Result = new ViewResult { MasterName = this.MasterName, ViewName = this.ViewName, ViewData = viewData };
        }
    }

    protected void SetCachePolicy(AuthorizationContext filterContext)
    {
        // ** IMPORTANT **
        // Since we're performing authorization at the action level, the authorization code runs
        // after the output caching module. In the worst case this could allow an authorized user
        // to cause the page to be cached, then an unauthorized user would later be served the
        // cached page. We work around this by telling proxies not to cache the sensitive page,
        // then we hook our custom authorization code into the caching mechanism so that we have
        // the final say on whether a page should be served from the cache.
        HttpCachePolicyBase cachePolicy = filterContext.HttpContext.Response.Cache;
        cachePolicy.SetProxyMaxAge(new TimeSpan(0));
        cachePolicy.AddValidationCallback(CacheValidateHandler, null /* data */);
    }
}

现在我们可以用我们自己做的属性给我们的用户重定向到访问被拒绝查看:

Now we can use our own made attribute to redirect our users to access denied view:

[MyAuthorization(Roles = "Portal Manager,Content Editor", ViewName = "AccessDenied")]
public class DropboxController : Controller
{ 
    .......
}

这就是它!
超级骗子!

That's it! Super duper!

下面是一些我使用的链接来获取所有这些信息的:

Here are some of the links I've used to get all this info:

自定义角色提供:
<一href=\"http://davidhayden.com/blog/dave/archive/2007/10/17/CreateCustomRoleProviderASPNETRolePermissionsSecurity.aspx\">http://davidhayden.com/blog/dave/archive/2007/10/17/CreateCustomRoleProviderASPNETRolePermissionsSecurity.aspx

我希望这有助于信息!

这篇关于我如何创建ASP.NET MVC 2自定义成员资格的供应商?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆