Skip to content
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
using AngleSharp.Dom;
using Bunit;
using EstateManagementUI.BlazorServer.Components.Pages.Contracts;
using EstateManagementUI.BlazorServer.Components.Permissions;
Expand Down Expand Up @@ -79,4 +80,244 @@ public void ContractsView_HasCorrectPageTitle()
var pageTitle = cut.FindComponent<Microsoft.AspNetCore.Components.Web.PageTitle>();
pageTitle.Instance.ChildContent.ShouldNotBeNull();
}

[Fact]
public void ContractsView_HasBackButton()
{
// Arrange
var contractId = Guid.NewGuid();
var contract = new ContractModel
{
ContractId = contractId,
Description = "Test Contract",
OperatorName = "Test Operator"
};

_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success(contract));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Back to List");
}

[Fact]
public void ContractsView_BackButton_NavigatesToContractsList()
{
// Arrange
var contractId = Guid.NewGuid();
var contract = new ContractModel
{
ContractId = contractId,
Description = "Test Contract",
OperatorName = "Test Operator"
};

_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success(contract));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Find and click the Back to List button
IRefreshableElementCollection<IElement> buttons = cut.FindAll("button");
IElement? backButton = buttons.FirstOrDefault(b => b.TextContent.Contains("Back to List"));
backButton.ShouldNotBeNull();
backButton.Click();

// Assert
_fakeNavigationManager.Uri.ShouldContain("/contracts");
}

[Fact]
public void ContractsView_DisplaysProducts_WhenPresent()
{
// Arrange
var contractId = Guid.NewGuid();
var contract = new ContractModel
{
ContractId = contractId,
Description = "Test Contract",
OperatorName = "Test Operator",
Products = new List<ContractProductModel>
{
new ContractProductModel
{
ContractProductId = Guid.NewGuid(),
ProductName = "Test Product",
DisplayText = "Test Display",
ProductType = "MobileTopup",
Value = "100",
NumberOfFees = 2
}
}
};

_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success(contract));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Test Product");
cut.Markup.ShouldContain("Test Display");
cut.Markup.ShouldContain("100");
}

[Fact]
public void ContractsView_DisplaysNoProducts_WhenEmpty()
{
// Arrange
var contractId = Guid.NewGuid();
var contract = new ContractModel
{
ContractId = contractId,
Description = "Test Contract",
OperatorName = "Test Operator",
Products = new List<ContractProductModel>()
};

_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success(contract));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("No products added to this contract yet");
}

[Fact]
public void ContractsView_DisplaysTransactionFees_WhenPresent()
{
// Arrange
var contractId = Guid.NewGuid();
var contract = new ContractModel
{
ContractId = contractId,
Description = "Test Contract",
OperatorName = "Test Operator",
Products = new List<ContractProductModel>
{
new ContractProductModel
{
ContractProductId = Guid.NewGuid(),
ProductName = "Test Product",
DisplayText = "Test Display",
ProductType = "MobileTopup",
Value = "100",
NumberOfFees = 1,
TransactionFees = new List<ContractProductTransactionFeeModel>
{
new ContractProductTransactionFeeModel
{
TransactionFeeId = Guid.NewGuid(),
Description = "Service Fee",
CalculationType = 0,
FeeType = 0,
Value = 10.50m
}
}
}
}
};

_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success(contract));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Transaction Fees");
cut.Markup.ShouldContain("Service Fee");
cut.Markup.ShouldContain("10.50");
}

[Fact]
public void ContractsView_LoadContract_QueryFails_ShowsNotFoundMessage()
{
// Arrange
var contractId = Guid.NewGuid();
_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Failure("Failed to load contract"));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Contract not found");
}

[Fact]
public void ContractsView_LoadContract_ReturnsNull_ShowsNotFoundMessage()
{
// Arrange
var contractId = Guid.NewGuid();
_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success<ContractModel>(null!));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Contract not found");
}

[Fact]
public void ContractsView_ContractNotFound_HasBackButton()
{
// Arrange
var contractId = Guid.NewGuid();
_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success<ContractModel>(null!));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Assert
cut.Markup.ShouldContain("Back to List");
}

[Fact]
public void ContractsView_ContractNotFound_BackButton_NavigatesToContractsList()
{
// Arrange
var contractId = Guid.NewGuid();
_mockMediator.Setup(x => x.Send(It.IsAny<ContractQueries.GetContractQuery>(), default))
.ReturnsAsync(Result.Success<ContractModel>(null!));

// Act
var cut = RenderComponent<View>(parameters => parameters
.Add(p => p.ContractId, contractId));
cut.WaitForState(() => !cut.Markup.Contains("animate-spin"), TimeSpan.FromSeconds(5));

// Find and click the Back to List button
IRefreshableElementCollection<IElement> buttons = cut.FindAll("button");
IElement? backButton = buttons.FirstOrDefault(b => b.TextContent.Contains("Back to List"));
backButton.ShouldNotBeNull();
backButton.Click();

// Assert
_fakeNavigationManager.Uri.ShouldContain("/contracts");
}
}
Loading