如何使用实体框架在多个级别上完全加载递归模型



EDIT:这是答案在LINQ中递归查询可能吗已经有人回答了,一定是错过了那个

我使用的是.NET Core 2.2。

我浏览了这个网站上提出的多个问题,但没有一个答案对我有效。

我的模型如下(简化(:

public class Product
{
/// <summary>
///     Gets or sets the Id.
/// </summary>
public string Id { get; set; }
/// <summary>
///     Gets or sets the code.
/// </summary>
public string Code { get; set; }
/// <summary>
///     Gets or sets the properties.
/// </summary>
public List<Property> Properties { get; set; }
/// <summary>
///     Gets or sets the products
/// </summary>
public List<Product> Products { get; set; }
}
public class Property
{
/// <summary>
///     Gets or sets the Id.
/// </summary>
public string Id { get; set; }
/// <summary>
///     Gets or sets the code
/// </summary>
public string Code { get; set; }
}

我正在尝试加载一个包含所有子产品的产品,还包括所有产品的属性。

首先,我已经能够递归地加载所有产品,但我真的不知道为什么它能工作。

我试过这个:

var products1 = this._context.Products.Where(x => x.Code == "TEST").Include(x => x.Products);

而且它只会加载一级产品的产品。

然后,纯属运气/错误,我在前面提到的之前离开了这一行

this._context.Products.ToList()

然后,第一行实际上递归地加载了所有产品。。。我想不错吧?

无论如何,现在我要做的是递归地加载所有产品,同时加载它们的所有属性。

我试过一些东西,包括看起来不太光彩的:

this._context.Products.Where(x => x.Code == "TEST").Include(x => x.Properties)
.Include(x => x.Products).ThenInclude(x => x.Properties);

但无论我做什么,我都只加载第一级递归的乘积的属性。我仍然递归地完全加载所有产品,但只有前两个级别加载了它们的属性。

所以最终我的问题是我该怎么做?作为一个额外的问题,如果真正的问题得到了回答,无论如何都可能得到回答:为什么我需要写这行:

this._context.Products.ToList()

此行之前:

var products1 = this._context.Products.Where(x => x.Code == "TEST").Include(x => x.Products);

要递归加载产品?

EDIT:请注意,我知道我可以在循环中用多个查询(每个产品一个(递归加载所有产品/属性,但如果可能的话,我肯定想避免这种情况

Eager加载不会递归工作,但您可以使用惰性加载。这会影响您的性能,但您可以迭代所有层。

请参阅https://learn.microsoft.com/en-us/ef/core/querying/related-data

使用延迟加载的最简单方法是安装Microsoft.EntityFrameworkCore.Proxy包,并通过调用UseLazyLoadingProxies来启用它。例如:

protected override void OnConfiguring(DbContextOptionsBuilder optionsBuilder)
=> optionsBuilder
.UseLazyLoadingProxies()
.UseSqlServer(myConnectionString);

EF Core将为任何导航属性启用延迟加载可以重写——也就是说,它必须是虚拟的,并且在可以继承自。

因此,将您的List转换为虚拟集合,就可以开始了。

最新更新