【问题标题】:How to reload collection in EF Core 2.x?如何在 EF Core 2.x 中重新加载集合?
【发布时间】:2019-07-16 15:05:02
【问题描述】:

我知道有一个Load 方法。

_dbContext.Entry(blog).Collection(b => b.Posts).Load()

但我正在尝试处理并发冲突,我已将 post 添加到 blog.Posts 中。如果调用Load,它不会清除blog.Posts,只需将现有的Posts附加到它。

我试过了:

blog.Posts = null;
_dbContext.Entry(blog).Collection(b => b.Posts).Load()

但是blog.Posts 变成了一个空集合(零计数)。

所以我想要一个Reload

【问题讨论】:

标签: c# entity-framework-core ef-core-2.2


【解决方案1】:

不幸的是,虽然EntityEntryReload 方法,但ReferenceEntryCollectionEntry 没有这样的方法(或者一般来说,NavigationEntry 是前两者的基础)。而Reload 方法只刷新原始属性,因此不能用于刷新导航属性。

幸运的是,创建一个自定义的并不难。它需要分离(或重新加载?)所有当前集合项,在调用Load之前将IsLoaded设置为false,将CurrentValue设置为null

类似这样(将其放入您选择的静态类并添加必要的usings):

public static void Reload(this CollectionEntry source)
{
    if (source.CurrentValue != null)
    {
        foreach (var item in source.CurrentValue)
            source.EntityEntry.Context.Entry(item).State = EntityState.Detached;
        source.CurrentValue = null;
    }
    source.IsLoaded = false;
    source.Load();
}

这样您就可以使用所需的

_dbContext.Entry(blog).Collection(b => b.Posts).Reload();

【讨论】:

  • Detached 分配是否必要?如果我只设置source.CurrentValue = null;然后设置source.IsLoaded = false;source.Load();,安全吗?
  • 不。我的测试表明所有这些都是必要的。不分离项目,您将获得缓存项目而不是数据库中的新项目以及添加的项目但未删除的项目。
  • @IvanStoev 这对我不起作用。有时间请看这里:stackoverflow.com/q/65723105/3850405
  • 我测试了这个解决方案,它可以工作,但要小心:如果重新加载的集合的某些元素在其他对象的列表中,它们仍将在“分离”状态和最新版本的列表中也会添加。所以你会有两次相同的元素,一个是“分离的”。
猜你喜欢
  • 1970-01-01
  • 2018-11-06
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2014-06-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多