14.8 DataAdapter Events
The
FillError event is most commonly raised when the
data being added violates a constraint in the
DataSet or when the data being added
can't be converted to a .NET Framework data type
without a loss of precision. When a FillError
event occurs, the current row isn't added to the
DataTable. Handling the
FillError event allows the error to be resolved
and the row to be either added or ignored before resuming the
Fill( ) operation with the next row.
The FillError event handler receives an argument
of FillErrorEventArgs, which contains specific
data about the event that can effectively respond to and handle the
error. The Continue property of the
FillErrorEventArgs argument determines whether an
exception is thrown or processing continues because of the error.
The following example demonstrates handling the
FillError event when filling a table containing
three columns:
SqlDataAdapter da;
// ... code to set up the data adapter
da.FillError += new FillErrorEventHandler(da_FillError);
DataSet ds = new DataSet();
da.Fill(ds, "MyTable");
private void da_FillError(object sender, FillErrorEventArgs e)
{
// ... code to identify and correct the error
// add the fixed row to the table
DataRow dr = e.DataTable.Rows.Add(new object[] {e.Values[0],
e.Values[1], e.Values[2]});
// continue the Fill with the rows remaining in the data source
e.Continue = true;
}
The RowUpdating event is raised before changes to a row
are submitted to the data source. The RowUpdating
event handler can modify update behavior, providing additional
handling or canceling the update for the row. The
RowUpdated event is raised after the update command
is executed against the data source and is used to respond to
exceptions that occur during the update.
The RowUpdating and RowUpdated
event handlers receive arguments of
SqlRowUpdatingEventArgs and
SqlRowUpdatedEventArgs, respectively, containing
data specific to each event. The arguments contain among other
properties, a reference to the Command object that
performs the update, a DataRow object containing
the updated data, a StatementType property
containing the type of update being performed, an
Errors property containing any errors generated,
and a Status property. The
Status property returns a value of
ErrorsOccurred if an error occurred while updating
the row. The Status property can control the
action to be taken with the current and remaining rows to be updated
after an error; an error can be thrown, the current row can be
skipped, or all remaining rows can be skipped by setting the
Status property after an error.
The following code demonstrates handling the
RowUpdating and RowUpdated
events:
SqlDataAdapter da;
// ... code to set up the data adapter
// add the event handlers
da.RowUpdating += new SqlRowUpdatingEventHandler(da_RowUpdating);
da.RowUpdated += new SqlRowUpdatedEventHandler(da_RowUpdated);
DataSet ds = new DataSet();
// ... code to fill the DataSet
// ... code to modify the data in the DataSet
da.Update(ds, "Orders");
private void da_RowUpdating(object sender, SqlRowUpdatingEventArgs e)
{
// Write the date, OrderID, and type of update to a log
System.IO.TextWriter tw = System.IO.File.AppendText("update.log");
tw.WriteLine("{0}: Order {1} {2}.", DateTime.Now, e.Row["OrderID",
DataRowVersion.Original], e.StatementType.ToString());
tw.Close();
}
private void da_RowUpdated(object sender, SqlRowUpdatedEventArgs e)
{
if(e.Status == UpdateStatus.ErrorsOccurred)
{
// set the error information for the row
e.Row.RowError = e.Errors.Message;
// skip peocessing the current row and continue with the rest
e.Status = UpdateStatus.SkipCurrentRow;
}
}
An alternative to processing each error in response to the
RowUpdated event as shown in this example is to
set the DataAdapter
ContinueUpdateOnError property to
true, allowing all errors to be handled once the
update of all rows is
complete.
|