sql - tipos - ¿Qué hace una transacción en torno a una sola declaración?
transacciones en sql server pdf (5)
Como dijo Charles Bretana, "no hace nada", nada además de lo que ya está hecho.
¿Has oído hablar de los requisitos "ACID" de una base de datos relacional? Esa "A" significa Atomic, lo que significa que la instrucción funciona en su totalidad, o no lo hace, y mientras se realiza la declaración, no se pueden hacer otras consultas sobre los datos afectados por esa consulta. BEGIN TRANSACTION / COMMIT "extiende" esta funcionalidad de bloqueo al trabajo realizado por varias instrucciones, pero no agrega nada a declaraciones individuales.
Sin embargo, el registro de transacciones de la base de datos siempre se escribe cuando se modifica una base de datos (insertar, actualizar, eliminar). Esta no es una opción, un hecho que tiende a irritar a la gente. Sí, hay rareza con inserciones masivas y modos de recuperación, pero todavía se escribe.
Voy a mencionar los niveles de aislamiento aquí también. Alterar con esto afectará a los comandos individuales, pero al hacerlo no hará que una consulta envuelta en una transacción declarada realice una consulta diferente a una consulta "independiente". (Tenga en cuenta que pueden ser muy poderosos y muy peligrosos con las transacciones declaradas en varias declaraciones). Tenga en cuenta también que "nolock" no se aplica a las inserciones / actualizaciones / eliminaciones: esas acciones siempre requieren bloqueos.
Entiendo cómo una transacción puede ser útil para coordinar un par de actualizaciones. Lo que no entiendo es incluir declaraciones únicas en las transacciones, que es el 90% de lo que he visto en mi vida. De hecho, en el código de la vida real, es más común en mi experiencia encontrar una serie de transacciones lógicamente relacionadas, cada una envuelta en su propia transacción, pero el todo no está envuelto en una transacción.
En MS-SQL, ¿hay alguna ventaja de incluir selecciones simples, actualizaciones únicas, inserciones individuales o eliminaciones únicas en una transacción?
Sospecho que esta es una programación supersticiosa.
Cuando inicia una transacción explícita y emite un DML
, los recursos bloqueados por la declaración permanecen bloqueados, y los resultados de la declaración no son visibles desde fuera de la transacción hasta que la confirme o restituya manualmente.
Esto es lo que puede o no necesitar.
Por ejemplo, es posible que desee mostrar los resultados preliminares al mundo exterior mientras mantiene un bloqueo sobre ellos.
En este caso, se inicia otra transacción que coloca una solicitud de bloqueo antes de que el primero se comprometa, evitando así la condición de carrera.
Las transacciones implícitas se comprometen o se retrotraen inmediatamente después de que la instrucción DML
complete o falle.
No hace nada. Todas las sentencias SQL individuales, (con raras excepciones como Inserciones masivas sin registro o Truncar tabla) son automáticamente "En una transacción", explícitamente lo diga o no ... (incluso si insertan, actualizan o eliminan millones de filas) .
EDITAR: basado en el comentario de @ Phillip a continuación ... En las versiones actuales de SQL Server, incluso las inserciones masivas y la tabla truncada escriben algunos datos en el registro de transacciones, aunque no tanto como otras operaciones. La distinción fundamental desde una perspectiva transaccional es que en estos otros tipos de operaciones, los datos en las tablas de la base de datos que se modifican no están en el registro en un estado que le permite deshacerse.
Todo esto significa que los cambios que la declaración hace a los datos en la base de datos se registran en el registro de transacciones para que puedan deshacerse si falla la operación.
La única función que proporcionan los comandos "Comenzar transacción", "Confirmar transacción" y "Realizar transacción Rollback" es permitirle colocar dos o más instrucciones SQL individuales en la misma transacción.
EDITAR: (para reforzar el comentario de las marcas ...) SÍ, esto podría atribuirse a la programación "supersticiosa", o podría ser un indicio de un malentendido fundamental de la naturaleza de las transacciones de bases de datos. Una interpretación más caritativa es que es simplemente el resultado de una sobre-aplicación de consistencia que es inapropiada y otro ejemplo más del eufemismo de Emerson que:
Una consistencia tonta es el duende de las mentes pequeñas,
adorado por pequeños estadistas y filósofos y teólogos
Para mí, envolver una sola declaración en una transacción significa que tengo la capacidad de deshacerla si, por ejemplo, olvido una cláusula WHERE al ejecutar una declaración UPDATE manual y única. Me ha salvado un par de veces.
p.ej
--------------------------------------------------------------
CREATE TABLE T1(CPK INT IDENTITY(1,1) NOT NULL, Col1 int, Col2 char(3));
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
INSERT INTO T1 VALUES (101, ''abc'');
SELECT * FROM T1
--------------------------------------------------------------
/* MISTAKE SCENARIO (run each row individually) */
--------------------------------------------------------------
BEGIN TRAN YOUR_TRANS_NAME_1; /* open a trans named YOUR_TRANS_NAME_1 */
UPDATE T1 SET COL2 = NULL; /* run some update statement */
SELECT * FROM T1; /* OOPS ... forgot the where clause */
ROLLBACK TRAN YOUR_TRANS_NAME_1; /* since it did bad things, roll it back */
SELECT * FROM T1; /* tans rolled back, data restored. */
--------------------------------------------------------------
/* NO MISTAKES SCENARIO (run each row individually) */
--------------------------------------------------------------
BEGIN TRAN YOUR_TRANS_NAME_2;
UPDATE T1 SET COL2 = ''CBA'' WHERE CPK = 4; /* run some update statement */
SELECT * FROM T1; /* did it correctly this time */
COMMIT TRAN YOUR_TRANS_NAME_2 /* commit (close) the trans */
--------------------------------------------------------------
DROP TABLE T1
--------------------------------------------------------------
Una posible excusa es que esa única declaración podría hacer que un montón de otros SQL se ejecuten a través de desencadenantes, y que están protegiendo contra algo que va mal allí, aunque esperaría que cualquier DBMS tenga el sentido común para usar transacciones implícitas en de la misma manera ya
La otra cosa que puedo pensar es que algunas API te permiten deshabilitar la confirmación automática, y el código está escrito por si alguien lo hace.