c# - ef-core 加载嵌套 tph 继承成员的集合属性

标签 c# entity-framework linq entity-framework-core tph

给定以下类结构

 public class Parent 
    {
        public Guid Id { get; 
        public List<BaseChild> Children { get; set; }
    }

 public abstract class BaseChild
    {
        public int Id { get; set; }
        public string ChildName { get; set; }
    }

public class NormalChild : BaseChild
    {
         public DateTime BirthDate { get; set; }
    }

public class RichChild : BaseChild
    {
        public List<OffshoreAccount> OffshoreAccounts { get; set; }
    }

public class OffshoreAccount 
    {
        public string AccountNumber { get; set; }
        public AccountInfo AccountInfo { get; set; }
    }

查询父数据以包含有关子离岸账户信息的最佳方法是什么?。我想出了下面的解决方案,使用 ef-core 的显式加载,但感觉不对。有没有更优雅的解决方案?

var parent = Context.Set<Parent>()
    .Where(o => o.Id == Guid.Parse(parentId))
    .Include(o => o.Children)
    .SingleOrDefault();

foreach (var child in parent.Children.OfType<RichChild>())
    {
        Context.Entry<RichChild>(child).Collection(f => f.OffshoreAccounts).Load();
        foreach (var account in child.OffshoreAccounts)
            {
                 Context.Entry<OffshoreAccount>(account).Reference(f => f.AccountInfo).Load();
            }
     }

最佳答案

更新(EF Core 2.1+):

从 v2.1 开始,EF Core 原生支持 Include on derived types通过 C# 强制转换或 as 运算符。

例如

.Include(e => e.Children)
    .ThenInclude(e => ((RichChild)e).OffshoreAccounts)
        .ThenInclude(e => e.AccountInfo)

.Include(e => e.Children)
    .ThenInclude(e => (e as RichChild).OffshoreAccounts)
        .ThenInclude(e => e.AccountInfo)

文档声称 Includestring 重载也可以使用,例如据此

.Include(e => "Children.OffshoreAccounts.AccountInfo")

应该也可以工作,但它没有(检查到 v3.1.4)。

原文:

目前还没有办法在父查询中实现这一点,但是可以通过使用 EntryCollectionQuery 的组合来改进显式加载Include/ThenIncludeLoad 调用:

var parent = Context.Set<Parent>()
    .Where(o => o.Id == Guid.Parse(parentId))
    .Include(o => o.Children)
    .SingleOrDefault();

Context.Entry(parent).Collection(e => e.Children)
    .Query().OfType<RichChild>()
    .Include(e => e.OffshoreAccounts)
        .ThenInclude(e => e.AccountInfo)
    .Load();

关于c# - ef-core 加载嵌套 tph 继承成员的集合属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41637055/

相关文章:

c# - 同一 LINQ 2 SQL 方法中的多个 WHERE

c# - yield return 和 LINQ Select 的不同结果

c# - 如何使用 C# 动态创建对象?

c# - 使用 Entity Framework 返回数据表

c# - 使用 LiNQ 选择 DataTable 并检查是否存在重复行

c# - Entity Framework 数据库提供程序兼容性错误

c# - 使用具有单个 DbContext 和 Entites 的多个数据库并在运行时生成 Conn String

c# - 验证 Windows Phone 应用内购买收据

c# - 如何使用 String.Format (c#) 去掉小数部分

c# - 带有输入参数和输出的 Task.Run