Кэширование publi c ключей аутентификации JWT в Azure Функция - PullRequest
0 голосов
/ 31 января 2020

У меня есть функция Azure. NET ядро ​​2.1 с различными конечными точками.

Для аутентификации у меня есть внешний поставщик безопасности, откуда мне нужно получить документ обнаружения (метаданные) до возможности проверки токена запроса.

Документ в настоящее время загружается каждый раз, когда делается один запрос:

var discoveryDocument = await configurationManager.GetConfigurationAsync();

Теперь я, естественно, не хочу делать этот вызов для каждый запрос в связи с тем, что документ изменяется редко.

С другой стороны, Azure функции не сохраняют состояния. Я слышал, что ConfigurationManager.GetConfigurationAsync() как-то кеширует извлеченные данные, хотя я не мог найти больше информации об этом. В настоящее время у меня появилась функция, которая запускается при запуске, извлекает документ и сохраняет его в локальной файловой системе. Поэтому, когда сделан запрос, я снова читаю файл, чтобы избежать повторного запроса на получение ключей publi c.

Есть ли какие-либо проблемы с этим?

Решение:

Я мог бы решить это с помощью класса c, как предложил @juunas. Для каждой функции я повторно использую метод ValidateToken(). Вызов документа обнаружения выполняется время от времени (когда IConfigurationManager считает, что его необходимо обновить), поскольку он автоматически кэшируется.

class AuthConfig
{
    static readonly IConfigurationManager<OpenIdConnectConfiguration> _configurationManager;

    static AuthConfig()
    {
        _configurationManager = new ConfigurationManager<OpenIdConnectConfiguration>(
            "<CONFIGURL>",
            new OpenIdConnectConfigurationRetriever(),
            new HttpDocumentRetriever());
    }

    public static async Task<MyUserEntity> ValidateToken(string token)
    {
        var discoveryDocument = await _configurationManager.GetConfigurationAsync(CancellationToken.None);

        var validationParameters = new TokenValidationParameters
        {
            RequireExpirationTime = true,
            RequireSignedTokens = true,
            ValidateIssuerSigningKey = true,
            IssuerSigningKeys = discoveryDocument.SigningKeys,
            ValidateLifetime = true,
            ValidateAudience = false,
            ValidateIssuer = true,
            ValidIssuer = discoveryDocument.Issuer
        };

        try
        {
            var claimsPrincipal = new JwtSecurityTokenHandler().ValidateToken(token, validationParameters, out var rawValidatedToken);
            var user = ParseMyUserEntity(claimsPrincipal);
            return user;
        }
        catch
        {
            return null;
        }
    }
}

1 Ответ

1 голос
/ 31 января 2020

Вы можете сохранить данные в поле stati c (которое также может быть в отдельном классе stati c).

Это должно работать как кэш в памяти в этом экземпляре функции в наименее. Если функция масштабируется до нескольких экземпляров, их кэши будут разделены.

...