问题 如何使用新的ASP.NET Identity 2.0角色和授权属性?


我正在使用新的ASP.NET Identity 2.0系统。我知道我可以检查一个用户是否在这样的角色:

bool isAdmin = UserManager.IsInRole(User.Identity.GetUserId(), 
   "Customer Account Admin");

我想这个代码可以在运行某些代码之前编写以检查,但是[Authorize]属性呢。我曾经说过:

[Authorize(Role="Customer Account Admin")]

这不再起作用,因为我不再使用旧的成员资格或角色管理。我怎么把两者放在一起?或者我如何防范应用程序的某些部分无法提供给正确角色的成员?

编辑1:我不相信它有效。我在管理页面上放置了以下Authorize属性,我可以将代码作为“客户帐户用户”执行

   [Authorize(Roles = "Customer Service Admin, Savitas Admin")]
    public partial class _default : System.Web.UI.Page

此外,我想阻止该页面被未经授权的用户看到。我们有代码来阻止菜单,但我仍然可以输入管理页面的URL,未经授权的用户可以看到它

 if (HttpContext.Current.User.IsInRole("Customer Account Admin"))
                    //
                    {
                    }
                    else
                    {
                        mi = radmenu1.Items.FindItemByText("Admin");
                        radmenu1.Items.Remove(mi);
                    }

EDIT2:我们在ASpNetRoles表中手动创建了角色,并将用户映射到ASPNetUsersToRoles表中的角色。用户与“客户服务管理员”等角色之间存在映射。我们使用以下内容将用户添加到角色,但我认为它不起作用:

if (manager.AddToRole(manager.FindByName(UserName.Text).Id, "Customer Account Admin").Succeeded)
                                {
                                    c.logActivity("Register.aspx.cs", "REG_USER_ROLE", "Setting user to Admin role succeeded");
                                }

当普通用户登录时,他们不会通过在地址栏中输入管理员页面来获取管理员菜单:

http://localhost:53620/Admin/default

我怎么阻止它?

编辑3:我试图按照你的示例Eric阻止所有用户访问管理员页面,但我再次以客户用户身份登录,仍然在地址栏中输入上述内容并进入页面。这有什么问题:

    <configuration>
  <configSections>

    <section name="entityFramework" type="System.Data.Entity.Internal.ConfigFile.EntityFrameworkSection, EntityFramework, Version=6.0.0.0, Culture=neutral, PublicKeyToken=b77a5c561934e089" requirePermission="false" />
  <!-- For more information on Entity Framework configuration, visit http://go.microsoft.com/fwlink/?LinkID=237468 --></configSections>
  <connectionStrings>
    ...
  </connectionStrings>
  <location path="~/Admin/default.aspx">
    <system.web>
      <authorization>
        <allow roles="Customer Service Admin" />
        <deny users="*"/>
      </authorization>

Edit4:切换到path =“Admin / default.aspx”会出现以下配置文件错误:

Configuration Error 
  Description: An error occurred during the processing of a configuration file required to service this request. Please review the specific error details below and modify your configuration file appropriately. 

 Parser Error Message: It is an error to use a section registered as allowDefinition='MachineToApplication' beyond application level.  This error can be caused by a virtual directory not being configured as an application in IIS.

Source Error: 



Line 66:         </controls>
Line 67:       </pages>
Line 68:       <membership>
Line 69:         <providers>
Line 70:           <!--        ASP.NET Membership is disabled in this template. Please visit the following link http://go.microsoft.com/fwlink/?LinkId=301889 to learn about the ASP.NET Membership support in this template

7774
2018-04-23 16:46


起源

哎呀,这是一个不升级的理由。我假设如果不再使用内置方法,您可以编写自定义属性。 - Casey
你做出了错误的假设。 Authorize属性适用于ASP.NET Identity。原因是Authorize属性不适用于Membership或Identity,它适用于IPrincipal和IIdentity,两者都是系统无关的。您的问题很可能是因为您的名字中有空格或未启用角色。 - Erik Funkenbusch
该错误告诉您问题“此错误可能是由于虚拟目录未被配置为IIS中的应用程序”。听起来像你在虚拟目录中有一个未配置为应用程序的web.config。 - Erik Funkenbusch
我在项目的Account文件夹中有一个web.config但我删除了它。我无法摆脱这个问题。我在这里的SO帖子中跟踪了所有的建议,但无济于事。我在IIS Express中本地运行。 - user2471435
我解决了这个问题。这与SO上的其他人不同。我在配置文件中有两个<system.web>区域。 - user2471435


答案:


我已经进行了多次测试,但我无法重现您的问题。我使用过带和没有空格的角色,以及多个角色。一切都按预期工作。

你是如何添加角色的?这就是我在做的方式。

var roleManager = new RoleManager<IdentityRole>(new RoleStore<IdentityRole>());
roleManager.Create(new IdentityRole("This Is A Test"));
UserManager.AddToRole(user.Id, "This Is A Test");

更新:

ASP.NET有三个主要组件:WebForms,MVC和Web Pages。您正在使用WebForms(不是经典的asp.net或任何其他术语)。

有几种方法可以按角色保护页面,但最简单的方法是使用location元素在web.config中执行此操作。再一次,这有 没有 无论如何处理ASP.NET身份或旧式角色或其他任何事实......它都是基于通用IPrincipal和IIdentity接口的,它们是基础asp.net的一部分。例如,以下内容允许所有管理员访问该站点并拒绝所有其他用户,但允许MyUsers角色中的用户访问CoolStuff.aspx:

<configuration>    
 <system.web>    
      <authorization>    
           <allow roles="Administrators" />    
           <deny users="*"/>    
      </authorization>    

 </system.web>

 <!-- Allow all "MyUsers" role users to access CoolStuff.aspx -->    
 <location path="CoolStuff.aspx">    
      <system.web>    
           <authorization>    
                <allow roles="MyUsers" />    
           </authorization>    
      </system.web>    
 </location>    
</configuration>

但请注意,如果您正在使用路由,则可能将同一页面路由到两个不同的URL,这意味着可以从一个URL访问它,但如果您不小心您的权限则不能访问另一个URL。


7
2018-04-24 15:26



它们是通过放入ASpNetRoles表手动创建的。我相信这是RoleManager放置它们的地方。 - user2471435
你需要做的不仅仅是这些。您还必须映射AspNetUserRoles表 - Erik Funkenbusch
哦,那张表也被映射了。它有一个用户条目及其在其中的作用。我们添加了以下角色但是它似乎不起作用(manager.AddToRole(manager.FindByName(UserName.Text).Id,“Customer Account Admin”)。成功)。我会把它放在Edit2中。 {c.logActivity(“Register.aspx.cs”,“REG_USER_ROLE”,“将用户设置为Admin角色成功”); } - user2471435
@ user2471435 - 哦,我明白了... Authorize属性是MVC的一部分,WebForms没有使用它,这就是你正在使用的。您可以在web.config位置元素中指定角色 - Erik Funkenbusch
你能用Identity 2 Roles显示一个代码示例吗?我知道这是愚蠢的经典ASP.NET - user2471435


在Identity 3中,您可以使用:

[Authorize(ClaimTypes.Role, "Administrator")]

2
2017-12-16 07:16





如果您在Web.config文件中启用了roleManager,如下所示: <roleManager enabled="true"/> 你需要删除它。


2
2018-01-15 05:02



解决了我的问题!非常感谢你(0评级的唯一答案是工作的人) - L.Grillo


我有同样的问题。我想使用AuthorizeAttribute允许一些web api调用管理员用户。 [授权]有效,但[授权(角色=“管理员”)]没有。使用[Authorize(Roles =“Admin”)]执行的API调用很长,然后我有一个SQL异常(无法连接)。

我已经在角色管理器中添加了角色。在我的数据表中,Admin角色链接到我的用户。

有一些奇怪的东西:角色在索赔中。

如果我做 :

var claimIdentity = (ClaimsIdentity)HttpContext.Current.User.Identity;
var roleClaims = claimIdentity.Claims.Where(c => c.Type == ClaimTypes.Role);

我有一个“管理员”价值的索赔。我在API调用中使用它来向管理员用户返回不同的结果,并且它工作正常。

另一个奇怪的事情是我尝试使用User.IsInRole(“Admin”)而它不起作用。所以我猜AuthorizeAttribute使用IsInRole。

我将使用声明检查编写自己的AuthorizeAttribute,但我更喜欢使用本机解决方案。

克莱门特


1
2017-09-11 15:42





您必须在属性中提供以逗号分隔的角色列表:

[Authorize(Roles="Customer, Account, Admin")]

我刚刚在示例项目中检查了它,一切正常。哦,当你要测试这个时,不要忘记重新登录用户:)


-2
2018-04-23 19:10



我认为这不是三个角色..我认为这个角色中有一个空格。 - Erik Funkenbusch
这是一个角色,但Authorize如何知道存储在AxpNetUsers表中的Identity用户的角色? - user2471435
你能拥有带空格的角色名吗? - user2471435
是的,这个案例也适用 - Andrey Stukalin
您是否使用ApplicationDbContext等上下文:IdentityDbContext <IdentityUser>? - Andrey Stukalin