Tak więc, po długim dniu prób rozwiązania tego problemu, w końcu zrozumiałem, w jaki sposób firma Microsoft chce, abyśmy stworzyli niestandardowe programy obsługi uwierzytelniania dla ich nowej konfiguracji pojedynczego oprogramowania pośredniego w rdzeniu 2.0.
Po przejrzeniu części dokumentacji na MSDN znalazłem klasę o nazwie, AuthenticationHandler<TOption>
która implementuje IAuthenticationHandler
interfejs.
Stamtąd znalazłem całą bazę kodów z istniejącymi schematami uwierzytelniania znajdującymi się pod adresem https://github.com/aspnet/Security
Wewnątrz jednego z nich pokazuje, jak firma Microsoft implementuje schemat uwierzytelniania JwtBearer. ( https://github.com/aspnet/Security/tree/master/src/Microsoft.AspNetCore.Authentication.JwtBearer )
Skopiowałem większość tego kodu do nowego folderu i wyczyściłem wszystkie rzeczy związane JwtBearer
.
W JwtBearerHandler
klasie (która rozszerza AuthenticationHandler<>
) istnieje przesłonięcie dlaTask<AuthenticateResult> HandleAuthenticateAsync()
Dodałem nasze stare oprogramowanie pośredniczące do konfigurowania roszczeń za pośrednictwem niestandardowego serwera tokenów i nadal napotykałem pewne problemy z uprawnieniami, po prostu wypluwając 200 OK
zamiast a, 401 Unauthorized
gdy token był nieprawidłowy i nie skonfigurowano żadnych roszczeń.
Zdałem sobie sprawę, że nadpisałem, Task HandleChallengeAsync(AuthenticationProperties properties)
który z jakiegokolwiek powodu jest używany do ustawiania uprawnień za pośrednictwem [Authorize(Roles="")]
kontrolera.
Po usunięciu tego zastąpienia kod działał i pomyślnie wyrzucił komunikat, 401
gdy uprawnienia nie pasowały.
Głównym wnioskiem jest to, że teraz nie możesz używać niestandardowego oprogramowania pośredniego, musisz go zaimplementować za pośrednictwem AuthenticationHandler<>
i musisz ustawić DefaultAuthenticateScheme
i DefaultChallengeScheme
podczas używania services.AddAuthentication(...)
.
Oto przykład tego, jak to wszystko powinno wyglądać:
W Startup.cs / ConfigureServices () dodaj:
services.AddAuthentication(options =>
{
options.DefaultAuthenticateScheme = "Custom Scheme";
options.DefaultChallengeScheme = "Custom Scheme";
})
.AddCustomAuth(o => { });
W Startup.cs / Configure () dodaj:
app.UseAuthentication();
Utwórz nowy plik 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);
}
}
Utwórz nowy plik CustomAuthOptions.cs
public class CustomAuthOptions: AuthenticationSchemeOptions
{
public CustomAuthOptions()
{
}
}
Utwórz nowy plik CustomAuthHandler.cs
internal class CustomAuthHandler : AuthenticationHandler<CustomAuthOptions>
{
public CustomAuthHandler(IOptionsMonitor<CustomAuthOptions> options, ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock) : base(options, logger, encoder, clock)
{
}
protected override async Task<AuthenticateResult> HandleAuthenticateAsync()
{
return AuthenticateResult.NoResult();
}
}