如何使用具有 entity framework 核心的通用类型?

How can I use a generic type with entity framework core?

如果我有一个看起来像这样的领域模型:

public class Foo<T> {
    public Guid Id { get; set; }
    public string Statement { get; set; }
    public T Value { get; set; }
}

我想将它用于内置数据类型(字符串、整数等...)以及日期。 我想像这样使用它:

var foo = new Foo<string>();
foo.Value = "Hey";

如何使用 EF Core 将其保存到数据库?

我想象数据库 table 看起来像

| Id | Statement | ValueAsString | ValueAsDecimal | ValueAsDate | ValueAsInt | 
| 1  | NULL      | "Hey"         |                |             |            |
| 2  | NULL      |               | 1.1            |             |            |

你应该还有一个 class。你的 class Foo 应该是抽象的。 所以你会得到":

public abstract class Foo<T> {
    public Guid Id { get; set; }
    public string Statement { get; set; }
    public T Value { get; set; }
}

那么您的实施 class 将是:

public class Orders: Foo<Order> {
}

现在您的 Orders class 具有可以存储的通用类型。

如果您想将不同的值类型保存到数据库中,类似于您问题中的 table,您可以这样做:

public interface IHasValue<T> {
    T Value { get; set; }
}

public abstract class Foo {
    public Guid Id { get; set; }
    public string Statement { get; set; }
}

public class Foostring : Foo, IHasValue<string> {
    string Value { get; set; }
}

public class FooInt : Foo, IHasValue<int> {
    int Value { get; set; }
}

在你的 DbContext class 添加属性:

public DbSet<FooString> FooStrings { get; set: }
public DbSet<FooInt> FooInts { get; set; }

您可以在 DbContextOnModelCreating 方法中为 table 设置列名:

protected override void OnModelCreating(ModelBuilder modelBuilder)
{
    // include the base class so a single table is created for the hierarchy
    // rather than a table for each child class
    modelBuilder.Entity<Foo>().ToTable("Foos");

    // Specify the column names or you will get weird names
    modelBuilder.Entity<FooString>().Property(entity => entity.Value)
        .HasColumnName("ValueAsString");
    modelBuilder.Entity<FooInt>().Property(entity => entity.Value)
        .HasColumnName("ValueAsInt");
}

此代码将生成一个 table Foos,其中包含列 IdStatementDiscriminatorValueAsStringValueAsInt.有关 Discrimiator 列的更多信息,请参见 here

您仍然需要为要用于 T 的每个 Type/column 创建一个 class,我认为您无法解决这个问题。