使用Identity Server 3的多个客户端的一个用户的多个角色

时间:2018-04-11 02:02:40

标签: c# authentication openid identityserver3

我正在尝试使用Identity Server 3创建身份验证服务器。到目前为止,我能够使用数据库来验证用户,获取声明并获取范围并为客户端生成id_token。 只是为了减少我要用InMemoryUse显示代码的行数,这是我的代码

范围类:

var scopes = new List<IdentityServer3.Core.Models.Scope>
        {
            //For Identity Scopes
            StandardScopes.OpenId, 
            StandardScopes.Profile, 
            StandardScopes.Roles,  
            StandardScopes.Address, 
            StandardScopes.Phone 
};
return scopes

我只是试图只获得带有角色的身份范围,就是这样。

客户类:

new Client()
        {
            ClientId = "mvcClient",
            ClientName = "MVC Client",                    
            AllowedGrantTypes = GrantTypes.Implicit,
            RequireConsent = false;
            RedirectUris = { ..something.. },
            PostLogoutRedirectUris = { ..something.. },
            AllowedScopes =
            {
                StandardScopes.OpenId.Name,
                StandardScopes.Profile.Name,
                StandardScopes.OfflineAccess.Name,
                StandardScopes.Roles.Name,
            }
        }

现在,这是我的用户类

new InMemoryUser
            {
               Username="Admin",
               Password="test123",
               Subject="1",
               Claims= new[]
               {
                   new Claim(Constants.ClaimTypes.GivenName, "Sam"),
                   new Claim(Constants.ClaimTypes.FamilyName, "Morgan"),
                   new Claim(Constants.ClaimTypes.Role, "Admin"),
               }
            }

这是客户端应用程序的启动类

           app.UseOpenIdConnectAuthentication(new OpenIdConnectAuthenticationOptions
        {
            Authority = "https://localhost:44328/identity",
            ClientId = "mvcClient",
            Scope = "openid profile roles address phone",
            ResponseType = "id_token",
            SignInAsAuthenticationType = "Cookies",

            UseTokenLifetime = false,
            Notifications = new OpenIdConnectAuthenticationNotifications
            {
                SecurityTokenValidated = n =>
                {
                    var id = n.AuthenticationTicket.Identity;

                    // we want to keep first name, last name, subject and roles
                    var givenName = id.FindFirst(Constants.ClaimTypes.GivenName);
                    //.. Same for Other Fields

                    // create new identity and set name and role claim type
                    var claimIdentity = new ClaimsIdentity(
                        id.AuthenticationType,
                        Constants.ClaimTypes.GivenName,
                        Constants.ClaimTypes.Role);

                    claimIdentity.AddClaim(givenName);
                    claimIdentity.AddClaims(roles);
                    claimIdentity.AddClaims(scopes);


                    n.AuthenticationTicket = new AuthenticationTicket(
                        claimIdentity,
                        n.AuthenticationTicket.Properties);

                    return Task.FromResult(0);
                }
            }
        });

现在我的问题是,我对多个客户端采用了类似的方法,当我从ClientA请求身份验证时,它为我提供了有关用户的正确信息。但是当开始ClientB时,好的是它不会要求授权,但它给了我ClientA的相同角色。这意味着如果User1ClientA的管理员,那么它会显示ClientB的管理员,User1ClientB的测试人员。

感谢您的任何帮助,谢谢

1 个答案:

答案 0 :(得分:0)

有一些方法

  • 每个客户端的前缀角色名称。在这种情况下,它可以是ClientA的ClientA_Admin和clientB的ClientB_Admin
  • 在客户端应用程序数据库中存储角色信息。意味着,ClientA的db拥有角色表。 ClientB的db拥有另一个。在startup.cs你有Idtoken =&gt; UserId =&gt;角色=&gt; Initialize ClaimIdentity包括您从客户端应用程序数据库加载的角色

如果您拥有所有客户的某些角色=&gt;将其存储在身份服务器db中。如果客户具有某些客户特定角色=&gt;将这些角色存储在客户端db

上述两个在大多数情况下都足够好