using FluentAssertions;
using Monitoring.Application.Reports.Handlers;
using Monitoring.Application.Reports.Queries;
using Monitoring.Domain.Entities.ExternalSystem;
using Monitoring.Domain.Entities.SyncedRecord;
using Monitoring.Domain.Enums;
using Monitoring.Domain.Values;
namespace BuildFlow.Monitoring.Tests.Reports;
/// 订单同步记录分页查询测试。
public class GetOrderRecordsQueryHandlerTests
{
[Fact]
public async Task Handle_ShouldFilterOrdersBySystemAndReturnNewestPage()
{
await using var db = MonitoringTestDb.Create();
var system = CreateSystem("u号租-A");
var otherSystem = CreateSystem("u号租-B");
db.ExternalSystems.AddRange(system, otherSystem);
db.SyncedRecords.AddRange(
CreateRecord(system.Id, "order-1", "order", new DateTime(2026, 7, 17, 1, 0, 0, DateTimeKind.Utc)),
CreateRecord(system.Id, "order-2", "order", new DateTime(2026, 7, 18, 1, 0, 0, DateTimeKind.Utc)),
CreateRecord(system.Id, "order-3", "order", new DateTime(2026, 7, 19, 1, 0, 0, DateTimeKind.Utc)),
CreateRecord(system.Id, "metric-1", "metric", new DateTime(2026, 7, 20, 1, 0, 0, DateTimeKind.Utc)),
CreateRecord(otherSystem.Id, "other-order", "order", new DateTime(2026, 7, 21, 1, 0, 0, DateTimeKind.Utc)));
await db.SaveChangesAsync();
var handler = new GetOrderRecordsQueryHandler(db);
var result = await handler.Handle(new GetOrderRecordsQuery(system.Id, 1, 2), default);
result.Total.Should().Be(3);
result.PageIndex.Should().Be(1);
result.PageSize.Should().Be(2);
result.Items.Select(item => item.ExternalId).Should().Equal("order-3", "order-2");
result.Items.Should().OnlyContain(item => item.ExternalSystemId == system.Id);
result.Items[0].Payload["status"].Should().NotBeNull();
result.Items[0].Payload["status"]!.ToString().Should().Be("running");
}
[Fact]
public async Task Handle_ShouldUseStableIdOrderingWhenOrderTimesMatch()
{
await using var db = MonitoringTestDb.Create();
var system = CreateSystem("u号租-A");
var occurredAt = new DateTime(2026, 7, 19, 1, 0, 0, DateTimeKind.Utc);
var lowId = Guid.Parse("00000000-0000-0000-0000-000000000001");
var middleId = Guid.Parse("00000000-0000-0000-0000-000000000002");
var highId = Guid.Parse("00000000-0000-0000-0000-000000000003");
db.ExternalSystems.Add(system);
db.SyncedRecords.AddRange(
CreateRecord(system.Id, "order-low", "order", occurredAt, lowId),
CreateRecord(system.Id, "order-high", "order", occurredAt, highId),
CreateRecord(system.Id, "order-middle", "order", occurredAt, middleId));
await db.SaveChangesAsync();
var handler = new GetOrderRecordsQueryHandler(db);
var firstPage = await handler.Handle(new GetOrderRecordsQuery(system.Id, 1, 2), default);
var secondPage = await handler.Handle(new GetOrderRecordsQuery(system.Id, 2, 2), default);
firstPage.Items.Select(item => item.Id).Should().Equal(highId, middleId);
secondPage.Items.Select(item => item.Id).Should().Equal(lowId);
}
private static ExternalSystemEntity CreateSystem(string name) => new()
{
Data = new SystemData
{
Name = name,
SystemType = ExternalSystemTypeEnum.UHaoZu,
BaseUrl = "https://b.uhaozu.com",
IsEnabled = true,
},
};
private static SyncedRecordEntity CreateRecord(
Guid systemId,
string externalId,
string recordType,
DateTime occurredAt,
Guid? id = null) => new()
{
Id = id ?? Guid.NewGuid(),
ExternalSystemId = systemId,
SyncJobId = Guid.NewGuid(),
ExternalId = externalId,
RecordType = recordType,
OccurredAt = occurredAt,
UpdatedAt = occurredAt,
Data = new RecordData
{
ExternalId = externalId,
RecordType = recordType,
Payload = new Dictionary
{
["status"] = "running",
["actualRent"] = "12.34",
},
},
};
}