53 lines
2.5 KiB
C#
53 lines
2.5 KiB
C#
using MediatR;
|
|
using Microsoft.AspNetCore.Http;
|
|
using Modules.User.Application.Errors;
|
|
using Modules.User.Application.Gateways;
|
|
using Modules.User.Application.Models;
|
|
|
|
namespace Modules.User.Application.Commands;
|
|
|
|
public class RefreshTokensCommand : IRequest<AuthenticationResult?>
|
|
{
|
|
public string? Ip { get; set; }
|
|
public HttpResponse Response { get; set; } = default!;
|
|
public string? CookiePath { get; set; }
|
|
}
|
|
|
|
public class RefreshTokensCommandHandler(UserContext userContext, IUserRepository userRepository, IAccountAccessQueries accessQueries,
|
|
IUnitOfWork unitOfWork) : IRequestHandler<RefreshTokensCommand, AuthenticationResult?>
|
|
{
|
|
public async Task<AuthenticationResult?> Handle(RefreshTokensCommand request, CancellationToken cancellationToken)
|
|
{
|
|
var accountId = userContext.GetAccountId();
|
|
if (!accountId.HasValue) return null;
|
|
var oldRefreshToken = userContext.GetRefreshToken();
|
|
|
|
var user = await userRepository.GetByAccountIdAsync(accountId.Value, cancellationToken)
|
|
?? throw new AccountException();
|
|
|
|
var now = DateTime.UtcNow;
|
|
var status = user.Account.GetBanStatus(now);
|
|
if (status.IsBanned) throw new AccountBannedException(status.ReleaseDate);
|
|
|
|
var jwtSettings = userContext.GetJwtSettings();
|
|
|
|
var userAgent = userContext.GetUserAgent();
|
|
var location = await userContext.GetLocation(request.Ip);
|
|
var newRefreshToken = TokenGenerator.GenerateRefreshToken();
|
|
var expiresAt = now.Add(jwtSettings.RefreshTokenExpireTime);
|
|
var clientInfo = Domain.Entities.User.ClientInfo.Create(userAgent, location?.Country, location?.Region);
|
|
|
|
var session = user.AddOrUpdateSession(oldRefreshToken, newRefreshToken, expiresAt, clientInfo);
|
|
await userRepository.SaveAsync(user, cancellationToken);
|
|
await unitOfWork.SaveChangesAsync(cancellationToken);
|
|
|
|
var roleNames = await accessQueries.GetRoleNamesAsync(user.Account.Id, cancellationToken);
|
|
var permissionNames = await accessQueries.GetPermissionNamesAsync(user.Account.Id, cancellationToken);
|
|
var permissionCodes = await accessQueries.GetEffectivePermissionCodesAsync(user.Account.Id, cancellationToken);
|
|
|
|
var newAccessToken = TokenGenerator.GenerateAccessToken(user, session, jwtSettings,
|
|
roleNames, permissionNames, permissionCodes);
|
|
|
|
return new AuthenticationResult { AccessToken = newAccessToken, SessionExpireDate = session.ExpiredDateUtc, };
|
|
}
|
|
} |