using Domain.Exceptions; using Features.Auth.Dtos; using Features.Auth.Identity; using Features.Auth.Services; using MediatR; using Microsoft.AspNetCore.Identity; namespace Features.Auth.Commands.Login; /// /// Handles by verifying credentials via /// and issuing access/refresh tokens. /// public class LoginHandler(UserManager userManager, ITokenService tokenService) : IRequestHandler { /// /// Thrown when the username does not match any account or the supplied password does not match /// the stored hash. /// public async Task Handle( LoginCommand request, CancellationToken cancellationToken ) { ApplicationUser user = await userManager.FindByNameAsync(request.Username) ?? throw new UnauthorizedException("Invalid username or password."); if (!await userManager.CheckPasswordAsync(user, request.Password)) throw new UnauthorizedException("Invalid username or password."); string accessToken = tokenService.GenerateAccessToken(user.Id, user.UserName); string refreshToken = tokenService.GenerateRefreshToken(user.Id, user.UserName); return new LoginPayload(user.Id, user.UserName, refreshToken, accessToken); } }