Files
tiku-backend.net/Tiku.IntegrationTests/Bootstrap/BuiltinBackofficeCatalogSeederTests.cs

150 lines
6.9 KiB
C#

using Microsoft.EntityFrameworkCore;
using Tiku.Application.Security;
using Tiku.Domain.Operations;
using Tiku.Domain.Platform;
using Tiku.Domain.Tenancy;
using Tiku.Infrastructure.Bootstrap;
using Tiku.Infrastructure.Persistence;
using Tiku.IntegrationTests.Infrastructure;
namespace Tiku.IntegrationTests.Bootstrap;
public sealed class BuiltinBackofficeCatalogSeederTests
{
[Fact]
public async Task Seed_populates_complete_catalog_and_is_idempotent()
{
using var database = PostgresTestDatabase.Create();
await using var dbContext = CreateDbContext(database.ConnectionString);
var seeder = new BuiltinBackofficeCatalogSeeder(dbContext);
await seeder.SeedAsync();
dbContext.ChangeTracker.Clear();
await seeder.SeedAsync();
Assert.Equal(15, await dbContext.SaasFeatures.CountAsync());
Assert.Equal(27, await dbContext.PermissionModules.CountAsync());
Assert.Equal(37, await dbContext.BackendPermissions.CountAsync());
Assert.Equal(21, await dbContext.BackendMenus.CountAsync());
Assert.Equal(15, await dbContext.SaasFeatures.Select(item => item.Code).Distinct().CountAsync());
Assert.Equal(27, await dbContext.PermissionModules.Select(item => item.Code).Distinct().CountAsync());
Assert.Equal(37, await dbContext.BackendPermissions.Select(item => item.Code).Distinct().CountAsync());
Assert.Equal(21, await dbContext.BackendMenus.Select(item => item.Code).Distinct().CountAsync());
Assert.True(await dbContext.PermissionModules.AnyAsync(item => item.Code == "platform_operations"));
Assert.True(await dbContext.BackendPermissions.AnyAsync(item =>
item.Code == BackendPermissions.PlatformOperationsView &&
item.PermissionModuleCode == "platform_operations"));
Assert.True(await dbContext.BackendPermissions.AnyAsync(item =>
item.Code == BackendPermissions.PlatformOperationsManage &&
item.PermissionModuleCode == "platform_operations"));
}
[Fact]
public async Task Seed_preserves_existing_values_and_fills_partial_catalog()
{
using var database = PostgresTestDatabase.Create();
await using var dbContext = CreateDbContext(database.ConnectionString);
dbContext.SaasFeatures.Add(new SaasFeature
{
Code = SaasFeatureCatalog.CoreBackoffice,
Name = "Custom feature name",
Category = "custom",
IsCore = true,
Status = SaasFeatureStatus.Active
});
dbContext.PermissionModules.Add(new PermissionModule
{
Code = "tenant_dashboard",
Name = "Custom module name",
Area = BackendPermissionArea.Tenant
});
dbContext.BackendPermissions.Add(new BackendPermission
{
Code = BackendPermissions.TenantDashboardView,
Name = "Custom permission name",
Area = BackendPermissionArea.Tenant,
PermissionModuleCode = "tenant_dashboard",
IsSystem = true
});
dbContext.BackendMenus.Add(new BackendMenu
{
Code = "tenant.dashboard",
Title = "Custom menu title",
Area = BackendPermissionArea.Tenant,
Path = "/custom-dashboard",
PermissionCode = BackendPermissions.TenantDashboardView,
IsActive = true
});
await dbContext.SaveChangesAsync();
dbContext.ChangeTracker.Clear();
await new BuiltinBackofficeCatalogSeeder(dbContext).SeedAsync();
Assert.Equal("Custom feature name", (await dbContext.SaasFeatures.SingleAsync(
item => item.Code == SaasFeatureCatalog.CoreBackoffice)).Name);
Assert.Equal("Custom module name", (await dbContext.PermissionModules.SingleAsync(
item => item.Code == "tenant_dashboard")).Name);
Assert.Equal("Custom permission name", (await dbContext.BackendPermissions.SingleAsync(
item => item.Code == BackendPermissions.TenantDashboardView)).Name);
Assert.Equal("Custom menu title", (await dbContext.BackendMenus.SingleAsync(
item => item.Code == "tenant.dashboard")).Title);
Assert.Equal(15, await dbContext.SaasFeatures.CountAsync());
Assert.Equal(27, await dbContext.PermissionModules.CountAsync());
Assert.Equal(37, await dbContext.BackendPermissions.CountAsync());
Assert.Equal(21, await dbContext.BackendMenus.CountAsync());
Assert.False(await dbContext.PermissionModules.AnyAsync(module =>
module.RequiredFeatureCode != null &&
!dbContext.SaasFeatures.Any(feature => feature.Code == module.RequiredFeatureCode)));
Assert.False(await dbContext.BackendPermissions.AnyAsync(permission =>
!dbContext.PermissionModules.Any(module => module.Code == permission.PermissionModuleCode)));
Assert.False(await dbContext.BackendMenus.AnyAsync(menu =>
menu.PermissionCode != null &&
!dbContext.BackendPermissions.Any(permission => permission.Code == menu.PermissionCode)));
}
[Fact]
public async Task Seed_backfills_new_permissions_for_existing_system_super_admin()
{
using var database = PostgresTestDatabase.Create();
await using var dbContext = CreateDbContext(database.ConnectionString);
var seeder = new BuiltinBackofficeCatalogSeeder(dbContext);
await seeder.SeedAsync();
var role = new PlatformBackendRole
{
Code = PlatformAdminBootstrapper.SuperAdminRoleCode,
Name = "超级管理员",
Status = BackendRoleStatus.Active,
IsSystem = true
};
dbContext.PlatformBackendRoles.Add(role);
dbContext.PlatformBackendRolePermissions.Add(new PlatformBackendRolePermission
{
RoleId = role.Id,
PermissionCode = BackendPermissions.PlatformDashboardView
});
await dbContext.SaveChangesAsync();
dbContext.ChangeTracker.Clear();
await seeder.SeedAsync();
dbContext.ChangeTracker.Clear();
await seeder.SeedAsync();
var permissionCodes = await dbContext.PlatformBackendRolePermissions.AsNoTracking()
.Where(binding => binding.RoleId == role.Id)
.Select(binding => binding.PermissionCode)
.ToArrayAsync();
Assert.Equal(BackendPermissions.Platform.Count, permissionCodes.Length);
Assert.Contains(BackendPermissions.PlatformQuestionBankManage, permissionCodes);
Assert.Equal(BackendPermissions.Platform.Count, permissionCodes.Distinct(StringComparer.Ordinal).Count());
}
private static TikuDbContext CreateDbContext(string connectionString)
{
var options = new DbContextOptionsBuilder<TikuDbContext>()
.UseNpgsql(connectionString, npgsql =>
npgsql.MigrationsAssembly(typeof(TikuDbContext).Assembly.FullName))
.Options;
return new TikuDbContext(options);
}
}