Comentarios en: Transacciones y modos de aislamiento en SQL Server y .NET https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/ El blog de Scientia® Soluciones Informáticas Mon, 21 Sep 2020 15:07:57 +0000 hourly 1 Por: blas https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-14494 Fri, 06 Sep 2013 13:10:39 +0000 http://www.programandoamedianoche.com/?p=278#comment-14494 un poco mas especifico seria que el proceso completo consite en la seleccion del ultimo numero, sumarle el siguiente y guardar el registro de la factura, todo en un mismo proceso…

]]>
Por: Roger https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-6067 Fri, 02 Mar 2012 16:02:13 +0000 http://www.programandoamedianoche.com/?p=278#comment-6067 Muy claro, muchas gracias. Así tendría que hacer Microsoft su documentación de MSDN. Me ha aclarado el tema, porque estaba mirando una aplicación en ASP.NET en la que tenía un problema de bloqueos, y veo que el nivel de isolation está bien aplicado.

]]>
Por: Keylin https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-228 Wed, 03 Nov 2010 14:58:28 +0000 http://www.programandoamedianoche.com/?p=278#comment-228 Me parece excelente tu artículo, llevo mucho tiempo tratando de averiguar sobre este tema pero resulta un poco difícil…

Gracias por esta publicación tan buena. 😀

]]>
Por: Toño https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-222 Thu, 21 Oct 2010 15:32:36 +0000 http://www.programandoamedianoche.com/?p=278#comment-222 Disculpa tengo unas preguntas, espero me puedas ayudar:

1. existe algun posibilidad de que teniendo un nivel de aislamiento read uncommited o read commited no se pueda realizar un insert mientras se realiza un select a la misma tabla.

2. puede pasar que teniendo algun nivel de aislamiento un select no termine debido a que en una transaccion de tipo insert,update o delete entre antes que terminara el select y no hace un commit.

3. como puedo saber que nivek de aislamiento posee actualmente mi base de datos.

Muchas gracias, ojala me puedas ayudar.

]]>
Por: Ctezo https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-207 Mon, 13 Sep 2010 04:02:33 +0000 http://www.programandoamedianoche.com/?p=278#comment-207 muy buen documento, esta muy interesante

Saludos

]]>
Por: Dario Krapp https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-109 Thu, 14 Jan 2010 21:05:20 +0000 http://www.programandoamedianoche.com/?p=278#comment-109 En respuesta a Alex_TS.

Muchas gracias por consultar y perdón por la demora, voy a intentar ir contestando por punto.

1. Sin hacer uso de transacciones, considerando las operaciones sobre la base de datos a nivel de instrucción; con ADO.NET, ¿como implementarías el bloqueo pesimista?.

Alguna vez y hace unos cuantos años tuve la oportunidad de conocer un proyecto hecho en VB6.0 con SQLServer 7.0 donde los bloqueos eran manejados completamente a mano y eran pesimistas, esto se lograba de la siguiente manera;
Las tablas poseian un registro extra denominado UserId (Id de usuario) donde cuando un usuario tomaba un registro su Id se grababa en ese campo y se pasaba a NULL cuando el mismo era liberado. Este esquema de
funcionamiento permitía manejar los bloqueos ya que cuando un usuario quería acceder a un registro, la aplicación podía saber si el mismo se encontraba bloqueado o no leyendo el campo UserId. Este modo de funcionamiento
añadía a los problemas clásicos de escalabilidad que poseen los bloqueos pesimistas nuevos problemas propios de la implementación, ya que si un usuario abandonaba la aplicación inesperadamente el registro quedaba bloquedo y aunque es
posible encontrar métodos para evitar este problema, mi punto de vista es que no es para nada recomendable utilizar bloqueos.

2. Si por ejemplo empleo un DataAdapter (o TableAdapter) para realizar operaciones sobre la base de datos, ¿qué tipo de bloqueo se aplica por defecto?, ¿como lo puedo modificar sin emplear transacciones?.

Un DataAdapter es un objeto que te va a permitir leer datos de un source y moverlos a memoria en un DataSet y efectuar también el paso contrario, o sea moverlos nuevamente al source luego de haberlos modificado en memoria, el método
Fill va a transferir los datos del source a memoria y el método Update va a leer los datos de memoria y los va a transferir nuevamente al source, por lo que el funcionamiento por defecto es el comportamiento «el último gana»,
para probarlo podés crear una tabla simple en SQL Server, te dejo un ejemplo:

CREATE TABLE [dbo].[Datos1](
[ID] [int] NOT NULL,
[Numero] [int] NOT NULL,
[Descripcion] [nvarchar](50) NOT NULL
) ON [PRIMARY]

y utilizar el siguiente código

SqlConnection SqlCn = new SqlConnection(WebConfigurationManager.ConnectionStrings[«Cn1»].ConnectionString);
SqlCn.Open();

//DataAdapter
SqlDataAdapter SqlDa = new SqlDataAdapter(«SELECT * FROM Datos1», SqlCn);
SqlDa.AcceptChangesDuringUpdate = true;

//Comando para actualización
SqlCommand command = new SqlCommand(«UPDATE Datos1 SET Descripcion = @Descripcion WHERE ID = @ID», SqlCn);

//Parámetro Descripcion
SqlParameter parameterDesc = command.Parameters.Add(«@Descripcion», SqlDbType.NVarChar, 50);
parameterDesc.SourceVersion = DataRowVersion.Current;
parameterDesc.SourceColumn = «Descripcion»;

//Parámetro ID
SqlParameter parameterID = command.Parameters.Add(«@ID», SqlDbType.Int);
parameterID.SourceVersion = DataRowVersion.Original;
parameterID.SourceColumn = «ID»;
SqlDa.UpdateCommand = command;

//Lectura de datos
DataSet DataSetD1 = new DataSet();
SqlDa.Fill(DataSetD1, «TableDatos1»);

//Actualización en memoria
foreach (DataRow DtRow in DataSetD1.Tables[0].Rows)
DtRow[«Descripcion»] = DtRow[«Descripcion»] + «Z»;

//Actualización en la base de datos
SqlDa.Update(DataSetD1.Tables[«TableDatos1»]);

Donde básicamente se modifica el valor del campo Descripcion para todos los registros, si ponés un break point en la última sentencia «SqlDa.Update(DataSetD1.Tables[«TableDatos1″]);» y antes que se ejecute vas a un query analizer
y ejecutás lo siguiente:

update Datos1 set Descripcion = Descripcion + ‘i’

antes de ejecutar la sentencia SqlDa.Update(DataSetD1.Tables[«TableDatos1»]); desde VS vas a ver que todos los registros poseen una «i» al final del campo Descripción, pero si luego presionas F5 en VS y ejecutás la sentencia
SqlDa.Update(DataSetD1.Tables[«TableDatos1»]); vas a notar que el cambio hecho desde el query analizer se ha perdido, ya que el update ha tomado los valores de memoria del DataSet (que aún no tenian el caracter i agregado) y los ha transferido al SQL,
si haciendo la misma prueba borrás un registro desde el Query Analizer, vas a notar que se produce un error en la sentencia SqlDa.Update(DataSetD1.Tables[«TableDatos1»]); ya que no podrá actualizar registros que han sido eliminados externamente, en este caso te quedarán
algunos registros modificados (previos al error) o otros no (los sucesivos al error).

3. Si por el contrario realizo las operaciones con un objeto de tipo OleDbCommand, en un escenario conectado, ¿que tipo de bloqueo se aplica por defecto?, ¿como lo puedo modificar sin emplear transacciones?.

De esto podrás pasarme un poco de código para entender como sería el caso.

4. ¿Como puedo implementar el bloqueo de tipo «el último gana»?

Este tipo de funcionamiento es el más sencillo de utilizar ya que podés leer la información necesaria de la base de datos, cortar la conexión, modificar la informacíon en forma desconectada y
reenviar las modificaciones al servidor de base de datos en una nueva conexion (en una transaccion si hay varias tablas involucradas). En este esquema, si dos usuarios leen la misma información el último en grabar es quien
preservará sus cambios.
Fuera de los puntos anteriores, para una aplicación actual y sin utilizar frameworks de entidades y esas cosas que estan tan de moda actualmente, yo particularmente pensaría en dos enfoques posibles, el enfoque «el último gana» y el enfoque «optimista»,
dejando las transacciones para los casos donde haya varias tablas involucradas en una misma entidad. El enfoque «el último gana» es como te comentaba previamente mientras que para el enfoque optimista, podés incluir una columna extra con un numero de versión,
al momento de actualizar los datos leidos previamente deberías verificar que el numero de versíon actual sea el mismo que leistes previamente, en caso afirmativo podrás modificar los datos incrementando el numero de version de la columna, en caso negativo deberás tomar alguna acción ya que la información ha sido
modificada externamente. Otra opción es en lugar de utilizar una columna version, emplear una columna datestamp para comparar contra fechas.

5. Cuando se emplean transacciones, ¿los niveles de aislamiento definen el tipo de bloqueo?

Si, para que el motor de base de datos pueda asegurarte el nivel de aislamiento que le estás pidiendo, el mismo deberá efectuar un tipo de bloqueo determinado, por lo que el tipo de bloqueo dependerá del nivel de aislamiento solicitado.

La verdad esq tengo un poco de «empanada mental» con estos estos conceptos. A ver si me lo puedes aclarar un poco.

Yo creo que hay dos cosas distintas;
La primera es que cuando hay varias tablas involucradas a modificar en una misma operación de base de datos deben utilizarse transacciones y el nivel de aislamiento definirá que bloqueos realizará el motor de base de datos en dicha operación y eso es lo que intenta comentar el articulo.
La segunda es qué tipo de bloqueo se debe utilizar en una aplicación para que un usuario no modifique los datos que otro esta modificando paralelamente, creo si no entendí mal que es sobre este tipo de bloqueos sobre los cuales estás interesado, y según mi punto de vista, las opciones son «el último gana» o el enfoque «optimista».

Espero que estas repuestas te hayan servido

Saludos!

]]>
Por: Alex_TS https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-108 Fri, 08 Jan 2010 03:24:30 +0000 http://www.programandoamedianoche.com/?p=278#comment-108 Buen artículo!, lo has explicado con bastante calidad.

Lo único que te recomendaría es que pusieras un fondo claro bajo el texto, pero el contenido mola.

Al respecto del tema que has tratado en este artículo, tengo ciertas dudas, son las siguientes:

1. Sin hacer uso de transacciones, considerando las operaciones sobre la base de datos a nivel de instrucción; con ADO.NET, ¿como implementarías el bloqueo pesimista?.

2. Si por ejemplo empleo un DataAdapter (o TableAdapter) para realizar operaciones sobre la base de datos, ¿qué tipo de bloqueo se aplica por defecto?, ¿como lo puedo modificar sin emplear transacciones?.

3. Si por el contrario realizo las operaciones con un objeto de tipo OleDbCommand, en un escenario conectado, ¿que tipo de bloqueo se aplica por defecto?, ¿como lo puedo modificar sin emplear transacciones?.

4. ¿Como puedo implementar el bloqueo de tipo «el último gana»?

5. Cuando se emplean transacciones, ¿los niveles de aislamiento definen el tipo de bloqueo?

La verdad esq tengo un poco de «empanada mental» con estos estos conceptos. A ver si me lo puedes aclarar un poco.

Gracias y saludos!

]]>
Por: lrocker https://www.programandoamedianoche.com/2009/04/transacciones-y-modos-de-aislamiento-en-sql-server-y-adonet/#comment-42 Wed, 03 Jun 2009 23:05:00 +0000 http://www.programandoamedianoche.com/?p=278#comment-42 Muy buen documento, muchas gracias por la publicación.
Saludos,

]]>