共用方式為


處理 DataAdapter 事件

DataAdapter ADO.NET 會公開三個事件,可用來響應數據源數據所做的變更。 下表顯示 DataAdapter 事件。

事件 說明
RowUpdating 在某一列上執行 UPDATE、INSERT 或 DELETE 作業(透過呼叫某個 Update 方法)即將開始。
RowUpdated 數據列上的UPDATE、INSERT或DELETE作業已完成(透過其中一個 Update 方法的呼叫)。
FillError Fill 作業中發生錯誤。

RowUpdating 和 RowUpdated

RowUpdating 會在資料來源上處理 DataSet 的資料列更新之前被引發。 在資料來源完成對 RowUpdated 的資料列的任何更新處理後,會觸發DataSet。 因此,您可以使用 RowUpdating 來修改更新行為,以便在更新發生前提供額外的處理、保留更新的行的參考、取消目前的更新,並排程批次處理以便稍後處理等等。 RowUpdated 對於回應更新期間發生的錯誤和例外狀況很有用。 您可以將錯誤資訊新增至 DataSet,以及重試邏輯等等。

傳遞至 RowUpdatingEventArgsRowUpdatedEventArgs 事件的 RowUpdatingRowUpdated 自變數包含下列項目:Command屬性,該屬性參考用來執行更新的Command對象;Row屬性,該屬性參考包含更新資訊的DataRow物件;StatementType屬性,表明正在執行的更新類型;TableMapping(如果適用);以及Status操作的結果。

您可以使用 Status 屬性來判斷作業期間是否發生錯誤,並視需要控制目前和結果數據列的動作。 當事件發生時,Status 屬性等於 ContinueErrorsOccurred。 下表顯示您可以設定 Status 屬性的值,以便在更新期間控制稍後的動作。

地位 說明
Continue 繼續更新作業。
ErrorsOccurred 中止更新作業並擲回例外狀況。
SkipCurrentRow 忽略目前的數據列並繼續更新作業。
SkipAllRemainingRows 中止更新作業,但不會拋出異常。

Status 屬性設定為 ErrorsOccurred 會導致拋出異常。 您可以將Errors屬性設定為所需的例外狀況,以控制要擲回的例外狀況。 使用除了 Status 的其他值可防止擲回例外狀況。

您也可以使用 ContinueUpdateOnError 屬性來處理更新資料列的錯誤。 如果 DataAdapter.ContinueUpdateOnErrortrue,當數據列的更新導致擲回例外狀況時,例外狀況的文字會放入 RowError 特定數據列的資訊中,而且處理會繼續,而不會擲回例外狀況。 這可讓您在 Update 完成後回應錯誤,而相反地,RowUpdated 事件可讓您在遇到錯誤時回應錯誤。

下列程式代碼範例示範如何新增和移除事件處理程式。 RowUpdating事件處理程式會以時間戳寫入所有已刪除記錄的記錄。 事件處理程式會將RowUpdated錯誤資訊新增至 RowErrorDataSet數據列的 屬性,隱藏例外狀況,並繼續處理 (鏡像 的行為ContinueUpdateOnError = true)。

' Assumes that connection is a valid SqlConnection object.  
Dim custAdapter As SqlDataAdapter = New SqlDataAdapter( _  
  "SELECT CustomerID, CompanyName FROM Customers", connection)  
  
' Add handlers.  
AddHandler custAdapter.RowUpdating, New SqlRowUpdatingEventHandler( _  
  AddressOf OnRowUpdating)  
AddHandler custAdapter.RowUpdated, New SqlRowUpdatedEventHandler(  
  AddressOf OnRowUpdated)  
  
' Set DataAdapter command properties, fill DataSet, and modify DataSet.  
  
custAdapter.Update(custDS, "Customers")  
  
' Remove handlers.  
RemoveHandler custAdapter.RowUpdating, _  
  New SqlRowUpdatingEventHandler(AddressOf OnRowUpdating)  
RemoveHandler custAdapter.RowUpdated, _  
  New SqlRowUpdatedEventHandler(AddressOf OnRowUpdated)  
  
Private Shared Sub OnRowUpdating(sender As Object, _  
  args As SqlRowUpdatingEventArgs)  
  If args.StatementType = StatementType.Delete Then  
    Dim tw As System.IO.TextWriter = _  
  System.IO.File.AppendText("Deletes.log")  
    tw.WriteLine( _  
      "{0}: Customer {1} Deleted.", DateTime.Now, args.Row(_  
      "CustomerID", DataRowVersion.Original))  
    tw.Close()  
  End If  
End Sub  
  
Private Shared Sub OnRowUpdated( _  
  sender As Object, args As SqlRowUpdatedEventArgs)  
  If args.Status = UpdateStatus.ErrorsOccurred  
    args.Status = UpdateStatus.SkipCurrentRow  
    args.Row.RowError = args.Errors.Message  
  End If  
End Sub  
// Assumes that connection is a valid SqlConnection object.  
SqlDataAdapter custAdapter = new SqlDataAdapter(  
  "SELECT CustomerID, CompanyName FROM Customers", connection);  
  
// Add handlers.  
custAdapter.RowUpdating += new SqlRowUpdatingEventHandler(OnRowUpdating);  
custAdapter.RowUpdated += new SqlRowUpdatedEventHandler(OnRowUpdated);  
  
// Set DataAdapter command properties, fill DataSet, modify DataSet.  
  
custAdapter.Update(custDS, "Customers");  
  
// Remove handlers.  
custAdapter.RowUpdating -= new SqlRowUpdatingEventHandler(OnRowUpdating);  
custAdapter.RowUpdated -= new SqlRowUpdatedEventHandler(OnRowUpdated);  
  
protected static void OnRowUpdating(  
  object sender, SqlRowUpdatingEventArgs args)  
{  
  if (args.StatementType == StatementType.Delete)  
  {  
    System.IO.TextWriter tw = System.IO.File.AppendText("Deletes.log");  
    tw.WriteLine(  
      "{0}: Customer {1} Deleted.", DateTime.Now,
       args.Row["CustomerID", DataRowVersion.Original]);  
    tw.Close();  
  }  
}  
  
protected static void OnRowUpdated(  
  object sender, SqlRowUpdatedEventArgs args)  
{  
  if (args.Status == UpdateStatus.ErrorsOccurred)  
  {  
    args.Row.RowError = args.Errors.Message;  
    args.Status = UpdateStatus.SkipCurrentRow;  
  }  
}  

填充錯誤

DataAdapterFillError操作中發生錯誤時,會發出Fill事件。 當加入的數據行中的數據無法轉換成 .NET Framework 類型而失去精確度時,通常會發生這種錯誤。

如果在操作期間發生 Fill 錯誤,則目前的資料列不會新增至 DataTable。 事件 FillError 可讓您解決錯誤並新增數據列,或忽略排除的數據列並繼續 Fill 作業。

FillErrorEventArgs傳遞至FillError事件的 可以包含數個屬性,可讓您回應並解決錯誤。 下表顯示 物件的屬性 FillErrorEventArgs

房產 說明
Errors Exception發生的 。
DataTable DataTable發生錯誤時要填入的物件。
Values 對象的陣列,其中包含發生錯誤時要加入之數據列的值。 在Values陣列中的序數參考與正在加入的行之列的序數參考相對應。 例如,Values[0] 是作為行的第一欄所添加的值。
Continue 可讓您選擇是否引發例外狀況。 將 Continue 屬性設定為 false,會停止目前的 Fill 作業,並擲回例外狀況。 將 Continue 設定為 true 即使發生錯誤,仍然繼續 Fill 操作。

下列程式代碼範例會為 FillError 的 事件 DataAdapter新增事件處理程式。 在事件程序代碼中 FillError ,此範例會判斷是否有精確度遺失的可能性,並提供回應例外狀況的機會。

AddHandler adapter.FillError, New FillErrorEventHandler( _  
  AddressOf FillError)  
  
Dim dataSet As DataSet = New DataSet  
adapter.Fill(dataSet, "ThisTable")  
  
Private Shared Sub FillError(sender As Object, _  
  args As FillErrorEventArgs)  
  If args.Errors.GetType() Is Type.GetType("System.OverflowException") Then  
    ' Code to handle precision loss.  
    ' Add a row to table using the values from the first two columns.  
    DataRow myRow = args.DataTable.Rows.Add(New Object() _  
      {args.Values(0), args.Values(1), DBNull.Value})  
    ' Set the RowError containing the value for the third column.  
    myRow.RowError = _  
      "OverflowException encountered. Value from data source: " & _  
      args.Values(2)  
    args.Continue = True  
  End If  
End Sub  
adapter.FillError += new FillErrorEventHandler(FillError);  
  
DataSet dataSet = new DataSet();  
adapter.Fill(dataSet, "ThisTable");  
  
protected static void FillError(object sender, FillErrorEventArgs args)  
{  
  if (args.Errors.GetType() == typeof(System.OverflowException))  
  {  
    // Code to handle precision loss.  
    //Add a row to table using the values from the first two columns.  
    DataRow myRow = args.DataTable.Rows.Add(new object[]  
       {args.Values[0], args.Values[1], DBNull.Value});  
    //Set the RowError containing the value for the third column.  
    myRow.RowError =
       "OverflowException Encountered. Value from data source: " +  
       args.Values[2];  
    args.Continue = true;  
  }  
}  

另請參閱