Listo para trabajar
Crear tabla tb_innodb_lock
eliminar tabla si existe test_innodb_lock; CREAR TABLA test_innodb_lock ( a INT (11), b VARCHAR (20) ) ENGINE INNODB DEFAULT charset = utf8; insertar en test_innodb_lock valores (1, 'a'); insertar en test_innodb_lock valores (2, 'b'); insertar en test_innodb_lock valores (3, 'c'); insertar en test_innodb_lock valores (4, 'd'); insertar en test_innodb_lock valores (5, 'e');
Crear índice
crear el índice idx_lock_a en test_innodb_lock (a); crear el índice idx_lock_b en test_innodb_lock (b);
Demostración de bloqueo de MySQL
Primero cambie la transacción de confirmación automática a confirmación manual:
set autocommit=0;
Iniciamos dos ventanas de sesión A y B, simulando una agarrando la cerradura y la otra bloqueándose sin agarrar.
Bloqueo de fila (escritura y lectura)
Una ejecución de ventana
actualizar test_innodb_lock set b = 'a1' donde a = 1;
SELECCIONAR * de test_innodb_lock;
Podemos ver el resultado actualizado en la ventana A
Ejecución de la ventana B
SELECCIONAR * de test_innodb_lock;
Podemos ver que la ventana B no puede ver los resultados actualizados, pero aún se ven los datos antiguos, debido a que el registro de a = 1 fue bloqueado por la instrucción SQL ejecutada por la ventana A y la operación de confirmación no se ejecutó. Entonces, la ventana B todavía ve los datos antiguos. Esta es la "lectura confirmada" en el nivel de aislamiento de MySQL.
La ventana A ejecuta la operación de confirmación
COMETER;
Consulta de la ventana B
SELECCIONAR * de test_innodb_lock;
En este momento, encontramos que la ventana B ha leído los datos más recientes.
Bloqueo de fila (escribir y escribir)
La ventana A realiza la actualización de un registro = 1
actualizar test_innodb_lock set b = 'a2' donde a = 1;
En este momento, no hay confirmación, y la ventana A mantiene el bloqueo.
La ventana B también actualiza el registro de a = 1
actualizar test_innodb_lock set b = 'a3' donde a = 1;
Como puede ver, la ventana B se ha bloqueado porque la ventana A aún no ha ejecutado el compromiso y aún mantiene el bloqueo. La ventana B no puede agarrar la cerradura registrada en la fila a = 1, por lo que se ha bloqueado esperando.
La ventana A ejecuta la operación de confirmación
COMETER;
Cambios en la ventana B
Puede ver que la ventana B se ha ejecutado correctamente en este momento
Bloqueo de mesa
Cuando un índice falla, el bloqueo de fila se actualizará a un bloqueo de tabla Uno de los métodos para el fallo de índice es cambiar el índice de forma automática o manual. El campo a en sí es un número entero, agregamos comillas, se convierte en una Cadena, esta vez el índice no será válido.
La ventana A actualiza el registro de a = 1
actualizar test_innodb_lock set b = 'a4' donde a = 1 o a = 2;
La ventana B actualiza el registro de a = 2
actualizar test_innodb_lock set b = 'b1' donde a = 3;
En este momento, se descubrió que aunque las filas actualizadas de la ventana A y B eran diferentes, la ventana B todavía estaba bloqueada porque el índice de la ventana A falló, lo que provocó que el bloqueo de fila se actualizara a bloqueo de tabla, bloqueando toda la tabla y la ventana de índice. B está bloqueado.
La ventana A ejecuta la operación de confirmación
COMETER;
Cambios en la ventana B
Puede ver que la ventana B se ha ejecutado correctamente en este momento
Bloqueo de espacios
¿Qué es un bloqueo de espacio?
Cuando usamos condiciones de rango para consultar datos, InnoDB bloqueará los datos en este rango. Por ejemplo, hay 4 datos con id: 1, 3, 5 y 7, buscamos datos en el rango de 1-7. Entonces 1-7 se bloqueará. 2, 4 y 6 también están en el rango de 1-7, pero estos registros de datos no existen, estos 2, 4 y 6 se denominan huecos.
El daño del bloqueo de brecha
Al buscar en el rango, se bloquearán todos los datos de todo el rango. Incluso algunos datos que no existen en este rango se bloquearán de forma inocente. Por ejemplo, quiero insertar 2 en 1, 3, 5 y 7, esta vez 1 -7 está bloqueado y 2 no se puede insertar en absoluto. En algunos escenarios, tendrá un gran impacto en el rendimiento.
Demostración de bloqueo de espacios
Primero modificamos el valor del campo a a 1, 3, 5, 7, 9
La ventana A actualiza los datos en el rango a = 1 ~ 7
actualizar test_innodb_lock set b = 'b5' donde a> 1 y a <7;
La ventana B inserta datos en a = 2
insertar en test_innodb_lock valores (2, "b6");
En este momento, se encuentra que la operación de actualización a = 2 en la ventana B ha estado esperando, porque los datos en el rango de 1 ~ 7 están bloqueados por el espacio y bloqueados. Solo cuando la ventana A ejecuta el compromiso, la ventana B a = 2 puede la actualización tener éxito
Análisis de bloqueo de filas
Ejecutar comandos de análisis SQL
mostrar el estado como 'innodb_row_lock%';
Descripción de nombre de variable
Innodb_row_lock_current_waits: el número de bloqueos en espera actualmente.
Innodb_row_lock_time: el período de tiempo desde el inicio del sistema hasta el bloqueo actual.
Innodb_row_lock_time_avg: el tiempo promedio que se pasa esperando el bloqueo cada vez.
Innodb_row_lock_time_max: el tiempo más largo que tarda la cerradura en esperar desde que se inicia el sistema.
Innodb_row_lock_waits: el número total de esperas para bloqueos después de que se inició el sistema hasta ahora.
Al final
Gracias a todos por ver aquí, el artículo tiene deficiencias, y son bienvenidos a señalar; si creen que está bien escrito, por favor denme el visto bueno.