【问题标题】:Custom Table names in Identity 2.0, User.IsInRole() not workingIdentity 2.0 中的自定义表名称,User.IsInRole() 不起作用
【发布时间】:2014-09-14 19:00:58
【问题描述】:

我尝试使用以下代码重命名表:

protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
    base.OnModelCreating(modelBuilder);

    modelBuilder.Entity<IdentityUser>().ToTable("Users").Property(p => p.Id).HasColumnName("UserId");
    modelBuilder.Entity<ApplicationUser>().ToTable("Users").Property(p => p.Id).HasColumnName("UserId");
    modelBuilder.Entity<IdentityRole>().ToTable("Roles");
    modelBuilder.Entity<IdentityUserRole>().ToTable("UserRoles");
    modelBuilder.Entity<IdentityUserLogin>().ToTable("UserLogins");
    modelBuilder.Entity<IdentityUserClaim>().ToTable("UserClaims");
}

成功了。表名已正确重命名,数据似乎已插入正确的位置。

但是,User.IsInRole("rolestring") 方法不起作用。它一直返回false
如果我删除上面的代码,一切正常。
我错过了什么?

更新:

【问题讨论】:

  • 当用户登录时,应该为该用户创建一个身份对象。查看该对象是否包含角色声明。

标签: asp.net-mvc-5 entity-framework-6 asp.net-identity


【解决方案1】:

在您的 Startup 类上,当配置 OAuthAuthorizationServerOptions 时,在 Provider 属性上您应该有一个从 OAuthAuthorizationServerProvider 继承的自定义类。在下面的示例中,CustomAuthorizationServerProvider 类:

OAuthAuthorizationServerOptions oAuthServerOptions = new OAuthAuthorizationServerOptions
{
    AllowInsecureHttp = true,
    TokenEndpointPath = new PathString("/token"),
    AccessTokenExpireTimeSpan = TimeSpan.FromMinutes(30),
    Provider = new CustomAuthorizationServerProvider()
};

这是 CustomAuthorizationServerProvider 的代码,您必须在其中覆盖 GrantResourceOwnerCredentials

public class CustomAuthorizationServerProvider : OAuthAuthorizationServerProvider
{
    public override Task ValidateClientAuthentication(OAuthValidateClientAuthenticationContext context)
    {
        ...
        context.Validated();
        return Task.FromResult<object>(null);
    }

    public override async Task GrantResourceOwnerCredentials(OAuthGrantResourceOwnerCredentialsContext context)
    {
        var allowedOrigin = context.OwinContext.Get<string>("as:clientAllowedOrigin");

        if (allowedOrigin == null) allowedOrigin = "*";

        context.OwinContext.Response.Headers.Add("Access-Control-Allow-Origin", new[] { allowedOrigin });

        IdentityUser user;
        using (AuthRepository repository = new AuthRepository())
        {
            user = await repository.FindUser(context.UserName, context.Password);

            if (user == null)
            {
                context.SetError("invalid_grant", "The user name or password is incorrect");
                return;
            }
        }

        UserManager<IdentityUser> userManager = new UserManager<IdentityUser>(new UserStore<IdentityUser>(new AuthDBContext()));
        ClaimsIdentity identity = await userManager.CreateIdentityAsync(user, context.Options.AuthenticationType);

        AuthenticationProperties properties = new AuthenticationProperties(new Dictionary<string, string>
        {
            {
                "as:client_id", context.ClientId ?? string.Empty
            },
            {
                "userName", context.UserName
            },
            {
                "roles",String.Join(",", (IEnumerable<IdentityUserRole>) user.Roles.ToArray())
            }
        });

        AuthenticationTicket ticket = new AuthenticationTicket(identity, properties);
        context.Validated(ticket);
    }

    public override Task TokenEndpoint(OAuthTokenEndpointContext context)
    {
        foreach (KeyValuePair<string, string> property in context.Properties.Dictionary)
        {
            context.AdditionalResponseParameters.Add(property.Key, property.Value);
        }

        return Task.FromResult<object>(null);
    }
}

注意:AuthDBContext 与您声明 OnModelCreating 方法的类相同。

因此,查看上面的代码,您将检查用户角色是否已插入到 AuthenticationProperties 字典中

{
    "roles",String.Join(",", (IEnumerable<IdentityUserRole>) user.Roles.ToArray())
}

然后将它们与当前用户的 ClaimsIdentity 对象一起插入到工单中。

AuthenticationTicket ticket = new AuthenticationTicket(identity, properties);

一旦您解决了这个问题,您只需在您的操作和/或控制器中添加 [Authorize] 属性,如下所示:

[Authorize(Roles = "Admin")]

或者签入你的控制器动作等价物:

ActionContext.RequestContext.Principal.IsInRole("Admin")

【讨论】:

  • 我没有使用OAuthAuthorizationServerOptions
  • @gldraphael 为什么不呢?您需要添加 app.UseOAuthAuthorizationServer(OAuthAuthorizationServerOptions);到“将 OAuth2 授权服务器功能添加到您的 OWIN Web 应用程序。此中间件执行 OAuth2 规范定义的授权和令牌端点的请求处理”。否则,执行 [Authorize] 属性的 User.IsInRole 将不起作用。
  • 嗯,我会试试这个并回复你
猜你喜欢
  • 1970-01-01
  • 2014-11-21
  • 2014-08-17
  • 1970-01-01
  • 2015-07-30
  • 2020-02-07
  • 1970-01-01
  • 2013-03-12
  • 1970-01-01
相关资源
最近更新 更多