使用 ASP.NET Core Web API 实现基于 JWT 令牌的实现

发布:2024-10-30 09:56 阅读:133 点赞:0

一. 创建ASP.NET Core Web API项目

首先,打开Visual Studio并创建一个新的ASP.NET Core Web API项目。选择ASP.NET Core Web API模板,并根据需要配置项目,然后点击创建。

二. 安装所需的NuGet包

为了实现JWT认证,你需要安装Microsoft.AspNetCore.Authentication.JwtBearer NuGet包。可以通过NuGet包管理器进行安装。

三. 在appsettings.json中配置JWT

appsettings.json文件中,添加JWT的相关设置,包括密钥、发行者、受众以及过期时间。

{
  "JwtSettings": {
    "SecretKey""wvFwnwxh7GucmY898kQdKzEU5TjE18SQ",  // 使用强密钥
    "Issuer""yourdomain.com",
    "Audience""yourdomain.com",
    "ExpiryInMinutes"60
  }
}

四. 创建JWT辅助类

创建一个辅助类,用于生成JWT令牌。

public class JwtTokenHelper
{
    private readonly IConfiguration _configuration; // 配置信息接口

    public JwtTokenHelper(IConfiguration configuration// 构造函数,接收配置信息
    {
        _configuration = configuration;
    }

    public string GenerateToken(string username// 生成JWT令牌的方法
    {
        var secretKey = Encoding.ASCII.GetBytes(_configuration["JwtSettings:SecretKey"]); // 获取密钥字节
        var tokenHandler = new JwtSecurityTokenHandler(); // JWT令牌处理器
        var tokenDescriptor = new SecurityTokenDescriptor // 定义令牌描述
        {
            Subject = new ClaimsIdentity(new Claim[] // 令牌主题,包含用户名声明
            {
                new Claim(ClaimTypes.Name, username)
            }),
            Expires = DateTime.UtcNow.AddMinutes(int.Parse(_configuration["JwtSettings:ExpiryInMinutes"])), // 过期时间
            Issuer = _configuration["JwtSettings:Issuer"], // 发行者
            Audience = _configuration["JwtSettings:Audience"], // 受众
            SigningCredentials = new SigningCredentials(new SymmetricSecurityKey(secretKey), SecurityAlgorithms.HmacSha256Signature) // 签名凭证
        };
        var token = tokenHandler.CreateToken(tokenDescriptor); // 创建令牌
        return tokenHandler.WriteToken(token); // 写入令牌字符串
    }
}

五. 在Startup.cs或Program.cs中配置JWT认证

Program.cs文件中,配置JWT认证的服务和中间件管道。

// 添加Swagger文档生成器的相关配置
builder.Services.AddSwaggerGen(c =>
{
    // 添加JWT Bearer定义到Swagger
    c.AddSecurityDefinition("Bearer"new OpenApiSecurityScheme
    {
        Description = "JWT Authorization header using the Bearer scheme. \r\n\r\n " +
                      "Enter 'Bearer' [space] and then your token in the text input below.\r\n\r\n" +
                      "Example: \"Bearer 12345abcdef\"",
        Name = "Authorization",
        In = ParameterLocation.Header,
        Type = SecuritySchemeType.ApiKey,
        Scheme = "Bearer"
    });

    c.AddSecurityRequirement(new OpenApiSecurityRequirement()
    {
        {
            new OpenApiSecurityScheme
            {
                Reference = new OpenApiReference
                {
                    Type = ReferenceType.SecurityScheme,
                    Id = "Bearer"
                },
                Scheme = "oauth2",
                Name = "Bearer",
                In = ParameterLocation.Header
            },
            new List<string>()
        }
    });
});

// 添加认证服务
builder.Services.AddAuthentication(options =>
{
    options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme; // 默认认证方案
    options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme; // 默认挑战方案
})
.AddJwtBearer(options =>
{
    options.TokenValidationParameters = new TokenValidationParameters // 令牌验证参数
    {
        ValidateIssuer = true// 验证发行者
        ValidateAudience = true// 验证受众
        ValidateLifetime = true// 验证生命周期
        ValidateIssuerSigningKey = true// 验证签名密钥
        ValidIssuer = builder.Configuration["JwtSettings:Issuer"], // 有效发行者
        ValidAudience = builder.Configuration["JwtSettings:Audience"], // 有效受众
        IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(builder.Configuration["JwtSettings:SecretKey"])) // 发行者签名密钥
    };
});

六. 配置Swagger以传递JWT令牌

确保项目中安装了Swashbuckle.AspNetCore包,以便在Swagger中传递JWT令牌。

七. 创建登录端点

创建一个控制器中的登录端点,用于发放JWT令牌。

[ApiController]
[Route("api/[controller]")]
public class AuthController : ControllerBase
{
    private readonly JwtTokenHelper _jwtTokenHelper; // JWT辅助类实例

    public AuthController(JwtTokenHelper jwtTokenHelper// 构造函数,接收JWT辅助类实例
    {
        _jwtTokenHelper = jwtTokenHelper;
    }

    [AllowAnonymous// 允许匿名访问
    [HttpPost("login")// POST请求登录端点
    public IActionResult Login([FromBody] LoginModel loginModel// 接收登录模型
    {
        // 这里应该替换为实际的用户验证逻辑
        if (loginModel.Username == "test" && loginModel.Password == "password")
        {
            var token = _jwtTokenHelper.GenerateToken(loginModel.Username); // 生成JWT令牌
            return Ok(new { Token = token }); // 返回令牌
        }
        return Unauthorized(); // 用户名或密码错误时返回未授权状态
    }
}

public class LoginModel // 登录模型类
{
    public string Username { getset; } // 用户名
    public string Password { getset; } // 密码
}

八. 保护路由

通过在控制器上添加[Authorize]属性,可以保护特定的路由。

[Authorize// 需要授权访问
[ApiController]
[Route("[controller]")]
public class WeatherForecastController : ControllerBase
{
    // ... 控制器代码 ...
}

九. 在Postman中测试JWT

  1. 登录:向/api/auth/login发送POST请求,并附上有效的用户名和密码。
  2. 获取令牌:从登录响应中复制JWT令牌。
  3. 访问受保护的资源:访问/API/WeatherForecast端点,并在Authorization头中包含JWT令牌。

十. 总结

通过以上步骤,我们成功地在ASP.NET Core Web API中实现了JWT认证,增强了应用的安全性,并简化了用户的认证流程。