1

I would like to combine a blazor server app with a minimal api as additional option for users to access data.

The blazor app uses windows authentication:

builder.Services.AddAuthentication(NegotiateDefaults.AuthenticationScheme)
   .AddNegotiate();

builder.Services.AddAuthorization(options =>
{
    options.FallbackPolicy = options.DefaultPolicy;
});

I would like to secure some endpoints of the minimal api with basic authentication. Some should be freely accessible.

How can I configure authentication for the minimal-api separatly from the blazor-app?

1 Answer 1

1

How can I configure authentication for the minimal-api separatly from the blazor-app?

In order to achieve that, you need have its own distinct authentication scheme and middleware configuration which could authenticate the request while hit the minimal API endpoint.

For instance, apart from your blazor authentication, you would write a sperate auth reuqest handlder which would check for the request endpoint and header for minimal API.

Let have a look in practice how we could impplement that:

Seperate Auth Handler:

public class BasicAuthenticationHandler : AuthenticationHandler<AuthenticationSchemeOptions>
{
    public BasicAuthenticationHandler(IOptionsMonitor<AuthenticationSchemeOptions> options,
        ILoggerFactory logger, UrlEncoder encoder, ISystemClock clock)
        : base(options, logger, encoder, clock)
    {
    }

    protected override Task<AuthenticateResult> HandleAuthenticateAsync()
    {
        if (!Request.Headers.ContainsKey("Authorization"))
        {
            
            return Task.FromResult(AuthenticateResult.Fail("Missing Authorization Header"));
        }

        var authHeader = AuthenticationHeaderValue.Parse(Request.Headers["Authorization"]);
        var credentialBytes = Convert.FromBase64String(authHeader.Parameter);
        var credentials = Encoding.UTF8.GetString(credentialBytes).Split(new[] { ':' }, 2);
        var username = credentials[0];
        var password = credentials[1];

        // Validate the credentials here (e.g., against a database or hardcoded values)
        if (username == "testuser" && password == "testpassword")
        {
            var claims = new[] { new Claim(ClaimTypes.Name, username) };
            var identity = new ClaimsIdentity(claims, Scheme.Name);
            var principal = new ClaimsPrincipal(identity);
            var ticket = new AuthenticationTicket(principal, Scheme.Name);

            return Task.FromResult(AuthenticateResult.Success(ticket));
        }

        return Task.FromResult(AuthenticateResult.Fail("Invalid Username or Password"));
    }
}

Program.cs:

builder.Services.AddRazorComponents()
    .AddServerSideBlazor();
builder.Services.AddAuthentication(NegotiateDefaults.AuthenticationScheme)
    .AddNegotiate();
builder.Services.AddAuthorization(options =>
{
    options.FallbackPolicy = options.DefaultPolicy;
});

builder.Services.AddAuthentication("BasicAuthentication")
    .AddScheme<AuthenticationSchemeOptions, BasicAuthenticationHandler>("BasicAuthentication", null);
builder.Services.AddAuthentication();
builder.Services.AddAuthorization();

var app = builder.Build();


app.UseWhen(context => !context.Request.Path.StartsWithSegments("/api"), appBuilder =>
{
    appBuilder.UseAuthentication(); // Apply authentication for Blazor
    appBuilder.UseAuthorization();
});

// Use authentication and authorization for Minimal API
app.UseWhen(context => context.Request.Path.StartsWithSegments("/api"), appBuilder =>
{
    appBuilder.UseAuthentication(); // Apply authentication for API
    appBuilder.UseAuthorization();
});

app.MapGet("/public", () => "This is a public endpoint");

// Secure endpoint (Basic Authentication required)
app.MapGet("/api/secure", [Authorize(AuthenticationSchemes = "BasicAuthentication")] () => "This is a secure endpoint");


app.Run();

Note: As you can see, then request would consist of API I would check for the authntication. So for the demo purpose I just did this way. You could have your own customized logic.

Output:

enter image description here enter image description here

Note: Please refer to this official document how you can use authentication in minimal API.

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.