窗口1:
mysql> begin;
Query OK, 0 rows affected (0.00 sec)
mysql> select * from table1 where id > 99 FOR UPDATE;
+-----+--------+--------+-------+------+
| id | field1 | field2 | field | a |
+-----+--------+--------+-------+------+
| 101 | hola | NULL | NULL | NULL |
| 103 | yo | NULL | NULL | NULL |
| 107 | hey | NULL | NULL | NULL |
+-----+--------+--------+-------+------+
3 rows in set (0.00 sec)
窗口二:
mysql> SELECT thread_id, event_id,
-> object_schema, object_name, index_name,
-> lock_type, lock_mode, lock_status, lock_data
-> FROM performance_schema.data_locks
-> WHERE thread_id = 279\G;
*************************** 1. row ***************************
thread_id: 279
event_id: 28
object_schema: laravel_doc
object_name: table1
index_name: NULL
lock_type: TABLE
lock_mode: IX
lock_status: GRANTED
lock_data: NULL
*************************** 2. row ***************************
thread_id: 279
event_id: 28
object_schema: laravel_doc
object_name: table1
index_name: PRIMARY
lock_type: RECORD
lock_mode: X
lock_status: GRANTED
lock_data: supremum pseudo-record
*************************** 3. row ***************************
thread_id: 279
event_id: 28
object_schema: laravel_doc
object_name: table1
index_name: PRIMARY
lock_type: RECORD
lock_mode: X
lock_status: GRANTED
lock_data: 101
*************************** 4. row ***************************
thread_id: 279
event_id: 28
object_schema: laravel_doc
object_name: table1
index_name: PRIMARY
lock_type: RECORD
lock_mode: X
lock_status: GRANTED
lock_data: 103
*************************** 5. row ***************************
thread_id: 279
event_id: 28
object_schema: laravel_doc
object_name: table1
index_name: PRIMARY
lock_type: RECORD
lock_mode: X
lock_status: GRANTED
lock_data: 107
5 rows in set (0.00 sec)
原始表格:
+-----+--------+--------+-------+------+
| id | field1 | field2 | field | a |
+-----+--------+--------+-------+------+
| 3 | hello | 1 | NULL | NULL |
| 97 | hi | 2 | NULL | NULL |
| 101 | hola | 3 | NULL | NULL |
| 103 | yo | 4 | NULL | NULL |
| 107 | hey | 5 | NULL | NULL |
+-----+--------+--------+-------+------+
间隙锁不显示,它们应该显示,因为我检查了,它阻止我插入,例如id = 102(在窗口2中)
“id”是主键
对于锁定读取(SELECT与FOR UPDATE或FOR SHARE)、UPDATE和DELETE语句,所采用的锁取决于语句使用的是具有唯一搜索条件的唯一索引还是范围类型搜索条件。
对于具有唯一搜索条件的唯一索引,InnoDB只锁定找到的索引记录,而不锁定它之前差距。
对于其他搜索条件和非唯一索引,InnoDB会锁定扫描的索引范围,使用间隙锁或下一个键锁阻止其他会话向该范围覆盖的间隙中插入内容。有关间隙锁和下一个键锁的信息,请参见第15.7.1节“InnoDB锁定”。
https://dev.mysql.com/doc/refman/8.0/en/innodb-locks-set.html
此外,它们应该出现,因为是唯一索引,而不是范围搜索,而不是唯一搜索条件
1条答案
按热度按时间tyg4sfes1#
事实上它们是,只是肉眼看不见:
记录X =记录锁定+间隔锁定=下一个键锁定
https://dev.mysql.com/blog-archive/innodb-data-locking-part-2-locks/
S →就像S,REC_NOT_GAP和S,GAP同时组合在一起,所以它是对行的共享访问权限,并防止在它之前插入。
X →就像是X,REC_NOT_GAP和X,GAP同时组合在一起,所以它是对该行的独占访问权限,并防止在该行之前插入。
https://xhinliang.win/2021/09/backend/innodb-locks/
LOCK_MODE有几个选项