![]() |
Database »
Database »
General
Intermediate
Easier Database Transactions - Extending the Using Statement to Perform Automatic Database TransactionsBy Chad Z. Hower aka KudzuAny user who works with database updates uses transactions. Transactions in ADO.NET are done using a transaction object, and a try..catch, but there is an easier, one might even say a more C# way to handle database transactions. |
C#, SQL, Windows, .NET CF, .NET 1.0, .NET 1.1, .NET 2.0, ADO.NET, SQL 2000, SQL 2005, VS.NET2003, VS2005, SQL CE, DBA, Dev
|
|
Advanced Search |
|
|
|
||||||||||||||||
Any user who works with database updates uses transactions. Transactions in ADO.NET are done using a transaction object, and a try..catch, but there is an easier, one might even say a more C# way to handle database transactions.
Because this technique relies on the using statement which is C# specific, this technique cannot be applied in Visual Basic .NET. However, rumors are that Visual Studio .NET 2005 will include a similar statement for Visual Basic.
Here is an example of a database transaction the normal way. This is a condensed version of the example on MSDN.
using (OleDbTransaction xTx = _DB.BeginTransaction()) {
try {
OleDbCommand xCmd = _DB.CreateCommand();
xCmd.Transaction = xTx;
xCmd.CommandText = "Insert into Person (Name, Telephone)" +
" values ('Normal One', '(412) 555-1212')";
xCmd.ExecuteNonQuery();
if (chckThrow.Checked) {
throw new Exception("Test Exception");
}
xCmd.CommandText = "Insert into Person (Name, Telephone)" +
" values ('Normal Two', '(423) 555-1212')";
xCmd.ExecuteNonQuery();
xTx.Commit();
}
catch (Exception xException) {
xTx.Rollback();
throw xException;
}
}
With my method, the code does the same, but becomes a bit shorter, cleaner, and even a bit more C# like.
using (Transaction xTx = new Transaction(_DB)) {
OleDbCommand xCmd = _DB.CreateCommand();
((IDbCommand)xCmd).Transaction = xTx.DBTransaction;
xCmd.CommandText = "Insert into Person (Name, Telephone)" +
" values ('Object One', '(412) 555-1212')";
xCmd.ExecuteNonQuery();
if (chckThrow.Checked) {
throw new Exception("Test Exception");
}
xCmd.CommandText = "Insert into Person (Name, Telephone)" +
" values ('Object Two', '(423) 555-1212')";
xCmd.ExecuteNonQuery();
xTx.Commit();
}
The demo project demonstrates this and allows simulated exceptions. The demo project uses the included Access database file for simplicity. However, the included class works with any ADO.NET data source.
The using statement in C# causes the dispose to be called when the block is exited. By implementing a Dispose, and checking to see if the transaction has been committed, the transaction class can then determine whether or not to call rollback. There is no need to rethrow any exception that may be in progress, because C# automatically continues the exception path as part of the handling of the using block.
public class Transaction : IDisposable {
private IDbConnection _DB;
private IDbTransaction _DBTransaction;
public IDbTransaction DBTransaction {
get { return _DBTransaction; }
}
public Transaction(IDbConnection aDB) : this(aDB, true) {
}
public Transaction(IDbConnection aDB, bool aHandle) {
if (aHandle) {
_DB = aDB;
_DBTransaction = _DB.BeginTransaction();
}
}
public void Commit() {
if (_DB != null) {
_DBTransaction.Commit();
_DBTransaction.Dispose();
_DB = null;
}
}
public void Dispose() {
if (_DB != null) {
_DBTransaction.Rollback();
_DBTransaction.Dispose();
_DB = null;
}
}
}
This class purely adds syntactic sugar to your code and makes performing transactions a little bit easier. The functionality is the same. But when working with transactions and having to manually create this structure each time, the shorter version is a lot easier to type, as well as read later when working in the code again.
| You must Sign In to use this message board. | ||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
|
||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||||
General
News
Question
Answer
Joke
Rant
Admin
|
PermaLink |
Privacy |
Terms of Use
Last Updated: 25 Oct 2004 Editor: Smitha Vijayan |
Copyright 2004 by Chad Z. Hower aka Kudzu Everything else Copyright © CodeProject, 1999-2009 Web12 | Advertise on the Code Project |