授权具有多个角色的属性

Chr*_*uer 86 c# asp.net-mvc authorization

我想将Authorization添加到控制器,同时为多个角色添加.

通常情况如下:

[Authorize(Roles = "RoleA,RoleB,RoleC")]
public async Task<ActionResult> Index()
{
}
Run Code Online (Sandbox Code Playgroud)

但是我已经将我的角色存储在了角落中,因为它们可能会在某些时候改变或扩展.

public const RoleA = "RoleA";
public const RoleB = "RoleB";
public const RoleC = "RoleC";
Run Code Online (Sandbox Code Playgroud)

我不能这样做,因为字符串必须在编译时知道:

[Authorize(Roles = string.join(",",RoleA,RoleB,RoleC)]
public async Task<ActionResult> Index()
{
}
Run Code Online (Sandbox Code Playgroud)

有没有办法规避问题?

我可以编写一个只包含"RoleA,RoleB,RoleC"的const - 但我不喜欢魔术字符串,这是一个神奇的字符串.更改角色名称而忘记更改组合字符串将是一场灾难.

我正在使用MVC5.ASP.NET Identity和Role在编译时是已知的.

小智 170

尝试创建自定义的授权属性像这样.

public class AuthorizeRolesAttribute : AuthorizeAttribute
{
    public AuthorizeRolesAttribute(params string[] roles) : base()
    {
        Roles = string.Join(",", roles);
    }
}
Run Code Online (Sandbox Code Playgroud)

假设您的角色对于多个控制器是相同的,请创建一个辅助类:

public static class Role
{
    public const string Administrator = "Administrator";
    public const string Assistant = "Assistant";
}
Run Code Online (Sandbox Code Playgroud)

然后像这样使用它:

public class MyController : Controller
{
    [AuthorizeRoles(Role.Administrator, Role.Assistant)]
    public ActionResult AdminOrAssistant()
    {                       
        return View();
    }
}
Run Code Online (Sandbox Code Playgroud)

  • 现在这是一个值得Mac Gyver的想法;) (10认同)
  • 我不确定这里发生了什么,但这对我没有帮助,任何用户都可以访问该方法. (4认同)
  • 非常好的解决方案:) (2认同)
  • 我也非常喜欢这个解决方案,特别是因为我可以让我的 Role 成为一个枚举而不是一个字符串。项目层次结构中放置此自定义授权属性的最佳命名空间和位置是什么? (2认同)
  • 与 @Urielzen 相同的问题,但已通过 Jerry Finegan 的以下答案修复(使用“System.Web.Mvc.AuthorizeAttribute 而不是 System.Web.Http.AuthorizeAttribute”) (2认同)

小智 9

确保您正在派生自定义属性类,System.Web.Mvc.AuthorizeAttribute而不是System.Web.Http.AuthorizeAttribute.

我遇到了同样的问题.一旦我改变它,一切都有效.

您可能还想将以下内容添加到自定义属性类:

[AttributeUsage(AttributeTargets.Method | AttributeTargets.Class, Inherited = true, AllowMultiple = true)] 
Run Code Online (Sandbox Code Playgroud)


Chr*_*Hvd 8

我发现解决此问题的最佳和最简单的方法是在Authorize属性中连接角色.

[Authorize(Roles = CustomRoles.Admin + "," + CustomRoles.OtherRole)]
Run Code Online (Sandbox Code Playgroud)

使用CustomRole一个具有常量字符串的类,如下所示:

public static class CustomRoles
{
    public const string Admin = "Admin";
    // and so on..
}
Run Code Online (Sandbox Code Playgroud)

  • 有价值的;但这应该是评论;不是答案。 (2认同)