ПО промежуточного слоя для проверки подлинности ASP.NET Core 2.0

89

В Core 1.1 последовал совету @ blowdart и реализовал специальное промежуточное ПО:

https://stackoverflow.com/a/31465227/29821

Это работало так:

  1. Промежуточное ПО запущено. Подобрал токен из заголовков запросов.
  2. Проверял токен и, если он действителен, создал удостоверение (ClaimsIdentity), содержащее несколько утверждений, которые затем добавлялись через HttpContext.User.AddIdentity ();
  3. В ConfigureServices using services.AddAuthorization я добавил политику, требующую утверждения, предоставляемого промежуточным программным обеспечением.
  4. Затем в контроллерах / действиях я бы использовал [Authorize (Roles = "некоторая роль, добавленная промежуточным программным обеспечением")]

Это в некоторой степени работает с 2.0, за исключением того, что если токен недействителен (шаг 2 выше) и утверждение никогда не добавляется, я получаю «No authenticationScheme не указан, и DefaultChallengeScheme не найден».

Итак, теперь я читаю, что авторизация изменилась в 2.0:

https://docs.microsoft.com/en-us/aspnet/core/migration/1x-to-2x/identity-2x

Какой правильный путь для меня сделать то же самое в ASP.NET Core 2.0? Я не вижу примера действительно настраиваемой аутентификации.

pbz
источник
Попробуйте эту ссылку, хотя в ней говорится о двух схемах, но она не даст вам знать
Митхун Паттанкар,
не могли бы вы добавить свой код, чтобы мы могли посмотреть? Я знаю, что у меня были проблемы с JWT в core2.0 - это был случай, когда его переставляли при запуске
Webezine 01

Ответы:

195

Итак, после долгого дня попыток решить эту проблему, я, наконец, понял, как Microsoft хочет, чтобы мы создавали собственные обработчики аутентификации для их новой установки с одним промежуточным ПО в ядре 2.0.

Просмотрев некоторую документацию в MSDN, я нашел класс, AuthenticationHandler<TOption>который реализует IAuthenticationHandlerинтерфейс.

Оттуда я нашел всю кодовую базу с существующими схемами аутентификации, расположенную по адресу https://github.com/aspnet/Security.

Внутри одного из них показано, как Microsoft реализует схему аутентификации JwtBearer. ( https://github.com/aspnet/Security/tree/master/src/Microsoft.AspNetCore.Authentication.JwtBearer )

Я скопировал большую часть этого кода в новую папку и удалил все, что связано с этим JwtBearer.

В JwtBearerHandlerклассе (который расширяется AuthenticationHandler<>) есть переопределение дляTask<AuthenticateResult> HandleAuthenticateAsync()

Я добавил в наше старое промежуточное программное обеспечение для настройки утверждений через пользовательский сервер токенов, и по-прежнему сталкивался с некоторыми проблемами с разрешениями, просто выплевывая 200 OKвместо a, 401 Unauthorizedкогда токен был недействительным и не было настроено никаких требований.

Я понял, что переопределил, Task HandleChallengeAsync(AuthenticationProperties properties)что по какой-то причине используется для установки разрешений [Authorize(Roles="")]в контроллере.

После удаления этого переопределения код 401заработал и успешно выдал ошибку, когда разрешения не совпадают.

Главный вывод из этого заключается в том, что теперь вы не можете использовать настраиваемое промежуточное программное обеспечение, вы должны реализовать его через, AuthenticationHandler<>и вы должны установить DefaultAuthenticateSchemeи DefaultChallengeSchemeпри использовании services.AddAuthentication(...).

Вот пример того, как все это должно выглядеть:

В Startup.cs / ConfigureServices () добавьте:

services.AddAuthentication(options =>
{
    // the scheme name has to match the value we're going to use in AuthenticationBuilder.AddScheme(...)
    options.DefaultAuthenticateScheme = "Custom Scheme";
    options.DefaultChallengeScheme = "Custom Scheme";
})
.AddCustomAuth(o => { });

В Startup.cs / Configure () добавьте:

app.UseAuthentication();

Создайте новый файл CustomAuthExtensions.cs

public static class CustomAuthExtensions
{
    public static AuthenticationBuilder AddCustomAuth(this AuthenticationBuilder builder, Action<CustomAuthOptions> configureOptions)
    {
        return builder.AddScheme<CustomAuthOptions, CustomAuthHandler>("Custom Scheme", "Custom Auth", configureOptions);
    }
}

Создайте новый файл CustomAuthOptions.cs

public class CustomAuthOptions: AuthenticationSchemeOptions
{
    public CustomAuthOptions()
    {

    }
}

Создайте новый файл CustomAuthHandler.cs

internal class CustomAuthHandler : AuthenticationHandler<CustomAuthOptions>
{
    public CustomAuthHandler(IOptionsMonitor<CustomAuthOptions> options, ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock) : base(options, logger, encoder, clock)
    {
        // store custom services here...
    }
    protected override async Task<AuthenticateResult> HandleAuthenticateAsync()
    {
        // build the claims and put them in "Context"; you need to import the Microsoft.AspNetCore.Authentication package
        return AuthenticateResult.NoResult();
    }
}
Зак
источник
1
отличный пост, но у меня проблемы с компиляцией вашего кода. Типы CustomAuthOptions и AuthenticateResult отсутствуют. Не могли бы вы их опубликовать?
Alexb
8
Готовы ли вы поделиться своими выводами в виде кода в репозитории Github?
CSharper
2
Не могли бы вы объяснить DefaultAuthenticateSchemeи DefaultChallengeScheme? Не понимаю, зачем они оба используются? и в чём разница между ними.
Мохаммед
11
+1 за «Отсюда я нашел всю кодовую базу с существующими схемами аутентификации, расположенную на github.com/aspnet/Security ». Просто посмотрите, как это делает команда ASP.NET, пока вы будете следовать этому (действительно отличному) ответу. Кто-нибудь из нас когда-нибудь думал, что однажды мы будем задавать вопросы о коде и методах работы MS, и ответ будет: «просто взгляните на их кодовую базу»?
Marc L.
3
Для других, которые придут позже, вы AuthExtensionдолжны находиться внутри Microsoft.Extensions.DependencyInjectionпространства имен. См. Этот пример: github.com/aspnet/Security/blob/rel/2.0.0/src/…
Гарри Полли,
4

Как указано в статье, на которую вы ссылаетесь, в Identity произошли значительные изменения с Core 1.x на Core 2.0. Основное изменение заключается в отказе от подхода промежуточного программного обеспечения и использовании внедрения зависимостей для настройки настраиваемых служб. Это обеспечивает большую гибкость в настройке Identity для более сложных реализаций. Итак, вы хотите отказаться от подхода промежуточного программного обеспечения, о котором вы упомянули выше, и перейти к услугам. Для достижения этой цели выполните действия по миграции, описанные в указанной статье. Начните с замены app.UseIdentity на app.UseAuthentication . UseIdentity устарела и не будет поддерживаться в будущих версиях. Полный пример того, как вставить настраиваемое преобразование утверждений и выполнить авторизацию для утверждения.просмотреть это сообщение в блоге .

Кевин Юнгханс
источник
12
Есть ли пример того, как использовать это с приложением WebAPI?
Alexb