gpt4 book ai didi

c# - 实现接口(interface)的实体的通用配置

转载 作者:行者123 更新时间:2023-12-03 22:53:33 29 4
gpt4 key购买 nike

假设我有一些界面,例如:

public interface ISoftDeletable
{
bool IsActive { get; set }
}

我有很多实体实现它:
public class Entity1 : ISoftDeletable
{
public int Id { get; set }
public bool IsActive { get; set; }
}

public class Entity2 : ISoftDeletable
{
public int Id { get; set }
public bool IsActive { get; set; }
}

OnModelCreating :
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.Entity<Entity1>().Property(e => e.IsActive).HasDefaultValue(true);
modelBuilder.Entity<Entity2>().Property(e => e.IsActive).HasDefaultValue(true);
}

有什么方法可以重构这个,所以我可以设置 HasDefaultValue对于所有实现 ISoftDeletable 的实体而不是像上面那样做?

我可能可以使用 IsActive = true 的每个实体的默认构造函数来解决这个特定情况。甚至创建一个基本抽象类,但我不太喜欢它。

类似问题: Ef core fluent api set all column types of interface

有没有更好的办法?

最佳答案

我在这里找到了一些答案:GetEntityTypes: configure entity properties using the generic version of .Property<TEntity> in EF Core

除了上面的评论之外,还有一种方法可以做到这一点,而无需为每个实体调用它。这可能可以重构为 Erndob 在我的问题下的评论中提到的一些扩展方法。

protected override void OnModelCreating(ModelBuilder modelBuilder)
{
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
{
if (typeof(ISoftDeletable).IsAssignableFrom(entityType.ClrType))
{
modelBuilder.Entity(entityType.ClrType).Property<bool>(nameof(ISoftDeletable.IsActive)).HasDefaultValue(true);
}
}
}

解决方法是使用 ModelBuilder.Model.GetEntityTypes()并找到可从 ISoftDeletable 分配的实体类型.

在我看来,这比手动配置甚至创建摘要要好得多 IEntityTypeConfiguration<>类,因为您不必记住全部使用它 ISoftDeletable类。

更干净的外观:
public static class ModelBuilderExtensions
{
public static ModelBuilder EntitiesOfType<T>(this ModelBuilder modelBuilder,
Action<EntityTypeBuilder> buildAction) where T : class
{
return modelBuilder.EntitiesOfType(typeof(T), buildAction);
}

public static ModelBuilder EntitiesOfType(this ModelBuilder modelBuilder, Type type,
Action<EntityTypeBuilder> buildAction)
{
foreach (var entityType in modelBuilder.Model.GetEntityTypes())
if (type.IsAssignableFrom(entityType.ClrType))
buildAction(modelBuilder.Entity(entityType.ClrType));

return modelBuilder;
}
}

OnModelCreating :
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
modelBuilder.EntitiesOfType<ISoftDeletable>(builder =>
{
builder.Property<bool>(nameof(ISoftDeletable.IsActive)).HasDefaultValue(true);

// query filters :)
var param = Expression.Parameter(builder.Metadata.ClrType, "p");
var body = Expression.Equal(Expression.Property(param, nameof(ISoftDeletable.IsActive)), Expression.Constant(true));
builder.HasQueryFilter(Expression.Lambda(body, param));
});
}

关于c# - 实现接口(interface)的实体的通用配置,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/51763168/

29 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com