Asp.NET Core 3 - Azure Active Directory - Ошибка проверки токена - Ошибка проверки подписи. Невозможно сопоставить ключ

мы используем Azure Active Directory для нашей компании. У нас есть внутренний веб-проект с Asp.Net Core 3. Мы используем React в качестве интерфейса. Пользователь может войти в систему со своими учетными данными AAD, и приложение React получит токен. Токен следует использовать для доступа к функциям в проекте ASP.Net Core. Следовательно, токен должен быть проверен в ASP.Net Core. Вот моя проблема. Мне удалось вызвать проверку токена, но я получаю разные ошибки.

Приложение ASP.Net: https://localhost:44350/

Приложение React: https://localhost:44395/

Это одно из действий ASP:

[HttpGet]
[Route("GetArticles")]
public async Task<JsonResult> GetArticles()
{
    if (!Request.Headers.TryGetValue("Authorization", out var authorizationToken))
    {
        return Json(Unauthorized());
    }

    if (!authorizationToken.Any())
    {
        return Json(Unauthorized());
    }
    
    var jwt = await Validate(authorizationToken.First());

    return Json(await _unitOfWork.ArticlesRepos.GetAllAsync());
}

Токен передан, и запускается проверка. Проверка выполняется в методе Validate:

public async Task<JwtSecurityToken> Validate(string token)
{
    string tenant = _configuration.GetValue<string>("Tenant");
    string publicKey = _configuration.GetValue<string>("AadPubKey");
    //string stsDiscoveryEndpoint = $"https://login.microsoftonline.com/common/v2.0/.well-known/openid-configuration";
    //string stsDiscoveryEndpoint = $"https://login.microsoftonline.com/{tenant}/oauth2/v2.0/token";
    string stsDiscoveryEndpoint = $"https://login.microsoftonline.com/{tenant}/v2.0/.well-known/openid-configuration";
    
    ConfigurationManager<OpenIdConnectConfiguration> configManager = new ConfigurationManager<OpenIdConnectConfiguration>(stsDiscoveryEndpoint, new OpenIdConnectConfigurationRetriever());

    OpenIdConnectConfiguration config = await configManager.GetConfigurationAsync();
    var IssuerSigningKeys = config.SigningKeys;

    var x = new X509Certificate2(Encoding.ASCII.GetBytes(publicKey));
    var y = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(publicKey));
    var rsa = new RSACryptoServiceProvider();
    string exponentvalue = "AQAB";
    var e = Base64UrlEncoder.DecodeBytes(exponentvalue);
    var N = publicKey;
    var modulus = Base64UrlEncoder.DecodeBytes(N);
    rsa.ImportParameters(
        new RSAParameters()
        {
                Modulus = modulus,
                Exponent = e
    });
    var signingKey = new RsaSecurityKey(rsa);

    TokenValidationParameters validationParameters = new TokenValidationParameters
    {
        ValidateAudience = false,
        ValidateIssuer = true,
        ValidIssuer = stsDiscoveryEndpoint,
        //ValidIssuer = "https://localhost:44350/",
        //ValidAudience = "https://localhost:44395/",
        ValidateIssuerSigningKey = true,
        IssuerSigningKey = signingKey,
        ValidateLifetime = false
    };

    JwtSecurityTokenHandler tokendHandler = new JwtSecurityTokenHandler();

    var result = tokendHandler.ValidateToken(token, validationParameters, out SecurityToken jwt);

    return jwt as JwtSecurityToken;
}

Как видите, мы пробовали разные вещи. Мы получаем следующие ошибки в строке с

var result = tokendHandler.ValidateToken(token, validationParameters, out SecurityToken jwt);:

Когда мы используем IssuerSigningKey = y, = ›

Microsoft.IdentityModel.Tokens.SecurityTokenSignatureKeyNotFoundException HResult = 0x80131500 Сообщение = IDX10501: Ошибка проверки подписи. Невозможно сопоставить ключ: kid: 'someId'. Обнаружены исключения: 'System.NotSupportedException: IDX10634: невозможно создать SignatureProvider. Алгоритм: 'RS256', SecurityKey: 'Microsoft.IdentityModel.Tokens.SymmetricSecurityKey, KeyId:' ', InternalId:' '.' не поддерживается

Когда мы используем IssuerSigningKey = signingKey, = ›

Microsoft.IdentityModel.Tokens.SecurityTokenSignatureKeyNotFoundException HResult = 0x80131500 Сообщение = IDX10501: Ошибка проверки подписи. Невозможно сопоставить ключ: kid: 'someId'. Пойманные исключения: ''.

Я понятия не имею, как настроить TokenValidationParameters. Когда я смотрю на https://login.microsoftonline.com/%7Btenant%7D/discovery/v2.0/keys Я вижу ключ, указанный в исключении. Но информации много.

{"keys":
[{"kty":"RSA"
,"use":"sig"
,"kid":"someId"
,"x5t":"someId"
,"n":"longString"
,"e":"AQAB"
,"x5c":["otherLongString"]
,"issuer":"https://login.microsoftonline.com/myTenant/v2.0"},
{...},{...}]

Как мы можем заставить валидацию работать?

заранее спасибо


person Sebastian Siemens    schedule 24.07.2020    source источник


Ответы (1)


Получение ошибки IDX10634 из алгоритма RS256 с использованием SymmetricSecurityKey похоже на поведение, которое было исправлено в новых версиях IdentityModel. Какую версию сборок IdentityModel вы используете? Попробуйте выполнить обновление до последней версии (в настоящее время 6.7.1) и посмотрите, сохраняется ли проблема.

В качестве нескольких примечаний:

JwtSecurityTokenHandler / TokenValidationParameters предназначены для долгоживущих объектов. Например, TokenValidationParameters имеет кеш, который можно использовать при повторном использовании.

Это приложение для СПА? Если да, то этот образец должен быть полезен:

https://github.com/Azure-Samples/ms-identity-javascript-react-spa-dotnetcore-webapi-obo

person keegan    schedule 06.08.2020