MySQL/InnoDB storage engine

Insert intention lock

lejpower 2021. 9. 6. 22:53

"Insert intention lock"은 레코드 인서트 전에 INSERT조작에 의해서 설정되는 Gap lock의 일종입니다. 이 락(잠금)은 동일한 인덱스 갭에 인서트된 여러 트랜잭션이 갭(간격) 내에서 동일한 위치에 인서트되지 않을 경우 서로 기다릴 필요가 없도록 인서트하려는 의도를 나타냅니다.값이 4와 7의 인덱스 레코드가 존재한다고 가정합니다. 각각 5와 6의 값을 인서트하려는 트랜잭션은 인서트된 행에 대한 단독 잠금을 얻기 전에 각각 4와 7 사이의 간격을 인서트 인텐션 락으로 잠그지만 행이 충돌하지 않으므로 서로 차단하지 않습니다.

다음 예에서는 인서트된 레코드에 대한 배타적 잠금을 얻기 전에 인서트 인텐션 락을 실행하는 트랜잭션을 보여 줍니다. 이 예에는 A와 B라는 두 고객이 포함됩니다.

 

클라이언트 A는 2개의 인덱스 레코드(90및 102)를 포함하는 테이블을 만들어 100을 넘는 ID를 가진 인덱스 레코드에 배타적 잠금 설정하는 트랜잭션을 시작합니다. 배타적 잠금은 레코드 102앞의 갭 락을 포함합니다.

mysql> CREATE TABLE child (id int(11) NOT NULL, PRIMARY KEY(id)) ENGINE=InnoDB;
mysql> INSERT INTO child (id) values (90),(102);

mysql> START TRANSACTION;
mysql> SELECT * FROM child WHERE id > 100 FOR UPDATE;
+-----+
| id  |
+-----+
| 102 |
+-----+

 

클라이언트 B는 트렌젝션을 시작하고, 갭에 레코드를 인서트 합니다. 트렌젝션은 배타적잠금의 획득을 기다리는 동안 인서트 인텐션 락을 획득합니다.

mysql> START TRANSACTION;
mysql> INSERT INTO child (id) VALUES (101);

인서트 인텐션 락의 트랜젝션 데이터는 SHOW ENGINE INNODB STATUS 그리고 InnoDB monitor 출력에 다음과 같이 나타나게 됩니다.

RECORD LOCKS space id 31 page no 3 n bits 72 index `PRIMARY` of table `test`.`child`
trx id 8731 lock_mode X locks gap before rec insert intention waiting
Record lock, heap no 3 PHYSICAL RECORD: n_fields 3; compact format; info bits 0
 0: len 4; hex 80000066; asc    f;;
 1: len 6; hex 000000002215; asc     " ;;
 2: len 7; hex 9000000172011c; asc     r  ;;...

'MySQL > InnoDB storage engine' 카테고리의 다른 글

read-ahead  (0) 2021.08.31