You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何修改.NET 8 Identity Bearer Token的各项属性?

在.NET 8 Identity中配置令牌与刷新令牌的核心参数

一、配置JWT令牌的基础参数(过期时间、颁发者、受众)

在Program.cs中配置JWT验证规则,同时在生成令牌时指定核心参数:

1. 配置验证规则

builder.Services.AddAuthentication(JwtBearerDefaults.AuthenticationScheme)
    .AddJwtBearer(options =>
    {
        options.TokenValidationParameters = new TokenValidationParameters
        {
            // 设置合法颁发者
            ValidIssuer = builder.Configuration["Jwt:Issuer"],
            // 设置合法受众
            ValidAudience = builder.Configuration["Jwt:Audience"],
            // 签名密钥(需与生成令牌时一致)
            IssuerSigningKey = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(builder.Configuration["Jwt:Key"])),
            // 启用过期验证
            ValidateLifetime = true,
            // 关闭时钟偏差(严格验证过期时间)
            ClockSkew = TimeSpan.Zero
        };
    });

2. 生成令牌时指定参数

在登录接口中创建JWT令牌,直接定义过期时间、颁发者和受众:

// 构造用户声明列表
var claims = new List<Claim>
{
    new Claim(ClaimTypes.Name, user.UserName),
    new Claim(ClaimTypes.Email, user.Email)
};

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

// 创建JWT令牌
var jwtToken = new JwtSecurityToken(
    issuer: _configuration["Jwt:Issuer"],
    audience: _configuration["Jwt:Audience"],
    claims: claims,
    expires: DateTime.UtcNow.AddMinutes(30), // 设置30分钟过期
    signingCredentials: signingCreds);

// 转换为字符串令牌
var tokenString = new JwtSecurityTokenHandler().WriteToken(jwtToken);

二、自定义刷新令牌的过期与管理

.NET 8 Identity未内置刷新令牌功能,需自行实现存储与验证:

1. 创建刷新令牌实体

public class RefreshToken
{
    public int Id { get; set; }
    public string UserId { get; set; }
    public string Token { get; set; }
    public DateTime Expires { get; set; } // 刷新令牌过期时间
    public bool IsRevoked { get; set; }
    public DateTime Created { get; set; } = DateTime.UtcNow;
}

2. 生成与存储刷新令牌

登录成功后生成刷新令牌并保存到数据库:

var refreshToken = new RefreshToken
{
    UserId = user.Id,
    Token = Guid.NewGuid().ToString(),
    Expires = DateTime.UtcNow.AddDays(7), // 设置7天过期
    IsRevoked = false
};

_context.RefreshTokens.Add(refreshToken);
await _context.SaveChangesAsync();

3. 刷新令牌验证逻辑

在刷新接口中验证令牌有效性,若未过期则生成新的访问令牌:

var storedToken = await _context.RefreshTokens.FirstOrDefaultAsync(t => t.Token == refreshToken && !t.IsRevoked);
if (storedToken == null || storedToken.Expires <= DateTime.UtcNow)
{
    return Unauthorized("刷新令牌无效或已过期");
}

// 生成新的访问令牌(逻辑同登录时的令牌生成)
// ...

// 可选:生成新的刷新令牌并替换旧令牌
storedToken.Token = Guid.NewGuid().ToString();
storedToken.Expires = DateTime.UtcNow.AddDays(7);
await _context.SaveChangesAsync();

三、修改令牌中的关联声明属性

声明属性可通过两种方式配置:临时声明(仅当前令牌有效)和持久化声明(存储在用户表中)。

1. 添加/修改临时声明

在生成令牌时直接构造声明列表:

var claims = new List<Claim>
{
    // 替换默认名称声明为全名
    new Claim(ClaimTypes.Name, $"{user.FirstName} {user.LastName}"),
    // 添加自定义声明
    new Claim("UserId", user.Id.ToString()),
    new Claim("IsEmailVerified", user.EmailConfirmed.ToString()),
    new Claim("Role", "Editor")
};

2. 添加/修改持久化声明

通过UserManager给用户添加持久化声明,后续生成令牌时可直接读取:

// 给用户添加持久化声明
await _userManager.AddClaimAsync(user, new Claim("PreferredLanguage", "zh-CN"));

// 生成令牌时读取用户的持久化声明
var userClaims = await _userManager.GetClaimsAsync(user);
var claims = new List<Claim>(userClaims)
{
    new Claim(ClaimTypes.Name, user.UserName)
};

四、查看令牌内容

使用JwtSecurityTokenHandler解析令牌,提取所有参数和声明:

public IActionResult InspectToken(string token)
{
    var handler = new JwtSecurityTokenHandler();
    if (!handler.CanReadToken(token))
    {
        return BadRequest("无效的JWT令牌");
    }

    var jwtToken = handler.ReadJwtToken(token);
    return Ok(new
    {
        Issuer = jwtToken.Issuer,
        Audience = jwtToken.Audiences.FirstOrDefault(),
        ExpiresAt = jwtToken.ValidTo,
        Claims = jwtToken.Claims.Select(c => new { Type = c.Type, Value = c.Value })
    });
}

内容的提问来源于stack exchange,提问作者Josh

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.02 04:43:33