回滚vs刷新vs重新加载实体数据 [英] Rollingback vs Refreshing vs Reloading Entity data

查看:197
本文介绍了回滚vs刷新vs重新加载实体数据的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个WPF项目,一个MVVM和一个EF6数据集,我正在寻找一种方法来回滚所有更改.

I have an WPF project, MVVM with an EF6 dataset and I'm looking to implement a way to rollback all changes.

以下代码显示了ViewModel如何加载数据:

The following code shows how ViewModel loads the data:

protected async override void GetData()
{
    ThrobberVisible = Visibility.Visible;

    ObservableCollection<MobileDeviceRequestVM> _requests = new ObservableCollection<MobileDeviceRequestVM>();

    var requests = await (from c in dbContext.MobileDeviceRequests
                           orderby c.RequestDate
                           select c)
                           .ToListAsync();

    foreach (MobileDeviceRequest req in requests)
    {
        _requests.Add(new MobileDeviceRequestVM { IsNew = false, TheEntity = req });
    }
    MobileDeviceRequests = _requests;
    RaisePropertyChanged("MobileDeviceRequests");
    ThrobberVisible = Visibility.Collapsed;
}

以下代码显示了ViewModel如何回滚任何更改:

The following code shows how the ViewModel rolls back any changes:

protected override void RollbackData()
{
    var changedEntries = dbContext.ChangeTracker.Entries()
        .Where(x => x.State != EntityState.Unchanged).ToList();

    foreach (var entry in changedEntries)
    {
        switch (entry.State)
        {
            case EntityState.Modified:
                entry.CurrentValues.SetValues(entry.OriginalValues);
                entry.State = EntityState.Unchanged;
                break;
            case EntityState.Added:
                entry.State = EntityState.Detached;
                break;
            case EntityState.Deleted:
                entry.State = EntityState.Unchanged;
                break;
        }
    }

    //Somewhere in here the OC: MobileDeviceRequests needs to get refreshed
    //with the context as items may have been added and/or deleted

    RaisePropertyChanged("MobileDeviceRequests");
}

以下代码显示了ViewModel如何刷新数据,取决于是否已更改某些内容,它可能会回滚数据,也可能不会回滚数据:

The following code shows how the ViewModel refreshes the data, which may or may not rollback data depending on if something has changed:

protected virtual void RefreshData()
{
    GetData();
}

以下内容创建了一个新的上下文

The following creates a new context

protected virtual void ReloadData()
{
    dbContext= new BAContext();
    GetData();
}

我想知道的是:
回滚
vs
刷新
vs
重新加载

What I'm wondering about is:
Rolling Back
vs
Refreshing
vs
Reloading

它们似乎几乎都在做同一件事,而ReloadData()则更昂贵.

They all seem to do virtually the same thing, the ReloadData() being the more expensive.

我想我要问的是,如果刷新执行了重新查询并填充了OC,回滚是否有任何意义.如果存在,那么您将如何重新填充OC,它与刷新有什么不同?

I guess what I'm asking is, if refresh does the requery and populates the OC, is there any point in having a rollback. If there is, then how would you repopulate the OC and would it be any different than the refresh?

推荐答案

上述方法并不等效.

当执行LINQ to Entities跟踪查询时,EF将重新查询数据库,但是将考虑返回实体的当前更改跟踪器状态,并将返回本地实体数据而不是实际数据.该概念类似于

When executing LINQ to Entities tracking query, EF will requery the database, but then will take into account the current change tracker state of the returned entities, and will return the local entity data rather than actual data. The concept is similar to the RefreshMode.ClientWins options of the older ObjectContext.Refresh method.

刷新的最终结果是最终将带来新数据(通过不同的上下文实例或另一个进程/用户添加到数据库中).但是当前的修改将继续生效.

The net effect of your refresh will be that it eventually will bring the new data (added to the database through different context instance or another process/user). But the current modifications will stay in effect.

因此IMO,您的选择只有两个-回滚当前的内容或使用新的上下文.回滚方法似乎可以实现,但是实体查询仍然不会应用在上下文实例外部进行的更改.但这无论如何都适用于长期存在的上下文中的跟踪实体查询,因此可能不会被认为是缺陷.

So IMO you the options are just two - rollback the current or use new context. The way you implemented it, rollback method seems to work, but entity queries still will not apply changes made outside the context instance. But this applies to the tracked entity queries in a long lived context anyway, so probably might not be considered a defect.

您选择哪两个取决于您的要求.但是,保证真正开始的唯一方法是使用新的上下文实例.

Which one of the two you choose depends on your requirements. But the only guaranteed way to start really fresh is to use a new context instance.

这篇关于回滚vs刷新vs重新加载实体数据的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆