85 lines
2.9 KiB
C#
85 lines
2.9 KiB
C#
using FluentAssertions;
|
|
using MiningService.API.Application.Commands;
|
|
using MiningService.Domain.AggregatesModel.MinerAggregate;
|
|
using MiningService.Domain.Exceptions;
|
|
using MiningService.Domain.SeedWork;
|
|
using NSubstitute;
|
|
using Xunit;
|
|
|
|
namespace MiningService.UnitTests.Application.Commands;
|
|
|
|
/// <summary>
|
|
/// EN: Unit tests for ClaimMiningRewardCommandHandler.
|
|
/// VI: Unit tests cho ClaimMiningRewardCommandHandler.
|
|
/// </summary>
|
|
public class ClaimMiningRewardCommandHandlerTests
|
|
{
|
|
private readonly IMinerRepository _minerRepository;
|
|
private readonly IUnitOfWork _unitOfWork;
|
|
private readonly ClaimMiningRewardCommandHandler _handler;
|
|
|
|
public ClaimMiningRewardCommandHandlerTests()
|
|
{
|
|
_unitOfWork = Substitute.For<IUnitOfWork>();
|
|
_minerRepository = Substitute.For<IMinerRepository>();
|
|
_minerRepository.UnitOfWork.Returns(_unitOfWork);
|
|
_handler = new ClaimMiningRewardCommandHandler(_minerRepository);
|
|
}
|
|
|
|
[Fact]
|
|
public async Task Handle_ReadySession_ReturnsReward()
|
|
{
|
|
// Arrange
|
|
var userId = Guid.NewGuid();
|
|
var miner = Miner.Create(userId);
|
|
miner.StartMiningSession(configBaseRate: 0.25m, sessionHours: 0); // Immediate claim
|
|
var command = new ClaimMiningRewardCommand(userId);
|
|
|
|
_minerRepository.GetByUserIdAsync(userId, Arg.Any<CancellationToken>())
|
|
.Returns(miner);
|
|
_minerRepository.UnitOfWork.SaveEntitiesAsync(Arg.Any<CancellationToken>())
|
|
.Returns(true);
|
|
|
|
// Act
|
|
var result = await _handler.Handle(command, CancellationToken.None);
|
|
|
|
// Assert
|
|
result.Should().NotBeNull();
|
|
result.PointsEarned.Should().BeGreaterThanOrEqualTo(0);
|
|
result.TotalPoints.Should().BeGreaterThanOrEqualTo(0);
|
|
|
|
await _minerRepository.Received(1).UnitOfWork.SaveEntitiesAsync(Arg.Any<CancellationToken>());
|
|
}
|
|
|
|
[Fact]
|
|
public async Task Handle_MinerNotFound_ThrowsNotFoundException()
|
|
{
|
|
// Arrange
|
|
var userId = Guid.NewGuid();
|
|
var command = new ClaimMiningRewardCommand(userId);
|
|
|
|
_minerRepository.GetByUserIdAsync(userId, Arg.Any<CancellationToken>())
|
|
.Returns((Miner?)null);
|
|
|
|
// Act & Assert
|
|
await Assert.ThrowsAsync<MinerNotFoundException>(() =>
|
|
_handler.Handle(command, CancellationToken.None));
|
|
}
|
|
|
|
[Fact]
|
|
public async Task Handle_NoActiveSession_ThrowsDomainException()
|
|
{
|
|
// Arrange
|
|
var userId = Guid.NewGuid();
|
|
var miner = Miner.Create(userId); // No session started
|
|
var command = new ClaimMiningRewardCommand(userId);
|
|
|
|
_minerRepository.GetByUserIdAsync(userId, Arg.Any<CancellationToken>())
|
|
.Returns(miner);
|
|
|
|
// Act & Assert
|
|
await Assert.ThrowsAsync<MiningDomainException>(() =>
|
|
_handler.Handle(command, CancellationToken.None));
|
|
}
|
|
}
|