InicioArticulos y noticiasBases de datosProgramaciónForosInternetServiciosContratacionEmail
También puedes ver ...
LinQ To SQL - Un ejemplo sencillo
Cómo activar Intelisense (autocompletado) en el Web.config
Leer un campo XML de SQL Server 2005 con C#
TripleDES - Un ejemplo practico en C#
Mostrar un GridView dentro de un DataList
Métodos Extensores: INNER JOIN
String.Format
LINQ con métodos Extensores y expresiones lambda
Métodos Extensores: SELECT
Problemas en la instalación de Visual Studio 2008-Visual studio web authoring component

Afiliados
La Web del programador
MundoProgramacion


 

TransactionScope - Simplificando el trabajo con transacciones.

A partir del Framewrok 2.0 tenemos a nuestra disposición el objeto TransactionScope, que permite simplificar el trabajo con transacciones. Especialmente llamativo es la capacidad de promocionar la transacción a un entorno de transacciones distribuidas (MS DTC - COM+) de forma casi transparente .

Vamos a empezar con un ejemplo sencillito, de esos que no tienen que fallar nunca. Lo primero que debemos hacer es añadir una referencia a System.Transactions en nuestro proyecto.

Sobre una base de datos de prueba, creamos una nueva tabla para nuestro ejemplo.

 

CREATE TABLE

Persona

(CodPersona int IDENTITY,

Nombre varchar(50),

Apellido1 varchar(100),

Apellido2 varchar(100),

FechaNacimiento datetime,

CONSTRAINT PK_Persona PRIMARY KEY (CodPersona)

)

Para acceder a los datos vamos a utilizar LinqToSQL, por lo que añadimos un nuevo archivo de este tipo a nuestro proyecto. Por supuesto también podríamos trabajar con el modelo clásico de ADO.NET. Podemos ver como añadir clases de LinqToSQL a nuestro proyecto desde este enlace:
http://www.devjoker.com/contenidos/Articulos/326/LinQ-To-SQL--Un-ejemplo-sencillo.aspx

Ahora creamos un formulario - con un único botón - y añadimos el siguiente código al evento click del botón.

 

using (TransactionScope transactionScope = new TransactionScope())

{

try

{

AddData();

transactionScope.Complete();

MessageBox.Show("OK");

}

catch (Exception ex)

{

MessageBox.Show(ex.Message,

"Error - Se deshacen los cambios");

}

}

Con esto estamos envolviendo el código con un objeto TransactionScope - que crea a su vez una transacción controlada por el componente de Windows denominado LTM (Lightweight Transaction Coordinator) - es lo que se conoce como ambito o contexto de la transacción.

Posteriormente llamamos a un método que se encarga de grabar los registros en la base de datos y si todo ha ido bien confirmamos las transaccion con el método Complete(). Como vemos todo muy simple.

El método AddData es un simple bucle que inserta 100 registros en la base de datos. Lo vemos - no debemos tener ningún tipo de problema si hemos leido el artículo de LinqToSql que hemos mencionado antes.

 

private void AddData()

{

using (DataDataContext ctx = new DataDataContext())

{

for (int i = 0; i < 100; i++){

Persona p = new Persona();

p.Nombre = String.Format("Nombre {0}", i);

p.Apellido1 = String.Format("Apellido1 {0}", i);

p.Apellido2 = String.Format("Apellido2 {0}", i);

p.FechaNacimiento = DateTime.Now.AddMonths(i * -1);

ctx.Personas.InsertOnSubmit(p);

}

ctx.SubmitChanges();

}

}

Si consultamos los datos de la tabla Persona - que creamos en nuestra base de datos al principio del artículo -tendremos algo así:

CodPersona  Nombre     Apellido1      Apellido2       FechaNacimiento
----------- ---------- -------------- --------------- -----------------------
1           Nombre 0   Apellido1 0    Apellido2 0     2008-07-14 23:26:43.907
2           Nombre 1   Apellido1 1    Apellido2 1     2008-06-14 23:26:43.907
3           Nombre 2   Apellido1 2    Apellido2 2     2008-05-14 23:26:43.907
4           Nombre 3   Apellido1 3    Apellido2 3     2008-04-14 23:26:43.907
5           Nombre 4   Apellido1 4    Apellido2 4     2008-03-14 23:26:43.907
6           Nombre 5   Apellido1 5    Apellido2 5     2008-02-14 23:26:43.907 
...

Todo ha ido bien y no hemos debido tener ningún problema.

Ahora queremos comprobar que cuando las cosas fallan los cambios se deshacen correctamente. Para ello incluimos un nuevo método, que llamará al método de añadir registros (y que acabamos de ver que funciona correctamente) y una finalizada la inserción de datos lanzará un error..

 

private void AddDataWithError()

{

AddData();

throw new ApplicationException("Error provocado");

}

Y modificamos nuestro código para que se llame al método que lanza el error. 

 

using (TransactionScope transactionScope = new TransactionScope())

{

try

{

AddDataWithError();

transactionScope.Complete();

}

catch (Exception ex)

{

MessageBox.Show(ex.Message,

"Error - Se deshacen los cambios");

}

}

Podemos comprobar que la aplicación muestra el mensaje de error y revierte correctamente las inserciones. Para ello insertamos un punto de detención (F9) en la línea que muestra el MessageBox de error. Cuando la ejecución de códgio se pare en el punto de detención, consultamos la base de datos con la siguiente instrucción:

 

SELECT * FROM Persona(NOLOCK)

En este momento podemos observar que se han inserado 100 nuevos registros, pero la transacción aún no ha sido confirmada - por eso debemos especificar NOLOCK para poder ver los datos. Continuamos la ejecución del código y volvemos a lanzar la consulta. La transacción se ha deshecho correctamente y los datos no se ha grabado. Funciona perfectamente.

Pero,¿como se está haciendo commit? ¿ donde se está haciendo el Rollback ? Cuando se crea una transacción utilizando TrasactionScope, se crea una transacción ligera que será controlada por un componente de Windows denominado LTM (Lightweight Transaction Coordinator),  es este componente el encargado de controlar la transacción. Por lo tanto, no es necesario hacer Rollback, una vez que salimos del ambito de la transacción los cambios se deshacen automanticamente si no han sido confirmados. Es decir, cuando salimos de la clausula using que contiene a TransactionScope.

Cuando en la transacción intervienen más de un recursos transaccional (diferentes bases de datos, colas ...) la transacción es promocionada, dejando de ser una transacción ligera - controladas por el LTM - y se convierte en una transacción distribuida - coordinada por el MS DTC (Distributed Transaction Coordinator). Es una técnica realmente potente que abordaremos en posteriores articulos. Como inveniente diremos que el coordinador de transacciones distribuidas en un componente COM+ y que por lo tanto se hace uso de interoperatividad con COM+ (y los problemas que ello puede suponer).

Saludos, DJK


 Versión para imprimir  Foros de consulta


Añadir comentario ... Para preguntar utiliza los foros
Autor:

Título:


Para preguntar utiliza los foros.



 Versión para imprimir

TransactionScope - Simplificando el trabajo con transacciones.
Autor: Pedro Herrarte Sánchez
Visitas: 131 Fecha de publicación: 11/08/2008
Pedro Herrarte, es consultor independiente, ofreciendo sercivios de consultoría, análisis, desarrollo y formación.

Posee mas de diez años de experiencia trabajando para las principales empresas de España.

Es especialista en tecnologías .NET, entornos Web, bases de datos (SQL Server y ORACLE) e integración de sistemas.

Es experto en desarrollo (C#, ASP.NET, VB.Net, T-SQL, PL/SQL, , ASP, CGI , C, Pro*C, Java, Essbase, Vignette, PowerBuilder y Visual Basic ...) y bases de datos (SQL Server y ORACLE).

Es fundador, diseñador y programador de www.devjoker.com.




18/08/2008 SQL Server 2008
Visitas: 39 | Comentarios: 0 | Archivo: Articulos
Categorias: Transact-SQL
Visitas: 131 | Comentarios: 0 | Archivo: Articulos
Categorias: C#|ADO.NET|LinQ
Visitas: 161 | Comentarios: 1 | Archivo: Articulos
Categorias: Humor
Visitas: 154 | Comentarios: 0 | Archivo: Articulos
Categorias: WCF
Visitas: 123 | Comentarios: 0 | Archivo: Articulos
Categorias: WCF
Visitas: 210 | Comentarios: 0 | Archivo: Articulos
Categorias: ASP.NET
Visitas: 278 | Comentarios: 5 | Archivo: Articulos
Categorias: ASP.NET
Visitas: 4990 | Comentarios: 4 | Archivo: Articulos
Categorias: C#|Transact-SQL|LinQ
Visitas: 603 | Comentarios: 1 | Archivo: Articulos
Categorias: Visual Studio
Visitas: 1402 | Comentarios: 1 | Archivo: Articulos
Categorias: Transact-SQL

Útimos temas recibidos en los foros ...
MAQUINAS VIRTUALES por victor ... [WIN 98/NT/2000/XP] 0 19/08/2008
Y lo mismo en WEB por systemat ... [C#] 1 18/08/2008
Manual del minicom de Linux con fotos. por Meta ... [UNIX] 4 17/08/2008
PROGRAMACION por JUANMA ... [Visual Basic .NET] 1 19/08/2008
Conectar ASP con B.D Informix por Franco ... [ASP] 9 02/05/2007
Codigo salir por Jazmin ... [ASP.NET] 1 18/08/2008
EXPORTAR DATOS A ARCHIVOS PLANOS. por WIX ... [ORACLE] 10 06/08/2007
formulario por artdark ... [C#] 2 04/08/2008
Codigo salir por Jazmin ... [ASP.NET] 0 18/08/2008
cambiar de modo un gried view por ivan ... [ASP.NET] 0 18/08/2008
ayuda urgente porfavor por vicancer ... [ASP.NET] 0 18/08/2008
pollo por hajaj ... [Actualidad] 1 15/08/2008

Access CGI JSP ORACLE UNIX
Actualidad HTML/DHTML/XHTML LINUX PHP Visual Basic .NET
ASP ISAPI MS DOS Power Builder Visual Basic 6.0
ASP.NET Java mySQL SQL WIN 98/NT/2000/XP
C# JavaScript Opinion SQL Server

devjoker  Te recomendamos además ...
22/10/2005 Insertar datos. INSERT    forma parte de...Tutorial SQL
11/03/2008 Problemas en la instalación de Visual Studio 2008-Visual studio web authoring component
17/01/2008 Insertar en una Tabla usando Linq2SQL (Linq To SQL)
30/12/2007 Novedades en C# 3.0 - Primeros pasos con LINQ
24/07/2006 SQL Dinamico    forma parte de...Tutorial PL/SQL
09/10/2006 Cadenas de texto    forma parte de...Tutorial C#
22/10/2005 Tablas    forma parte de...Tutorial SQL
09/08/2007 Como mostrar el formato de fecha corta en un gridView
02/09/2007 Procedimientos almacenados en Transact SQL    forma parte de...Tutorial de Transact SQL
25/08/2007 Variables en Transact SQL    forma parte de...Tutorial de Transact SQL

 

Encuesta
Si trabajas con .NET ¿Que entorno utilizas?
[Ver] [Votar]