【问题标题】:Why does ChangeTracker.Load() not load all of my navigation properties?为什么 ChangeTracker.Load() 不加载我的所有导航属性?
【发布时间】:2021-11-26 12:41:47
【问题描述】:

我的Company 实体中引用了一组实体,如下所示

public sealed class Company 
{
    private readonly List<CompanyJobCategory> _jobCategories = new();
    public IReadOnlyCollection<CompanyJobCategory> JobCategories => _jobCategories.AsReadOnly();
}

public sealed class CompanyJobCategory
{
    public CompanyJobCategory(int jobCategoryId, Guid companyId)
    {
        JobCategoryId = jobCategoryId;
        CompanyId = companyId;
    }
    
    public int JobCategoryId { get; private set; }
    public JobCategory JobCategory { get; private set; }
    public Guid CompanyId { get; private set; }
}

public sealed class JobCategory
{
    // the stuff I need is here
}

一切正常,但我现在需要确保在调用 DbContext.SaveChanges() 之前的某个时间点可以使用这些 JobCategory 导航属性

我这样抓取实体

var entry = DbContext.ChangeTracker
    .Entries<Company>()
    .FirstOrDefault(entry => entry.Entity.Id == id)!;

但是可以看到对于每个entry.Entity.JobCategoriesJobCategory 始终为空(由于我如何初始化实体)

我想我可以做类似的事情

DbContext.ChangeTracker.Entries<Company>().First().Collection(x => x.JobCategories).Load();

但这不会填充子导航道具

我还尝试在调用Load() 之前将IsLoaded 设置为false,但这没有帮助

我注意到的最奇怪的事情是,偶尔如果我查看 entry.Collections(x => x.JobCategories)[0].JobCategory,其中一些子实体会被完全加载,但是我如何添加其中任何一个都没有区别。这怎么可能?

我还尝试了以下方法,这似乎加载了大部分 JobCategory 引用,但仍有一些作为 null 出现 - 可能吗?

entry.Collection(x => x.JobCategories)
    .Query()
    .Include(y => y.JobCategory)
    .Load();

【问题讨论】:

  • “引用另一个名为 JobCategory 的实体” - 单个 JobCategoryJobCategory 的集合?我假设阅读您的 Q 是一个集合,但它可能会被证明是有用的,请让它更清晰。
  • @ErmiyaEskandary CompanyJobCategory 包含对单个 JobCategory 的引用 - 它基本上是一个 m2m 连接表
  • 最后一个 sn-p(带有 Query().Include(...).Load() )是完成您要求的预期方式。
  • @IvanStoev 谢谢 Ivan,知道为什么 1 或 2 个导航道具仍未填充吗?大多数情况下它都有效,但有些仍然为空,即使我可以看到 do 引用了外表中的真实行......虽然这似乎是不可能的

标签: c# .net-core entity-framework-core


【解决方案1】:

这就是我的工作方式

// get the entity which is about to be persisted
var entry = DbContext.ChangeTracker
    .Entries<Company>()
    .FirstOrDefault(x => x.Entity.Id == id)!;

// select the ids for the referenced entities I need to load
var jobCategoryIds = entry.Entity.JobCategories
    .Select(x => x.JobCategoryId); 

// load them into into DbContext
await DbContext.Set<JobCategory>()
    .Where(x => jobCategoryIds.Contains(x.Id))
    .LoadAsync();

我需要将我需要的引用实体直接加载到DbContext中,而不是仅仅在跟踪的集合上调用LoadAsync()

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2015-02-21
    • 2013-09-08
    • 1970-01-01
    • 1970-01-01
    • 2016-11-21
    相关资源
    最近更新 更多