Identity Server 6: проблема в том, как авторизовать API в Asp.net (.Net Framework 4.8)?
Я попробовал этот метод в разделе «Запуск API» ниже и показал мне ошибку, когда я вызываю API через веб-проект MVC. Ошибка: «Код состояния ответа не указывает на успех: 401 (Несанкционировано)».
app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions
{
AuthenticationType = "jwt",
AuthenticationMode = Microsoft.Owin.Security.AuthenticationMode.Active,
TokenValidationParameters = new TokenValidationParameters
{
ValidIssuer = Urls.IdentityServer,
ValidateIssuer = true,
ValidAudience = Urls.IdentityServer + "/resources",
ValidateAudience = true,
ValidateIssuerSigningKey = true,
ValidateLifetime = true,
IssuerSigningKeyResolver = LoadKeys,
NameClaimType = "name",
RoleClaimType = "role",
},
});
Мой метод Keyset при запуске веб-API.
internal static DiscoveryCache _discoveryCache = new DiscoveryCache(Urls.IdentityServer);
private IEnumerable<SecurityKey> LoadKeys(string token, SecurityToken securityToken, string kid, TokenValidationParameters validationParameters)
{
var disco = _discoveryCache.GetAsync().Result;
var keys = disco.KeySet.Keys
.Where(x => x.N != null && x.E != null)
.Select(x =>
{
var rsa = new RSAParameters
{
Exponent = Base64UrlEncoder.DecodeBytes(x.E),
Modulus = Base64UrlEncoder.DecodeBytes(x.N),
};
return new RsaSecurityKey(rsa)
{
KeyId = x.Kid
};
});
return keys;
}
Метод политик/правил в веб-сервере идентификации. это мой метод «публичной задачи GetProfileDataAsync(контекст ProfileDataRequestContext)».
{
var UserName = "";
foreach (var data in context.Subject.Identities)
{
UserName = data.Name;
}
var Roless = _loginValidationService.RoleAsync(UserName).Result;
List<Claim> customClaims = new List<Claim>();
foreach (var item in Roless)
{
var role = new Claim("role", item.Name);
customClaims.Add(role);
}
var RoleClaim = _loginValidationService.ClaimAsync(Roless).Result;
foreach (var claim in RoleClaim)
{
var Roleclaim = new Claim( claim.ClaimType, claim.ClaimValue) ;
customClaims.Add(Roleclaim);
}
var getuser = _applicationDbContext.Users.Where(x => x.UserName.Equals(UserName)).ToList();
foreach (var user in getuser)
{
var Userclaims = _applicationDbContext.UserClaims.Where(x => x.UserId.Equals(user.Id)).ToList();
foreach (var Claim in Userclaims)
{
var role = new Claim(Claim.ClaimType, Claim.ClaimValue);
customClaims.Add(role);
}
}
context.IssuedClaims.AddRange(customClaims);
return Task.CompletedTask;
}`
1 ответ
Хорошо, у меня есть ответ на этот вопрос. KeySet имеет значение null при запуске моего веб-API. Я включил один метод для этого решения. и я решил свою проблему с помощью этого метода. Метод - это...
{
public class OpenIdConnectSigningKeyResolver
{
private readonly OpenIdConnectConfiguration openIdConfig;
public OpenIdConnectSigningKeyResolver(string authority)
{
var cm = new ConfigurationManager<OpenIdConnectConfiguration>($"{authority.TrimEnd('/')}/.well-known/openid-configuration", new OpenIdConnectConfigurationRetriever());
openIdConfig = AsyncHelper.RunSync(async () => await cm.GetConfigurationAsync());
}
public SecurityKey[] GetSigningKey(string kid)
{
return new[] { openIdConfig.JsonWebKeySet.GetSigningKeys().FirstOrDefault(t => t.KeyId == kid) };
}
}
}
И мой запуск веб-API...
public class Startup
{
public void Configuration(IAppBuilder app)
{
var Domain = Urls.IdentityServer;
var KeyResolver = new OpenIdConnectSigningKeyResolver(Domain);
app.UseJwtBearerAuthentication(new JwtBearerAuthenticationOptions
{
AuthenticationType = "jwt",
AuthenticationMode = AuthenticationMode.Active,
TokenValidationParameters = new TokenValidationParameters
{
ValidIssuer = Domain,
ValidAudience = "APICore",
IssuerSigningKeyResolver = (token, securityToken, kid, parameters) => KeyResolver.GetSigningKey(kid)
}
});
HttpConfiguration config = new HttpConfiguration();
config.Routes.MapHttpRoute(
name: "DefaultApi",
routeTemplate: "{controller}/{id}",
defaults: new { id = RouteParameter.Optional });
app.UseWebApi(config);
}
}