63 lines
2.0 KiB
C#
63 lines
2.0 KiB
C#
using System.IdentityModel.Tokens.Jwt;
|
|
using System.Security.Claims;
|
|
using Microsoft.Extensions.Options;
|
|
using Tiku.Application.Auth;
|
|
using Tiku.Application.Security;
|
|
using Tiku.Domain.Tenancy;
|
|
|
|
namespace Tiku.Infrastructure.Auth;
|
|
|
|
public sealed class TokenService(IOptions<JwtOptions> options, IJwtKeyRing keyRing) : ITokenService
|
|
{
|
|
private readonly JwtOptions options = options.Value;
|
|
|
|
public (string Token, DateTimeOffset ExpiresAt) CreateAccessToken(
|
|
Guid userId,
|
|
Guid sessionId,
|
|
string? phone,
|
|
string? email,
|
|
AuthRealm realm,
|
|
Guid? tenantId,
|
|
bool mfaSatisfied)
|
|
{
|
|
var expiresAt = DateTimeOffset.UtcNow.AddMinutes(options.AccessTokenMinutes);
|
|
var claims = new List<Claim>
|
|
{
|
|
new(JwtRegisteredClaimNames.Sub, userId.ToString()),
|
|
new(TikuClaimTypes.SessionId, sessionId.ToString()),
|
|
new(JwtRegisteredClaimNames.Jti, Guid.NewGuid().ToString("N")),
|
|
new(JwtRegisteredClaimNames.Iat, DateTimeOffset.UtcNow.ToUnixTimeSeconds().ToString(), ClaimValueTypes.Integer64),
|
|
new(TikuClaimTypes.Realm, realm.ToString().ToLowerInvariant())
|
|
};
|
|
|
|
if (tenantId.HasValue)
|
|
{
|
|
claims.Add(new Claim(TikuClaimTypes.TenantId, tenantId.Value.ToString()));
|
|
}
|
|
|
|
if (mfaSatisfied)
|
|
{
|
|
claims.Add(new Claim(TikuClaimTypes.Mfa, "mfa"));
|
|
}
|
|
|
|
if (!string.IsNullOrWhiteSpace(phone))
|
|
{
|
|
claims.Add(new Claim(TikuClaimTypes.Phone, phone));
|
|
}
|
|
|
|
if (!string.IsNullOrWhiteSpace(email))
|
|
{
|
|
claims.Add(new Claim(TikuClaimTypes.Email, email));
|
|
}
|
|
|
|
var token = new JwtSecurityToken(
|
|
options.Issuer,
|
|
options.Audience,
|
|
claims,
|
|
expires: expiresAt.UtcDateTime,
|
|
signingCredentials: keyRing.SigningCredentials);
|
|
|
|
return (new JwtSecurityTokenHandler().WriteToken(token), expiresAt);
|
|
}
|
|
}
|