feat: 重构 RBAC1 角色权限模型

This commit is contained in:
2025-12-02 16:21:46 +08:00
parent 3d69151426
commit b459c7edbe
21 changed files with 780 additions and 49 deletions

View File

@@ -1,8 +1,6 @@
using System.Linq;
using Microsoft.EntityFrameworkCore;
using Microsoft.EntityFrameworkCore.ChangeTracking;
using Microsoft.EntityFrameworkCore.Metadata.Builders;
using Microsoft.EntityFrameworkCore.Storage.ValueConversion;
using TakeoutSaaS.Domain.Identity.Entities;
using TakeoutSaaS.Infrastructure.Common.Persistence;
using TakeoutSaaS.Shared.Abstractions.Ids;
@@ -31,6 +29,26 @@ public sealed class IdentityDbContext(
/// </summary>
public DbSet<MiniUser> MiniUsers => Set<MiniUser>();
/// <summary>
/// 角色集合。
/// </summary>
public DbSet<Role> Roles => Set<Role>();
/// <summary>
/// 权限集合。
/// </summary>
public DbSet<Permission> Permissions => Set<Permission>();
/// <summary>
/// 用户-角色关系。
/// </summary>
public DbSet<UserRole> UserRoles => Set<UserRole>();
/// <summary>
/// 角色-权限关系。
/// </summary>
public DbSet<RolePermission> RolePermissions => Set<RolePermission>();
/// <summary>
/// 配置实体模型。
/// </summary>
@@ -40,6 +58,10 @@ public sealed class IdentityDbContext(
base.OnModelCreating(modelBuilder);
ConfigureIdentityUser(modelBuilder.Entity<IdentityUser>());
ConfigureMiniUser(modelBuilder.Entity<MiniUser>());
ConfigureRole(modelBuilder.Entity<Role>());
ConfigurePermission(modelBuilder.Entity<Permission>());
ConfigureUserRole(modelBuilder.Entity<UserRole>());
ConfigureRolePermission(modelBuilder.Entity<RolePermission>());
ApplyTenantQueryFilters(modelBuilder);
}
@@ -59,23 +81,6 @@ public sealed class IdentityDbContext(
ConfigureAuditableEntity(builder);
ConfigureSoftDeleteEntity(builder);
var converter = new ValueConverter<string[], string>(
v => string.Join(',', v),
v => string.IsNullOrWhiteSpace(v) ? Array.Empty<string>() : v.Split(',', StringSplitOptions.RemoveEmptyEntries));
var comparer = new ValueComparer<string[]>(
(l, r) => (l == null && r == null) || (l != null && r != null && Enumerable.SequenceEqual(l, r)),
v => v.Aggregate(0, (current, item) => HashCode.Combine(current, item.GetHashCode())),
v => v.ToArray());
builder.Property(x => x.Roles)
.HasConversion(converter)
.Metadata.SetValueComparer(comparer);
builder.Property(x => x.Permissions)
.HasConversion(converter)
.Metadata.SetValueComparer(comparer);
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.Account }).IsUnique();
}
@@ -99,4 +104,58 @@ public sealed class IdentityDbContext(
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.OpenId }).IsUnique();
}
private static void ConfigureRole(EntityTypeBuilder<Role> builder)
{
builder.ToTable("roles");
builder.HasKey(x => x.Id);
builder.Property(x => x.TenantId).IsRequired();
builder.Property(x => x.Name).HasMaxLength(64).IsRequired();
builder.Property(x => x.Code).HasMaxLength(64).IsRequired();
builder.Property(x => x.Description).HasMaxLength(256);
ConfigureAuditableEntity(builder);
ConfigureSoftDeleteEntity(builder);
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.Code }).IsUnique();
}
private static void ConfigurePermission(EntityTypeBuilder<Permission> builder)
{
builder.ToTable("permissions");
builder.HasKey(x => x.Id);
builder.Property(x => x.TenantId).IsRequired();
builder.Property(x => x.Name).HasMaxLength(64).IsRequired();
builder.Property(x => x.Code).HasMaxLength(128).IsRequired();
builder.Property(x => x.Description).HasMaxLength(256);
ConfigureAuditableEntity(builder);
ConfigureSoftDeleteEntity(builder);
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.Code }).IsUnique();
}
private static void ConfigureUserRole(EntityTypeBuilder<UserRole> builder)
{
builder.ToTable("user_roles");
builder.HasKey(x => x.Id);
builder.Property(x => x.TenantId).IsRequired();
builder.Property(x => x.UserId).IsRequired();
builder.Property(x => x.RoleId).IsRequired();
ConfigureAuditableEntity(builder);
ConfigureSoftDeleteEntity(builder);
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.UserId, x.RoleId }).IsUnique();
}
private static void ConfigureRolePermission(EntityTypeBuilder<RolePermission> builder)
{
builder.ToTable("role_permissions");
builder.HasKey(x => x.Id);
builder.Property(x => x.TenantId).IsRequired();
builder.Property(x => x.RoleId).IsRequired();
builder.Property(x => x.PermissionId).IsRequired();
ConfigureAuditableEntity(builder);
ConfigureSoftDeleteEntity(builder);
builder.HasIndex(x => x.TenantId);
builder.HasIndex(x => new { x.TenantId, x.RoleId, x.PermissionId }).IsUnique();
}
}