Home About Skills Products
Work
Projects Services Experience
Learn
Tutorials Courses Blogs Resources
Contact
Blog · .NET

ASP.NET Core Web API Authentication with JWT

ASP.NET Core Web API Authentication with JWT
Advertisement

JWT (JSON Web Token) authentication is the standard choice for a stateless ASP.NET Core API consumed by a separate frontend or mobile app. Here's a complete, working setup.

Installing the Packages

dotnet add package Microsoft.AspNetCore.Authentication.JwtBearer

Configuring the Authentication Middleware

builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
    .AddJwtBearer(options =>
    {
        options.TokenValidationParameters = new TokenValidationParameters
        {
            ValidateIssuer = true,
            ValidateAudience = true,
            ValidateLifetime = true,
            ValidateIssuerSigningKey = true,
            ValidIssuer = config["Jwt:Issuer"],
            ValidAudience = config["Jwt:Audience"],
            IssuerSigningKey = new SymmetricSecurityKey(
                Encoding.UTF8.GetBytes(config["Jwt:Key"])),
        };
    });

app.UseAuthentication();
app.UseAuthorization();

Issuing a Token on Login

app.MapPost("/login", (LoginDto dto, IConfiguration config) =>
{
    // Verify credentials against your database here first
    var claims = new[] { new Claim(ClaimTypes.Name, dto.Email) };

    var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(config["Jwt:Key"]));
    var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);

    var token = new JwtSecurityToken(
        issuer: config["Jwt:Issuer"],
        audience: config["Jwt:Audience"],
        claims: claims,
        expires: DateTime.UtcNow.AddHours(2),
        signingCredentials: creds);

    return Results.Ok(new { token = new JwtSecurityTokenHandler().WriteToken(token) });
});

Protecting Endpoints

app.MapGet("/posts", () => posts)
   .RequireAuthorization();

Any request without a valid Authorization: Bearer {token} header now gets an automatic 401 — no manual token-checking code needed in the handler itself.

Role-Based Authorization

app.MapDelete("/posts/{id}", (int id) => { /* ... */ })
   .RequireAuthorization(policy => policy.RequireRole("Admin"));

Keeping Secrets Out of Source Control

The signing key belongs in appsettings.Development.json locally (git-ignored) and in environment variables or a secrets manager in production — never committed alongside your code. A leaked signing key means anyone can forge a valid token for any user.

Building Your First REST API with ASP.NET Core

Building Your First REST API with ASP.NET Core

Minimal APIs, Entity Framework Core, and FluentValidation — a real, working ASP.NET Core API without controller-class ceremony.

Entity Framework Core Migrations: A Practical Guide

Creating, applying, and safely rolling back EF Core migrations — the .NET equivalent of Laravel migrations, and where the workflow differs.

Clean Architecture in ASP.NET Core

Clean Architecture in ASP.NET Core

Structuring an ASP.NET Core app so business logic has zero dependency on frameworks or databases — Domain, Application, Infrastructure, and Web layers.

Advertisement
Esc