回滚与刷新与重新加载实体数据

时间:2018-01-24 07:44:03

标签: c# wpf mvvm entity-framework-6

我有一个WPF项目,MVVM带有EF6数据集,我正在寻找实现回滚所有更改的方法。

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

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如何回滚任何更改:

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如何刷新数据,根据某些内容是否发生了变化,这些数据可能会也可能不会回滚数据:

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

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

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

我想知道的是:
回滚
VS
清爽
vs
重装

他们似乎都做了同样的事情,ReloadData()更贵。

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

1 个答案:

答案 0 :(得分:2)

上述方法并不相同。

执行LINQ to Entities跟踪查询时,EF将重新查询数据库,但随后会考虑返回实体的当前更改跟踪器状态,并返回本地实体数据而不是实际数据。该概念类似于旧版RefreshMode.ClientWins方法的ObjectContext.Refresh选项。

刷新的最终效果是它最终会带来新数据(通过不同的上下文实例或其他进程/用户添加到数据库中)。但目前的修改将继续有效。

所以IMO你的选项只有两个 - 回滚当前或使用新的上下文。实现它的方式,回滚方法似乎工作,但实体查询仍然不会应用在上下文实例之外进行的更改。但这适用于长期生存环境中的跟踪实体查询,因此可能不会被视为缺陷。

您选择的两个中哪一个取决于您的要求。但唯一有保证的新方法就是使用新的上下文实例。