如何在ASP.NET Core中将角色添加到Windows身份验证

Ant*_*hik 7 c# roles windows-authentication asp.net-core-mvc asp.net-core

我在visual studio 2015中使用windows身份验证创建了一个asp.net核心项目.我无法弄清楚如何向Identity添加角色.

我有一个带有Windows帐户用户名的表.当用户打开网站时,用户被添加到身份(我假设发生了什么,因为我可以通过User.Identity.Name显示用户名),我想从另一个表中提取角色并将其分配给用户, 这可能吗?或许还有更好的方法吗?(为什么?,怎么样?)

我找不到任何与Windows身份验证相关的示例,但我已经阅读了文档并阅读了本指南.我仍然被困住了.

blo*_*art 10

使用Windows身份验证时,角色来自Active Directory,而不是数据库.

您可以使用声明转换来更改每个请求的入站标识,以从数据库中提取额外的角色.

public class ClaimsTransformer : IClaimsTransformer
{
    public Task<ClaimsPrincipal> TransformAsync(ClaimsPrincipal principal)
    {
        ((ClaimsIdentity)principal.Identity).AddClaim(
            new Claim("ExampleClaim", "true"));
        return Task.FromResult(principal);
    }
}
Run Code Online (Sandbox Code Playgroud)

然后将其连接起来

app.UseClaimsTransformation(new ClaimsTransformationOptions
{
    Transformer = new ClaimsTransformer()
});
Run Code Online (Sandbox Code Playgroud)

请注意,在当前的版本中,没有DI支持,因此您必须手动从DI中提取数据库信息(如果它就在那里).

  • @blowdart在.netcore 2.0中有效吗?我没有找到UseClaimsTransformation. (3认同)

Sim*_*ice 9

这是我用来检查用户是否在角色 \ 组中的工作代码,请在闲暇时使用

using System.Collections.Generic;
using System.DirectoryServices.AccountManagement;
using System.Linq;
using System.Security.Principal;

namespace Santander.IsUserInGroupOrRole_cs
{

public class IsUserInRole
{
    public static bool IsInGroup(string groupName)
    {
        var myIdentity = GetUserIdWithDomain();
        var myPrincipal = new WindowsPrincipal(myIdentity);
        return myPrincipal.IsInRole(groupName);
    }

    public bool IsInGroup(List<string> groupNames)
    {
        var myIdentity = GetUserIdWithDomain();
        var myPrincipal = new WindowsPrincipal(myIdentity);

        return groupNames.Any(group => myPrincipal.IsInRole(group));
    }

    public static WindowsIdentity GetUserIdWithDomain()
    {
        var myIdentity = WindowsIdentity.GetCurrent();
        return myIdentity;
    }

    public static string GetUserId()
    {
        var id = GetUserIdWithDomain().Name.Split('\\');
        return id[1];
    }

    public static string GetUserDisplayName()
    {
        var id = GetUserIdWithDomain().Name.Split('\\');

        var dc = new PrincipalContext(ContextType.Domain, id[0]);
        var adUser = UserPrincipal.FindByIdentity(dc, id[1]);
        return adUser.DisplayName;

    }
}
}
Run Code Online (Sandbox Code Playgroud)

  • 如果您可以加入我昨天晚上 20:00 发送的聊天链接,那么是的,我可以向您详细说明 (3认同)

Dan*_*anO 6

对于任何感兴趣的人,这里有一个简单的示例,说明如何将 EF DBContext 注入自定义 ClaimsTransformer 并添加一些自定义角色声明。

启动.cs

public void ConfigureServices(IServiceCollection services)
{
  services.AddScoped<IClaimsTransformer, MyClaimsTransformer>();

  services.AddMvc();

  services.AddDbContext<MyDbContext>(options => options.UseSqlServer(
      Configuration.GetConnectionString("MyConnStringSetting")
    ));

  (...)
}

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory)
{
  app.UseClaimsTransformation(context =>
  {
    var transformer = context.Context.RequestServices.GetRequiredService<IClaimsTransformer>();
    return transformer.TransformAsync(context);
  });

  (...)
}
Run Code Online (Sandbox Code Playgroud)

MyClaimsTransformer.cs

public class MyClaimsTransformer : IClaimsTransformer
{
  private readonly MyDbContext _context;

  public MyClaimsTransformer(MyDbContext context)
  {
    _context = context;
  }

  public Task<ClaimsPrincipal> TransformAsync(ClaimsTransformationContext context)
  {
    var identity = (ClaimsIdentity)context.Principal.Identity;
    var userName = identity.Name;
    var roles = _context.Role.Where(r => r.UserRole.Any(u => u.User.Username == userName)).Select(r => r.Name);
    foreach (var role in roles)
    {
      var claim = new Claim(ClaimTypes.Role, role);
      identity.AddClaim(claim);
    }
    return Task.FromResult(context.Principal);
  }
}
Run Code Online (Sandbox Code Playgroud)

  • 现在类型已更改为 IClaimsTransformation。 (2认同)