在ADO.NET数据集中维护DataRowState - RejectChanges()方法不起作用?

时间:2009-08-06 02:25:48

标签: ado.net datatable dataset rowstate

简化问题:

我有一些带有一些数据表的DataSet ...... 我有一个绑定到其中一个数据表的Winforms DataGrid。 用户通过DataGrid将一些行粘贴到所述数据表中,假设有3行;

现在所有三行的RowState = DataRowState.Added。

我现在开始一个sqlserver事务。

然后调用dataAdapter1.Update(dataSet1)将行更新到SqlServer中。 第1行......好的 第2行..好的 在sqlserver级别的第3行错误(通过设计我强制执行唯一索引)

检测到此错误后,我回滚sqlserver事务。

我还尝试使用Dataset1.RejectChanges()和/或Datatable1.RejectChanges()中的任何一个“回滚”数据表/数据集更改。

问题既不是.RejectChanges()也是我设想的方式。我的数据表现在有两行(row1,row2),其RowState = DataRowState.Unchanged; row3完全消失了。

我想要发生的是,当我回滚sqlserver事务时,数据表中的所有3行在调用dataAdapter1.Update()方法之前保持在SAME STATE。

(原因是用户可以查看绑定的DataGrid中的错误,采取纠正措施,然后再次尝试更新)。

任何想法?即我正在寻找相当于在ADO dataTable级别回滚状态的东西。

2 个答案:

答案 0 :(得分:0)

好的,所以我想办法解决这个问题。

获取原始数据表的克隆,并更新克隆。

如果发生错误,您仍然拥有原始数据表及其原始DataRowState;此外,您可以将克隆中发生的任何错误复制到原始Datatable,从而反映数据网格中的错误,供用户查看。

如果更新成功,您只需使用克隆刷新原始数据表。

VB代码:

Try
    'daMyAdapter.Update(dsDataset, "MyDatatable") <-- replace original with below lines.
    _dtMyDatatableClone = dsDataset.MyDatatable.Copy()

    If _dtMyDatatableClone IsNot Nothing Then
      daMyAdapter.Update(_dtMyDatatableClone)

       'if you get here, update was successul - refresh now!
       dsDataset.MyDatatable.Clear()
       dsDataset.MyDatatable.Merge(_dtMyDatatableClone, False, MissingSchemaAction.Ignore)
    End If
Catch
    'uh oh, put error handler here.
End Try

答案 1 :(得分:0)

我遇到类似的问题,试图将更改回滚到绑定到Xceed DataGrid的DataTable。在DataGrid中进行编辑后,编辑后的值都将成为DataRow的当前状态的一部分。 RejectChanges仅适用于阻止建议的行状态变为当前状态。

为了还原给定行的更改,我编写了一个方法来用原始版本覆盖当前行版本。要将版本设置为原始,只需在数据表上调用AcceptChanges()即可。

    public static void RevertToOriginalValues(DataRow row)
    {
        if (row.HasVersion(DataRowVersion.Original) && row.HasVersion(DataRowVersion.Current))
        {
            for (int colIndex = 0; colIndex < row.ItemArray.Length; colIndex++)
            {
                var original = row[colIndex, DataRowVersion.Original];
                row[colIndex] = original;
            }
        }
    }