using BuildFlow.Platform.Application.Menus.Commands;
using BuildFlow.Platform.Application.Menus.Handlers;
using BuildFlow.Platform.Domain.Entities;
using BuildFlow.Platform.Infrastructure.Persistence;
using FluentAssertions;
using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.DependencyInjection;
using Xunit;
namespace BuildFlow.Platform.Tests.Menus;
///
/// 菜单管理测试。约束菜单主键使用 int64,并保证拖拽排序按 long Id 落库。
///
public class MenuSortTests
{
[Fact]
public void MenuIdentifier_ShouldUseInt64()
{
typeof(Menu).GetProperty(nameof(Menu.Id))!.PropertyType.Should().Be(typeof(long));
typeof(Menu).GetProperty(nameof(Menu.ParentId))!.PropertyType.Should().Be(typeof(long?));
}
[Fact]
public async Task SortMenusCommand_ShouldUpdateMenusByInt64Ids()
{
await using var db = BuildInMemoryDb();
db.Menus.AddRange(
BuildMenu(1, "root", null, 0),
BuildMenu(2, "child-a", 1, 0),
BuildMenu(3, "child-b", 1, 1));
await db.SaveChangesAsync();
var handler = new SortMenusCommandHandler(db);
var affected = await handler.Handle(
new SortMenusCommand(
[
new MenuSortItem(2, null, 1),
new MenuSortItem(3, null, 0),
]),
CancellationToken.None);
affected.Should().Be(2);
var childA = await db.Menus.SingleAsync(m => m.Id == 2);
var childB = await db.Menus.SingleAsync(m => m.Id == 3);
childA.ParentId.Should().BeNull();
childA.Order.Should().Be(1);
childB.ParentId.Should().BeNull();
childB.Order.Should().Be(0);
}
private static PlatformDbContext BuildInMemoryDb()
{
var services = new ServiceCollection();
services.AddDbContext(o => o.UseInMemoryDatabase($"platform-menu-{Guid.NewGuid()}"));
return services.BuildServiceProvider().GetRequiredService();
}
private static Menu BuildMenu(long id, string code, long? parentId, int order)
=> new()
{
Id = id,
Code = code,
Name = code.Replace(".", "-", StringComparison.Ordinal),
Path = $"/{code}",
ParentId = parentId,
Title = code,
Order = order,
CreatedBy = "test",
CreatedAt = DateTime.UtcNow,
UpdatedBy = "test",
UpdatedAt = DateTime.UtcNow,
OperatorIP = "127.0.0.1",
};
}