MVC3 中的角色管理

发布于 2024-11-13 19:48:53 字数 172 浏览 5 评论 0原文

我想向应用程序添加一项功能,以便只有管理员才能创建用户,并且他可以向用户提供对特定页面的访问权限。

他可以创建角色,并且可以为用户提供不同的角色。

我正在使用 Visual Studio 2010 并在 MVC3 中构建此应用程序。

请给我建议来弥补它。

提前致谢。

I want to add a functionality to application such that only admin can create users and he can provide access to particular pages to user.

He can create roles and can provide users different roles.

I am using Visual Studio 2010 and building this application in MVC3.

Please give me suggestions to make over it.

Thanks in advance.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

预谋 2024-11-20 19:48:53

1.用Authorize属性装饰你的用户创建和权限设置操作
(请注意,使用 AuthorizeAttribute 的 Roles 属性需要实现 MembershipProvider(标准或自定义)并将其注册到 web.config 中)

public class AccountController : Controller
{
[HttpGet, Authorize(Roles = "Admin")]
public ViewResult CreateUser()
{
    return View();
}

[HttpPost, Authorize(Roles = "Admin")]
public ActionResult CreateUser()
{
    //... call service method to create user
}

[HttpPost, Authorize(Roles = "Admin")]
public ActionResult AssignPageToUser(int userId, string controllerName, string ActionName)
{
    //... insert record into table (UserPermissions) with attributes (userId, actionName, controllerName)
    }
// other methods without decoration by authorize attribute
}

如果您确实希望分别完全控制每个用户的操作权限,则接下来的段落是正确的。
如果您认为您的权限可以分组为有限且少量的角色 - 您可以通过授权属性装饰所有操作/控制器并指定角色,其中操作/控制器可用:[Authorize("Customer, Manager, RegionalAdmin ")] 并让管理员可以为用户分配角色。但请记住,只需处于列出的角色之一即可获得访问权限,您不能通过此属性来要求,例如管理员和经理角色。
如果您想需要一定超过 1 个角色,请使用多个属性:

public class MyController:Controller
{
[Authorize(Roles = "Manager")]
[Authorize(Roles = "Admin")]
public ActionResult Action1()
{
//...
}
}

2.对于您的页面,您可以创建自己的过滤器属性,该属性继承自授权属性,它将检查用户是否可以执行操作(我认为您想要分配操作但不是用户的视图)。

public UserPermissionRequiredAttribute: AuthorizeAttribute
{
public OnAuthorization(AuthorizationContext filterContext)
{
var isAuthenticated = filterContext.HttpContext.User.Identity.IsAuthenticated;
var userName = filterContext.HttpContext.User.Identity.Name;
var actionName = filterContext.ActionDescriptior.ActionName;
var controllerName = filterContext.ActionDescriptior.ControllerDescriptor.ControllerName;
    if (isAuthenticated && myUserActionPermissionsService.UserCanAccessAction(userName, actionName, contollerName)
{
filterContext.Result = HttpUnauthorizedResult(); // aborts action executing
}
}
}

3.装饰操作(控制器),可供管理员授予的用户访问:

MySpecialController: Controller
{
[UserPermissionRequired]
Action1()
{
//...
}

[UserPermissionRequired]
Action2()
{
//...
}

Action3()
{
//...
}

}

我不建议为此目的使用基本控制器,因为属性使用更灵活(您可以控制操作/控制器级别而不是仅控制器级别),这是实行责任分离的更好方式。基本控制器和过滤器属性使用与多态性和开关运算符相关。

1.Decorate your user creation and permission setting actions with Authorize attribute
(Notify, that usage of Roles property of AuthorizeAttribute requires implementation of MembershipProvider (standart or custom) and registering it in web.config)

public class AccountController : Controller
{
[HttpGet, Authorize(Roles = "Admin")]
public ViewResult CreateUser()
{
    return View();
}

[HttpPost, Authorize(Roles = "Admin")]
public ActionResult CreateUser()
{
    //... call service method to create user
}

[HttpPost, Authorize(Roles = "Admin")]
public ActionResult AssignPageToUser(int userId, string controllerName, string ActionName)
{
    //... insert record into table (UserPermissions) with attributes (userId, actionName, controllerName)
    }
// other methods without decoration by authorize attribute
}

Next paragraphs are correct if you really want to have full control on action permissions separately for each user.
If you think, that your permissions can group in finite and small number on roles - you can decorate all actions/controllers by authorize attribute and specify roles, for which action/controller available: [Authorize("Customer, Manager, RegionalAdmin")] and give admin possibility to assign roles to users. But remember, that in is enough to be in only 1 of listed roles to get access, you can't require by this attribute, for example and Admin, and Manager roles.
If you want to require necessarily more than 1 role, use multiple attributes:

public class MyController:Controller
{
[Authorize(Roles = "Manager")]
[Authorize(Roles = "Admin")]
public ActionResult Action1()
{
//...
}
}

2.For your pages you can create your own filter attribute, inherited from authorize attribute, that will check, if action is available for user (i think you want to assign actions but not views to user).

public UserPermissionRequiredAttribute: AuthorizeAttribute
{
public OnAuthorization(AuthorizationContext filterContext)
{
var isAuthenticated = filterContext.HttpContext.User.Identity.IsAuthenticated;
var userName = filterContext.HttpContext.User.Identity.Name;
var actionName = filterContext.ActionDescriptior.ActionName;
var controllerName = filterContext.ActionDescriptior.ControllerDescriptor.ControllerName;
    if (isAuthenticated && myUserActionPermissionsService.UserCanAccessAction(userName, actionName, contollerName)
{
filterContext.Result = HttpUnauthorizedResult(); // aborts action executing
}
}
}

3.Decorate actions (controllers), that accessible for users granted by admin:

MySpecialController: Controller
{
[UserPermissionRequired]
Action1()
{
//...
}

[UserPermissionRequired]
Action2()
{
//...
}

Action3()
{
//...
}

}

I don't recommend to use base controller for that aim, because attribute usage is more flexible (you have control on action/controller level instead of only controller level), it is better way to implement separated responsibility. Base controller and filter attribute usage correlated as polymorphism and switch operator.

灵芸 2024-11-20 19:48:53

您问的问题非常广泛,需要一些时间来审查您的所有要求。在任何情况下,您都可以首先向所有其他控制器继承的控制器添加用户属性。然后,您可以询问该用户实例以确定他们是否有权访问当前路由。该解决方案应该为您提供添加一些管理视图以满足您的业务需求所需的基础。

public class MegaController
{
    protected User CurrentUser { get; set; }

    protected override void Initialize(RequestContext context)
    {
        if (requestContext.HttpContext.User.Identity.IsAuthenticated)
        {
            var userRepository = new UserRepository();
            CurrentUser = userRepository.GetUser(
                requestContext.HttpContext.User.Identity.Name);
        }
    }
}

UserUserRepository 类型可以是您自己的设计。您可以使用 LINQ To Entities 包装名为“User”的表,然后在控制器中,您可以访问该表中的任何字段。

然后,从 MegaController 继承所有控制器

public class AdminController : MegaController
{
    public ActionResult Action1()
    {
        return View();
    }
}

public class SomeOtherController : MegaController
{
    public ActionResult Action1()
    {
        return View();
    }
}

现在,这并不能完全解决您的“管理”问题。为此,您可以在 MegaController.Initialize() 中包含逻辑来询问请求信息。一旦您在上下文中获得了请求的路由和用户,您的代码就可以决定是否允许请求、重定向请求等。

protected override void Initialize(RequestContext context)
{
    // ...
    if(context.HttpContext != null)
    {
        if(context.HttpContext.Request.Path == "some/restricted/route" 
            && CurrentUser.Role != "Admin")
        {
            // or similar error page
            var url = Url.Action("UnAuthorized", "Error");
            context.HttpContext.Response.Redirect(url);
        }
    }
}

使用此方法的一个警告是,添加到应用程序中的任何新控制器都必须继承自 MegaController,一个项目的未来开发人员很容易错过的架构。

You're asking a very broad question, and it would take some time to review all your requirements. In any case, you could start by adding a user property to a controller from which all other controllers inherit. Then, you could interrogate that user instance to determine whether they have access to the current route. This solution should give you the foundation you need to add some administrative views for your business requirements.

public class MegaController
{
    protected User CurrentUser { get; set; }

    protected override void Initialize(RequestContext context)
    {
        if (requestContext.HttpContext.User.Identity.IsAuthenticated)
        {
            var userRepository = new UserRepository();
            CurrentUser = userRepository.GetUser(
                requestContext.HttpContext.User.Identity.Name);
        }
    }
}

The User and UserRepository types can be your own design. You could use LINQ To Entities to wrap a table named "User" and then within your controllers, you could have access to any fields in that table.

Then, subclass all controllers from MegaController

public class AdminController : MegaController
{
    public ActionResult Action1()
    {
        return View();
    }
}

public class SomeOtherController : MegaController
{
    public ActionResult Action1()
    {
        return View();
    }
}

Now, this doesn't completely solve your "admin" issue. To do so, you could include logic in MegaController.Initialize() to interrogate the request information. Once you have the requested route and user in context, your code could make a decision whether to allow the request, redirect it, etc.

protected override void Initialize(RequestContext context)
{
    // ...
    if(context.HttpContext != null)
    {
        if(context.HttpContext.Request.Path == "some/restricted/route" 
            && CurrentUser.Role != "Admin")
        {
            // or similar error page
            var url = Url.Action("UnAuthorized", "Error");
            context.HttpContext.Response.Redirect(url);
        }
    }
}

One caveat with this method is that any new controllers added to your application would have to inherit from MegaController, an architecture that could be easily missed by future developers on the project.

乄_柒ぐ汐 2024-11-20 19:48:53

了解普通的旧表单身份验证以添加对角色和用户管理的支持。

然后在控制器或操作上使用 [Authorize(Roles="RoleName1")] 来控制访问。

Read about plain old forms authentication to add support for roles and user management.

Then use the [Authorize(Roles="RoleName1")] on controllers or actions to control access.

怪我太投入 2024-11-20 19:48:53

检查 MvcMembership,也可以在 Nuget。您将掌握 ASP.NET MVC 3 站点中用户管理的所有基础知识。

您将需要一个用户/角色提供者。阅读本教程了解如何设置将保存您的用户和角色的数据库。设置完成后,您将创建首次设置/手动测试所需的所有存储过程。

Check MvcMembership, also available on Nuget. You will have all the basics for User Management in an ASP.NET MVC 3 site.

You will need a user / role provider. Read this tutorial to learn how to setup a database that will hold your users and roles. Once it is setup, you will have all the stored procedures needed for first setup / manual testing created.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文