Search
Duplicate

5. 잠금

table lock

β€’
κ°œλ³„ ν…Œμ΄λΈ” λ‹¨μœ„λ‘œ μ„€μ •λ˜κ³  λͺ…μ‹œμ , λ¬΅μ‹œμ μœΌλ‘œ 락을 νšλ“
β€’
InnoDB ν…Œμ΄λΈ”μ˜ 경우 μŠ€ν† λ¦¬μ§€ 엔진 μ°¨μ›μ—μ„œ λ ˆμ½”λ“œ 기반 잠금 제곡 -> λ‹¨μˆœ 데이터 λ³€κ²½ 쿼리둜 인해 λ¬΅μ‹œμ  ν…Œμ΄λΈ” 락 μ„€μ • X, DDL κ²½μš°μ—λ§Œ ν…Œμ΄λΈ” 락 μ„€μ •
# session 1 lock tables morak.appointment read; # session 2 select * from morak.appointment; # 성곡 update morak.appointment set status='OPEN' where id=1; # λŒ€κΈ°μ€‘ # session 1 unlock tables; # update 쿼리 μ‹€ν–‰
SQL
볡사
# session 1 lock tables morak.appointment write; # session 2 update morak.appointment set status='OPEN' where id=1; # λŒ€κΈ°μ€‘ select * from morak.appointment; # λŒ€κΈ°μ€‘ # session 1 unlock tables; #쿼리 μ‹€ν–‰
SQL
볡사

named lock

β€’
get_lock() ν•¨μˆ˜λ₯Ό μ΄μš©ν•΄ μž„μ˜μ˜ λ¬Έμžμ—΄μ— λŒ€ν•΄ 잠금 μ„€μ •
β€’
ν…Œμ΄λΈ”, λ ˆμ½”λ“œ 등에 κ±°λŠ” 것이 μ•„λ‹ˆλΌ νŠΉμ • λ¬Έμžμ—΄μ— λŒ€ν•΄ 잠금
β€’
8.0 λΆ€ν„° μ€‘μ²©ν•΄μ„œ μ‚¬μš© κ°€λŠ₯
# was λΌλŠ” μ΄λ¦„μ˜ 락을 νšλ“, 락이 이미 있으면 2초만 λŒ€κΈ° select get_lock('was', 2); # was λΌλŠ” μ΄λ¦„μ˜ 락이 free ν•œμ§€ 확인 0이면 X, 1이면 O select is_free_lock('was'); # was λΌλŠ” μ΄λ¦„μ˜ 락 ν•΄μ œ select release_lock('was');
SQL
볡사
β€’ λΆ„μ‚° ν™˜κ²½μ—μ„œ μ‚¬μš©, μš”μ²­μ— λŒ€ν•œ key κ°’μœΌλ‘œ 해석 κ°€λŠ₯

metadata lock

β€’
잘 λͺ¨λ₯΄κ² λ‹€. 쑰금 더 κ³΅λΆ€ν•œ 뒀에 λ‹€μ‹œ 보자

InnoDB μŠ€ν† λ¦¬μ§€ 엔진 잠금

β€’
μŠ€ν† λ¦¬μ§€ 엔진 λ‚΄λΆ€μ—μ„œ λ ˆμ½”λ“œ 기반의 잠금 방식 νƒ‘μž¬
β€’
λ™μ‹œμ„± 처리 κ°€λŠ₯
β€’
information_schema 와 performance_schema 둜 잠금 확인 κ°€λŠ₯

record lock

β€’
λ ˆμ½”λ“œ μžμ²΄κ°€ μ•„λ‹Œ 인덱슀의 λ ˆμ½”λ“œλ₯Ό 잠금
β€’
μΈλ±μŠ€κ°€ ν•˜λ‚˜λ„ μ—†λŠ” ν…Œμ΄λΈ”λ„ λ‚΄λΆ€μ μœΌλ‘œ μžλ™ μƒμ„±λœ ν΄λŸ¬μŠ€ν„°λ“œ 인덱슀λ₯Ό μ΄μš©ν•΄ 잠금 μ„€μ •
β€’
PK λ˜λŠ” unique μΈλ±μŠ€μ— μ˜ν•œ λ³€κ²½ μž‘μ—…μ—μ„œλŠ” λ ˆμ½”λ“œμ— 락

gap lock

β€’
λ ˆμ½”λ“œμ™€ λ°”λ‘œ μΈμ ‘ν•œ λ ˆμ½”λ“œ μ‚¬μ΄μ˜ κ°„κ²©λ§Œμ„ 잠금
β€’
λ ˆμ½”λ“œμ™€ λ ˆμ½”λ“œ μ‚¬μ΄μ˜ 간격에 μƒˆλ‘œμš΄ λ ˆμ½”λ“œκ°€ μƒμ„±λ˜λŠ” 것을 μ œμ–΄
β€’
λ„₯슀트 ν‚€ 락의 μΌλΆ€λ‘œ 자주 μ‚¬μš©

next key lock

β€’
λ ˆμ½”λ“œ 락 + κ°­ 락
β€’
λ°”μ΄λ„ˆλ¦¬ λ‘œκ·Έμ— κΈ°λ‘λ˜λŠ” 쿼리가 λ ˆν”Œλ¦¬μΉ΄ μ„œλ²„μ—μ„œ 싀행될 λ•Œ μ†ŒμŠ€ μ„œλ²„μ—μ„œ λ§Œλ“€μ–΄ λ‚Έ 결과와 λ™μΌν•œ κ²°κ³Όλ₯Ό λ§Œλ“€μ–΄λ‚΄λ„λ‘ 보μž₯ν•˜λŠ” 것이 μ£Όλͺ©μ 
β€’
λ°λ“œλ½, λ‹€λ₯Έ νŠΈλž™μž­μ…˜ λŒ€κΈ° μƒνƒœ 자주 λ°œμƒ
β€’
λ°”μ΄λ„ˆλ¦¬ 둜그 포맷을 ROW 포맷 ν˜•νƒœλ‘œ λ°”κΏ”μ„œ λ„₯슀트 ν‚€ λ½μ΄λ‚˜ κ°­ 락을 μ€„μ΄λŠ” 것이 μ’‹μŒ
β—¦
statement 포맷의 λ°”μ΄λ„ˆλ¦¬ λ‘œκ·Έκ°€ κ°€μ§€λŠ” 단점을 많이 해결해쀄 수 μžˆμ–΄μ„œ MySQL 8.0 μ—μ„œλŠ” ROW 포맷의 λ°”μ΄λ„ˆλ¦¬ λ‘œκ·Έκ°€ κΈ°λ³Έ μ„€μ •

auto increment lock(μžλ™ 증가 락)

β€’
auto increment λ₯Ό μœ„ν•œ ν…Œμ΄λΈ” μˆ˜μ€€μ˜ 잠금
β€’
insert, replace 같은 μƒˆλ‘œμš΄ λ ˆμ½”λ“œλ₯Ό μ €μž₯ν•˜λŠ” μΏΌλ¦¬μ—μ„œλ§Œ ν•„μš”, update, delete μ—μ„œλŠ” 락 X
β€’
νŠΈλžœμž­μ…˜κ³Ό 관계없이 insert, replace λ¬Έμž₯μ—μ„œ auto increment 값을 κ°€μ Έμ˜€λŠ” μˆœκ°„λ§Œ 락이 κ±Έλ Έλ‹€κ°€ ν•΄μ œ
β€’
μ§€κΈˆκΉŒμ§€ MySQL 5.0 μ΄ν•˜ 방식
β€’
5.1 μ΄μƒλΆ€ν„°λŠ” innodb_auto_inc_lock_mode λ³€μˆ˜λ₯Ό μ΄μš©ν•˜μ—¬ μž‘λ™ 방식 λ³€κ²½ κ°€λŠ₯
β—¦
8.0 λΆ€ν„°λŠ” innodb_auto_inc_lock_mode=2 κ°€ κΈ°λ³Έ -> λ°”μ΄λ„ˆλ¦¬ 둜그 포맷이 STATEMENT μ—μ„œ ROW 둜 기본값이 λ³€κ²½λ˜μ—ˆκΈ° λ•Œλ¬Έ

index 와 잠금

β€’
λ³€κ²½ν•΄μ•Ό ν•  λ ˆμ½”λ“œλ₯Ό μ°ΎκΈ° μœ„ν•΄ κ²€μƒ‰ν•œ 인덱슀의 λ ˆμ½”λ“œλ₯Ό λͺ¨λ‘ 락을 건닀
인덱슀 리프 λ…Έλ“œ
city
id
daejeon
5
dongtan
6
seoul
1
seoul
2
seoul
4
ulsan
3
ν…Œμ΄λΈ”
id
name
city
1
eden
seoul
2
ellie
seoul
3
winnie
ulsan
4
kkara
seoul
5
chalee
daejeon
6
albur
dongtan
# session 1 start transaction; update member set name='eden2' where id=1; # id = 1 에 λ ˆμ½”λ“œ 락 # city = seoul 에 λ ˆμ½”λ“œ 락 # session 2 update member set name='eden2' where id=1;# λŒ€κΈ° update member set name='eden2' where city='seoul'; # λŒ€κΈ° update member set name='eden2' where name='ellie'; # λŒ€κΈ° update member set name='eden2' where id=2; # complete update member set name='eden2' where city='ulsan'; # complete
SQL
볡사
β€’
μΈλ±μŠ€κ°€ μ—†λ‹€λ©΄ ν…Œμ΄λΈ” ν’€ μŠ€μΊ”ν•˜λ©΄μ„œ update μž‘μ—… -> λͺ¨λ“  λ ˆμ½”λ“œκ°€ μž κΉ€
β€’
where 쑰건절 컬럼으둜 A, B κ°€ 있고 A 만 index κ°€ κ±Έλ € 있으면 B 둜 μΈν•œ 전체 λ ˆμ½”λ“œ μž κΈˆμ€ μΌμ–΄λ‚˜μ§€ μ•ŠλŠ”λ‹€.
β€’
performance_schema 의 data_locks ν…Œμ΄λΈ”λ‘œ 확인 κ°€λŠ₯
β—¦
lock_mode column
β–ͺ
IX -> Internal eXclusive
β–ͺ
REC_NOT_GAP -> 갭이 ν¬ν•¨λ˜μ§€ μ•Šμ€ 순수 λ ˆμ½”λ“œ 잠금