/// <summary> /// 自定义 客户端存储 /// </summary> public class CustomerClientStore : IClientStore { private readonly List<Client> Clients = new List<Client> { new Client { ClientId = "client1" , // 没有交互性用户,使用 clientid/secret 实现认证。 AllowedGrantTypes = GrantTypes.ClientCredentials, // 用于认证的密码 ClientSecrets = { new Secret( "secret" .Sha256()) }, // 客户端有权访问的范围(Scopes) AllowedScopes = { "api1" } }, new Client { ClientId = "client2" , // 用户名 密码 模式 AllowedGrantTypes = GrantTypes.ResourceOwnerPassword, // 用于认证的密码 ClientSecrets = { new Secret( "secret" .Sha256()) }, // 客户端有权访问的范围(Scopes) AllowedScopes = { "api1" } }, new Client { ClientId = "client3" , // 授权码 模式 AllowedGrantTypes = GrantTypes.Code, RedirectUris = { "http://localhost:5001/test/index" }, // 是否需要确认授权,这个配置我们会在后面介绍,这里设置为 false RequireConsent = false , // 这个参数必须设置 为 false RequirePkce = false , // 用于认证的密码 ClientSecrets = { new Secret( "secret" .Sha256()) }, // 客户端有权访问的范围(Scopes) AllowedScopes = { "api1" , IdentityServerConstants.StandardScopes.OpenId, IdentityServerConstants.StandardScopes.Profile } }, new Client { ClientId = "client4" , // 授权码 模式 AllowedGrantTypes = GrantTypes.Implicit, RedirectUris = { "http://localhost:5001/test/index" }, // 认证成功后允许的回调地址 // 是否需要确认授权,这个配置我们会在后面介绍,这里设置为 false RequireConsent = false , // 用于认证的密码 ClientSecrets = { new Secret( "secret" .Sha256()) }, //AlwaysIncludeUserClaimsInIdToken=true, //允许token通过浏览器 (必须 true) AllowAccessTokensViaBrowser = true , // 客户端有权访问的范围(Scopes) AllowedScopes = { "api1" , IdentityServerConstants.StandardScopes.OpenId, IdentityServerConstants.StandardScopes.Profile } } }; public async Task<Client> FindClientByIdAsync( string clientId) { // TODO: 这里可以从数据库或其他持久化设备获取 Client return Clients.FirstOrDefault(t => t.ClientId == clientId); } } |