Ver3.0 ๐ ํธ๋์ญ์ (Transaction)๊ณผ ACID ํน์ฑ ์๋ฒฝ ์ดํดํ๊ธฐ

๐ ํธ๋์ญ์ (Transaction)๊ณผ ACID ํน์ฑ ์๋ฒฝ ์ดํดํ๊ธฐ
๋ฐ์ดํฐ๋ฒ ์ด์ค์ ํต์ฌ ๊ฐ๋ ์ ์น๊ตฌ์ฒ๋ผ ์ฝ๊ฒ ํ์ด๋๋ฆฝ๋๋ค!
๐ฌ ํธ๋์ญ์ , ๋๋์ฒด ๋ญ๊ธธ๋?
์ผ, ์น๊ตฌ์ผ! ๐ ์ค๋์ ๋ฐ์ดํฐ๋ฒ ์ด์ค์์ ์ ๋ง์ ๋ง ์ค์ํ ๊ฐ๋ ์ธ ํธ๋์ญ์ (Transaction)์ ๋ํด ์ด์ผ๊ธฐํด๋ณผ๊น ํด. ํ๋ก๊ทธ๋๋ฐ ๊ณต๋ถํ๋ค ๋ณด๋ฉด ์ด ๋จ์ด ์ง์ง ๋ง์ด ๋ฃ๊ฒ ๋๋๋ฐ, ์ฒ์์ ์ข ์ด๋ ต๊ฒ ๋๊ปด์ง ์ ์์ด. ํ์ง๋ง ๊ฑฑ์ ๋ง! ๋ด๊ฐ ์ต๋ํ ์ฝ๊ณ ์ฌ๋ฏธ์๊ฒ ์ค๋ช ํด์ค๊ฒ.
ํธ๋์ญ์ ์ ํ๋ง๋๋ก ์ ์ํ๋ฉด, ๋ฐ์ดํฐ๋ฒ ์ด์ค์์ ์ํ๋๋ ์์ ์ ๋ ผ๋ฆฌ์ ๋จ์์ผ. ์... ์ด๊ฒ๋ง์ผ๋ก๋ ์ข ์ถ์์ ์ด์ง? ๐ค ์ข ๋ ์ฝ๊ฒ ์ค๋ช ํด๋ณผ๊ฒ.
์ํ ATM์์ ๋์ ์ด์ฒดํ๋ค๊ณ ์๊ฐํด๋ด. ๋์ ๊ณ์ข์์ 10๋ง์์ ๋นผ๊ณ , ์น๊ตฌ ๊ณ์ข์ 10๋ง์์ ๋ฃ๋ ๊ฑฐ์ง. ์ด ๊ณผ์ ์ ์ฌ์ค ๋ ๊ฐ์ง ์์ ์ผ๋ก ์ด๋ฃจ์ด์ ธ ์์ด:
1๋จ๊ณ: ๋ด ๊ณ์ข์์ 10๋ง์ ์ฐจ๊ฐ ๐ธ
2๋จ๊ณ: ์น๊ตฌ ๊ณ์ข์ 10๋ง์ ์ถ๊ฐ ๐ฐ
๊ทธ๋ฐ๋ฐ ๋ง์ฝ 1๋จ๊ณ๋ ์ฑ๊ณตํ๋๋ฐ, ๊ฐ์๊ธฐ ์์คํ ์ ๋ฌธ์ ๊ฐ ์๊ฒจ์ 2๋จ๊ณ๊ฐ ์คํจํ๋ฉด ์ด๋ป๊ฒ ๋ ๊น? ๐ฑ ๋ด ๋์ ์ฌ๋ผ์ก๋๋ฐ ์น๊ตฌ๋ ๋ชป ๋ฐ๋ ์ต์ ์ ์ํฉ์ด ๋ฒ์ด์ง๋ ๊ฑฐ์ง! ์ด๋ฐ ์ผ์ด ์ ๋ ์ผ์ด๋๋ฉด ์ ๋์์?
๋ฐ๋ก ์ด๋ด ๋ ํ์ํ ๊ฒ ํธ๋์ญ์ ์ด์ผ. ํธ๋์ญ์ ์ ์ด ๋ ์์ ์ ํ๋์ ๋ฌถ์์ผ๋ก ์ฒ๋ฆฌํด์, ๋ ๋ค ์ฑ๊ณตํ๊ฑฐ๋ ๋ ๋ค ์คํจํ๋๋ก ๋ง๋ค์ด์ค. ์ค๊ฐ์ ์ด์ ์ฉกํ ์ํ๋ ์ ๋ ํ์ฉํ์ง ์๋ ๊ฑฐ์ง! ๐ก๏ธ
๐ฏ ํธ๋์ญ์ ์ ํต์ฌ ๊ฐ๋
ํธ๋์ญ์ ์ ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์ํ๋ฅผ ๋ณํ์ํค๋ ํ๋์ ๋ ผ๋ฆฌ์ ๊ธฐ๋ฅ์ ์ํํ๊ธฐ ์ํ ์์ ์ ๋จ์ ๋๋ ํ๊บผ๋ฒ์ ์ํ๋์ด์ผ ํ ์ผ๋ จ์ ์ฐ์ฐ๋ค์ ์๋ฏธํด.
ํ๋ก๊ทธ๋๋ฐ์ ํ๋ค ๋ณด๋ฉด, ํนํ ์ฌ๋ฅ๋ท ๊ฐ์ ํ๋ซํผ์์ ๊ฒฐ์ ์์คํ ์ด๋ ํฌ์ธํธ ๊ด๋ฆฌ ์์คํ ์ ๊ฐ๋ฐํ ๋ ํธ๋์ญ์ ๊ฐ๋ ์ด ์ ๋ง ์ค์ํด์ ธ. ์ฌ์ฉ์๊ฐ ์ฌ๋ฅ์ ๊ตฌ๋งคํ๊ณ ํฌ์ธํธ๊ฐ ์ฐจ๊ฐ๋๋ ๊ณผ์ , ํ๋งค์์๊ฒ ์์ต์ด ์ ์ฐ๋๋ ๊ณผ์ ๋ฑ์ด ๋ชจ๋ ์์ ํ๊ฒ ์ฒ๋ฆฌ๋์ด์ผ ํ๊ฑฐ๋ ! ๐ผ
๐ค ACID? ์ฐ์ฑ? ์๋์ผ, ํธ๋์ญ์ ์ 4๊ฐ์ง ํน์ฑ์ด์ผ!
์, ์ด์ ๋ณธ๊ฒฉ์ ์ผ๋ก ํธ๋์ญ์ ์ ํต์ฌ์ธ ACID ํน์ฑ์ ๋ํด ์์๋ณผ ์๊ฐ์ด์ผ! ๐ ACID๋ Atomicity, Consistency, Isolation, Durability์ ์๊ธ์๋ฅผ ๋ด ๊ฑฐ์ผ. ํ๋์ฉ ์ฒ์ฒํ ํํค์ณ๋ณด์!
โ๏ธ A - Atomicity (์์์ฑ)
์ฒซ ๋ฒ์งธ ํน์ฑ์ ์์์ฑ(Atomicity)์ด์ผ. ์์(Atom)๋ ๋ ์ด์ ์ชผ๊ฐค ์ ์๋ ๊ฐ์ฅ ์์ ๋จ์๋ผ๋ ๋ป์ด์ง? ํธ๋์ญ์ ์์๋ ๋ง์ฐฌ๊ฐ์ง์ผ! ๐ฌ
์์์ฑ์ ํธ๋์ญ์ ์ ๋ชจ๋ ์ฐ์ฐ์ด ์์ ํ ์ํ๋๊ฑฐ๋, ์์ ์ํ๋์ง ์์์ผ ํ๋ค๋ ํน์ฑ์ด์ผ. ์ด๊ฑธ "All or Nothing" ์์น์ด๋ผ๊ณ ๋ ํด. ์ค๊ฐ ์ํ๋ ์กด์ฌํ ์ ์์ด!
๐ฏ ์ค์ํ ์์:
์จ๋ผ์ธ ์ผํ๋ชฐ์์ ์ํ์ ๊ตฌ๋งคํ๋ค๊ณ ์๊ฐํด๋ด. ๋ค์๊ณผ ๊ฐ์ ์์ ๋ค์ด ์ผ์ด๋์ผ ํด:
1๏ธโฃ ์ฌ๊ณ ์์ ์ํ 1๊ฐ ์ฐจ๊ฐ
2๏ธโฃ ์ฃผ๋ฌธ ํ
์ด๋ธ์ ์ฃผ๋ฌธ ์ ๋ณด ์ถ๊ฐ
3๏ธโฃ ๊ฒฐ์ ํ
์ด๋ธ์ ๊ฒฐ์ ์ ๋ณด ๊ธฐ๋ก
4๏ธโฃ ๊ณ ๊ฐ ํฌ์ธํธ ์ฐจ๊ฐ
๋ง์ฝ 3๋ฒ๊น์ง๋ ์ฑ๊ณตํ๋๋ฐ 4๋ฒ์์ ์คํจํ๋ฉด? ๐ฐ ์์์ฑ ๋๋ถ์ 1~3๋ฒ ์์ ๋ ๋ชจ๋ ์ทจ์(Rollback)๋์ด์ ์๋ฌด ์ผ๋ ์์๋ ๊ฒ์ฒ๋ผ ๋์๊ฐ!
์์์ฑ์ ๋ณด์ฅํ๊ธฐ ์ํด ๋ฐ์ดํฐ๋ฒ ์ด์ค๋ Commit๊ณผ Rollback์ด๋ผ๋ ๋ ๊ฐ์ง ์ฐ์ฐ์ ์ ๊ณตํด:
| ์ฐ์ฐ | ์ค๋ช | ๊ฒฐ๊ณผ |
|---|---|---|
| Commit | ํธ๋์ญ์ ์ ๋ชจ๋ ์์ ์ด ์ฑ๊ณต์ ์ผ๋ก ์๋ฃ๋จ | ๋ณ๊ฒฝ์ฌํญ์ด ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์๊ตฌ์ ์ผ๋ก ๋ฐ์ โ |
| Rollback | ํธ๋์ญ์ ์ค ํ๋๋ผ๋ ์คํจํจ | ๋ชจ๋ ๋ณ๊ฒฝ์ฌํญ์ด ์ทจ์๋๊ณ ์ด์ ์ํ๋ก ๋ณต๊ตฌ โฉ๏ธ |
-- SQL ํธ๋์ญ์
์์
BEGIN TRANSACTION;
UPDATE accounts SET balance = balance - 100000 WHERE user_id = 'user1';
UPDATE accounts SET balance = balance + 100000 WHERE user_id = 'user2';
-- ๋ชจ๋ ์์
์ด ์ฑ๊ณตํ๋ฉด
COMMIT;
-- ๋ฌธ์ ๊ฐ ๋ฐ์ํ๋ฉด
ROLLBACK;
์ ์ฝ๋๋ฅผ ๋ณด๋ฉด, BEGIN TRANSACTION์ผ๋ก ํธ๋์ญ์ ์ ์์ํ๊ณ , ๋ชจ๋ ์์ ์ด ์ฑ๊ณตํ๋ฉด COMMIT์ผ๋ก ํ์ ํ๊ณ , ๋ฌธ์ ๊ฐ ์๊ธฐ๋ฉด ROLLBACK์ผ๋ก ๋๋๋ฆฌ๋ ๊ฑฐ์ผ. ๊ฐ๋จํ์ง? ๐
๐ฏ C - Consistency (์ผ๊ด์ฑ)
๋ ๋ฒ์งธ๋ ์ผ๊ด์ฑ(Consistency)์ด์ผ. ์ด๊ฑด ํธ๋์ญ์ ์ด ์คํ๋๊ธฐ ์ ๊ณผ ํ์ ๋ฐ์ดํฐ๋ฒ ์ด์ค๊ฐ ์ผ๊ด๋ ์ํ๋ฅผ ์ ์งํด์ผ ํ๋ค๋ ํน์ฑ์ด์ผ. ๐
๋ฐ์ดํฐ๋ฒ ์ด์ค์๋ ์ฌ๋ฌ ๊ฐ์ง ๋ฌด๊ฒฐ์ฑ ์ ์ฝ์กฐ๊ฑด๋ค์ด ์์ด. ์๋ฅผ ๋ค๋ฉด:
๐ ๊ธฐ๋ณธํค(Primary Key)๋ ์ค๋ณต๋ ์ ์๋ค
๐ ์ธ๋ํค(Foreign Key)๋ ์ฐธ์กฐํ๋ ํ ์ด๋ธ์ ์ค์ ๋ก ์กด์ฌํ๋ ๊ฐ์ด์ด์ผ ํ๋ค
๐ NOT NULL ์ ์ฝ์ด ์๋ ์ปฌ๋ผ์ NULL ๊ฐ์ ๊ฐ์ง ์ ์๋ค
๐ CHECK ์ ์ฝ์กฐ๊ฑด์ ๋ง์กฑํด์ผ ํ๋ค (์: ๋์ด๋ 0๋ณด๋ค ์ปค์ผ ํจ)
๐ ๋น์ฆ๋์ค ๊ท์น์ ์ค์ํด์ผ ํ๋ค (์: ๊ณ์ข ์์ก์ ์์๊ฐ ๋ ์ ์์)
์ผ๊ด์ฑ์ ์ด๋ฐ ๋ชจ๋ ๊ท์น๋ค์ด ํธ๋์ญ์ ์ ํ๋ก ๊นจ์ง์ง ์๋๋ก ๋ณด์ฅํด์ค. ๋ง์ฝ ํธ๋์ญ์ ์คํ ๊ฒฐ๊ณผ๊ฐ ์ด๋ฐ ๊ท์น์ ์๋ฐํ๋ค๋ฉด, ๊ทธ ํธ๋์ญ์ ์ ์๋์ผ๋ก ์ทจ์๋๋ ๊ฑฐ์ง! ๐ซ
๐ก ์ผ๊ด์ฑ ์์
์ํ ์์คํ ์ ์๋ก ๋ค์ด๋ณผ๊ฒ. ์ ์ฒด ๊ณ์ข์ ์์ก ํฉ๊ณ๋ ํญ์ ์ผ์ ํด์ผ ํ๋ค๋ ๊ท์น์ด ์๋ค๊ณ ๊ฐ์ ํด๋ณด์:
ํธ๋์ญ์ ์ :
โข A ๊ณ์ข: 500,000์
โข B ๊ณ์ข: 300,000์
โข ์ ์ฒด ํฉ๊ณ: 800,000์ ๐ฐ
ํธ๋์ญ์ (A โ B๋ก 100,000์ ์ด์ฒด):
โข A ๊ณ์ข: 500,000 - 100,000 = 400,000์
โข B ๊ณ์ข: 300,000 + 100,000 = 400,000์
ํธ๋์ญ์ ํ:
โข A ๊ณ์ข: 400,000์
โข B ๊ณ์ข: 400,000์
โข ์ ์ฒด ํฉ๊ณ: 800,000์ โ (์ผ๊ด์ฑ ์ ์ง!)
๋ณด๋ค์ํผ ํธ๋์ญ์ ์ ํ๋ก ์ ์ฒด ๊ธ์ก์ ํฉ์ด ๋์ผํ๊ฒ ์ ์ง๋๊ณ ์์ด. ์ด๊ฒ ๋ฐ๋ก ์ผ๊ด์ฑ์ด์ผ! ๋ง์ฝ ์ค๊ฐ์ ๋ฌธ์ ๊ฐ ์๊ฒจ์ A ๊ณ์ข์์๋ง ๋์ด ๋น ์ง๊ณ B ๊ณ์ข์๋ ์ถ๊ฐ๋์ง ์์๋ค๋ฉด, ์ ์ฒด ํฉ๊ณ๊ฐ 700,000์์ด ๋์ด๋ฒ๋ ค์ ์ผ๊ด์ฑ์ด ๊นจ์ง๋ ๊ฑฐ์ง. ์ด๋ฐ ์ํฉ์ ์ ๋ ํ์ฉ๋์ง ์์! ๐ก๏ธ
๐ I - Isolation (๊ฒฉ๋ฆฌ์ฑ)
์ธ ๋ฒ์งธ๋ ๊ฒฉ๋ฆฌ์ฑ(Isolation)์ด์ผ. ์ด๊ฑด ์ฌ๋ฌ ํธ๋์ญ์ ์ด ๋์์ ์คํ๋ ๋, ๊ฐ ํธ๋์ญ์ ์ด ๋ค๋ฅธ ํธ๋์ญ์ ์ ์ํฅ์ ๋ฐ์ง ์๊ณ ๋ ๋ฆฝ์ ์ผ๋ก ์คํ๋์ด์ผ ํ๋ค๋ ํน์ฑ์ด์ผ. ๐๏ธ
์ค์ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์คํ ์์๋ ์๋ง์ ์ฌ์ฉ์๋ค์ด ๋์์ ๋ฐ์ดํฐ๋ฅผ ์ฝ๊ณ ์ฐ๊ณ ์์ด. ๋ง์ฝ ๊ฒฉ๋ฆฌ์ฑ์ด ๋ณด์ฅ๋์ง ์์ผ๋ฉด ์ด๋ค ์ผ์ด ๋ฒ์ด์ง๊น? ๐ฑ
๐จ ๊ฒฉ๋ฆฌ์ฑ์ด ์๋ค๋ฉด ๋ฐ์ํ ์ ์๋ ๋ฌธ์ ๋ค:
1. Dirty Read (๋ํฐ ๋ฆฌ๋) ๐ฉ
ํ ํธ๋์ญ์
์ด ์์ง ์ปค๋ฐํ์ง ์์ ๋ฐ์ดํฐ๋ฅผ ๋ค๋ฅธ ํธ๋์ญ์
์ด ์ฝ์ด๋ฒ๋ฆฌ๋ ํ์
2. Non-Repeatable Read (๋ฐ๋ณต ๋ถ๊ฐ๋ฅํ ์ฝ๊ธฐ) ๐
ํ ํธ๋์ญ์
๋ด์์ ๊ฐ์ ๋ฐ์ดํฐ๋ฅผ ๋ ๋ฒ ์ฝ์๋๋ฐ ๊ฐ์ด ๋ฌ๋ผ์ง๋ ํ์
3. Phantom Read (ํฌํ
๋ฆฌ๋) ๐ป
ํ ํธ๋์ญ์
๋ด์์ ๊ฐ์ ์ฟผ๋ฆฌ๋ฅผ ๋ ๋ฒ ์คํํ๋๋ฐ ๊ฒฐ๊ณผ ํ์ ๊ฐ์๊ฐ ๋ฌ๋ผ์ง๋ ํ์
์ด๋ฐ ๋ฌธ์ ๋ค์ ๋ฐฉ์งํ๊ธฐ ์ํด ๋ฐ์ดํฐ๋ฒ ์ด์ค๋ ๊ฒฉ๋ฆฌ ์์ค(Isolation Level)์ด๋ผ๋ ๊ฐ๋ ์ ์ ๊ณตํด. ๊ฒฉ๋ฆฌ ์์ค์ 4๋จ๊ณ๋ก ๋๋์ด์ ธ ์์ด:
| ๊ฒฉ๋ฆฌ ์์ค | Dirty Read | Non-Repeatable Read | Phantom Read | ์ฑ๋ฅ |
|---|---|---|---|---|
| READ UNCOMMITTED | ๋ฐ์ โ | ๋ฐ์ โ | ๋ฐ์ โ | ๊ฐ์ฅ ๋น ๋ฆ ๐ |
| READ COMMITTED | ๋ฐฉ์ง โ | ๋ฐ์ โ | ๋ฐ์ โ | ๋น ๋ฆ โก |
| REPEATABLE READ | ๋ฐฉ์ง โ | ๋ฐฉ์ง โ | ๋ฐ์ โ | ๋ณดํต โ๏ธ |
| SERIALIZABLE | ๋ฐฉ์ง โ | ๋ฐฉ์ง โ | ๋ฐฉ์ง โ | ๊ฐ์ฅ ๋๋ฆผ ๐ข |
๊ฒฉ๋ฆฌ ์์ค์ด ๋์์๋ก ๋ฐ์ดํฐ ์ ํฉ์ฑ์ ์ข์์ง์ง๋ง ๋์์ฑ ์ฒ๋ฆฌ ์ฑ๋ฅ์ ๋จ์ด์ ธ. ๋ฐ๋๋ก ๊ฒฉ๋ฆฌ ์์ค์ด ๋ฎ์ผ๋ฉด ์ฑ๋ฅ์ ์ข์ง๋ง ๋ฐ์ดํฐ ์ ํฉ์ฑ ๋ฌธ์ ๊ฐ ๋ฐ์ํ ์ ์์ด. ๊ทธ๋์ ์ํฉ์ ๋ง๋ ์ ์ ํ ๊ฒฉ๋ฆฌ ์์ค์ ์ ํํ๋ ๊ฒ ์ค์ํด! โ๏ธ
๐ญ ๊ฒฉ๋ฆฌ์ฑ ์ค์ ์์
์ข ๋ ๊ตฌ์ฒด์ ์ธ ์๋ฅผ ๋ค์ด๋ณผ๊ฒ. ๋ ๋ช ์ ์ฌ์ฉ์๊ฐ ๋์์ ๊ฐ์ ์ํ์ ์ฌ๊ณ ๋ฅผ ํ์ธํ๊ณ ๊ตฌ๋งคํ๋ ค๊ณ ํ๋ค๊ณ ๊ฐ์ ํด๋ณด์:
-- ํธ๋์ญ์
1 (์ฌ์ฉ์ A)
BEGIN TRANSACTION;
SELECT stock FROM products WHERE id = 100; -- ์ฌ๊ณ : 1๊ฐ
-- (๊ตฌ๋งค ๊ฒฐ์ ์ค...)
UPDATE products SET stock = stock - 1 WHERE id = 100;
COMMIT;
-- ํธ๋์ญ์
2 (์ฌ์ฉ์ B) - ๋์์ ์คํ
BEGIN TRANSACTION;
SELECT stock FROM products WHERE id = 100; -- ์ฌ๊ณ : 1๊ฐ?
-- (๊ตฌ๋งค ๊ฒฐ์ ์ค...)
UPDATE products SET stock = stock - 1 WHERE id = 100;
COMMIT;
๋ง์ฝ ๊ฒฉ๋ฆฌ์ฑ์ด ์ ๋๋ก ๋ณด์ฅ๋์ง ์์ผ๋ฉด, ๋ ์ฌ์ฉ์ ๋ชจ๋ ์ฌ๊ณ ๊ฐ 1๊ฐ๋ผ๊ณ ๋ณด๊ณ ๊ตฌ๋งค๋ฅผ ์งํํ ์ ์์ด. ๊ทธ๋ฌ๋ฉด ์ฌ๊ณ ๊ฐ -1๊ฐ๊ฐ ๋๋ ๋ง๋ ์ ๋๋ ์ํฉ์ด ๋ฐ์ํ๋ ๊ฑฐ์ง! ๐จ
ํ์ง๋ง ์ ์ ํ ๊ฒฉ๋ฆฌ ์์ค์ด ์ค์ ๋์ด ์๋ค๋ฉด, ํ ํธ๋์ญ์ ์ด ์๋ฃ๋ ๋๊น์ง ๋ค๋ฅธ ํธ๋์ญ์ ์ ๋๊ธฐํ๊ฑฐ๋, ์ต์ ๋ฐ์ดํฐ๋ฅผ ์ฝ์ ์ ์๊ฒ ๋์ด์ ์ด๋ฐ ๋ฌธ์ ๋ฅผ ๋ฐฉ์งํ ์ ์์ด! ๐ฏ
๐พ D - Durability (์ง์์ฑ)
๋ง์ง๋ง์ ์ง์์ฑ(Durability)์ด์ผ. ์ด๊ฑด ํธ๋์ญ์ ์ด ์ฑ๊ณต์ ์ผ๋ก ์๋ฃ(Commit)๋๋ฉด, ๊ทธ ๊ฒฐ๊ณผ๋ ์๊ตฌ์ ์ผ๋ก ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์ ์ฅ๋์ด์ผ ํ๋ค๋ ํน์ฑ์ด์ผ. ๐ช
์ฝ๊ฒ ๋งํด์, ํ๋ฒ ์ปค๋ฐ๋ ๋ฐ์ดํฐ๋ ์์คํ ์ ์ฅ์ ๊ฐ ๋ฐ์ํ๋๋ผ๋ ์ ๋ ์ฌ๋ผ์ง๋ฉด ์ ๋๋ค๋ ๊ฑฐ์ผ! ์ ์ ์ด ๋๋ , ์๋ฒ๊ฐ ๋ค์ด๋๋ , ํ๋๋์คํฌ๊ฐ ๊ณ ์ฅ๋๋ ์๊ด์์ด ๋ง์ด์ผ. ๐ฅ
๐ก๏ธ ์ง์์ฑ์ ๋ณด์ฅํ๋ ๋ฐฉ๋ฒ๋ค:
1. ๋ก๊ทธ ๊ธฐ๋ฐ ๋ณต๊ตฌ (Log-based Recovery) ๐
๋ชจ๋ ๋ณ๊ฒฝ์ฌํญ์ ๋ก๊ทธ ํ์ผ์ ๊ธฐ๋กํด๋์๋ค๊ฐ, ์ฅ์ ๋ฐ์ ์ ๋ก๊ทธ๋ฅผ ์ด์ฉํด ๋ณต๊ตฌ
2. ์ฒดํฌํฌ์ธํธ (Checkpoint) โ๏ธ
์ฃผ๊ธฐ์ ์ผ๋ก ๋ฉ๋ชจ๋ฆฌ์ ๋ฐ์ดํฐ๋ฅผ ๋์คํฌ์ ์ ์ฅํ์ฌ ๋ณต๊ตฌ ์๊ฐ ๋จ์ถ
3. ๋ฐฑ์
๊ณผ ๋ณต๊ตฌ (Backup & Recovery) ๐ฟ
์ ๊ธฐ์ ์ผ๋ก ๋ฐ์ดํฐ๋ฒ ์ด์ค ์ ์ฒด๋ฅผ ๋ฐฑ์
ํ์ฌ ๋๊ท๋ชจ ์ฅ์ ์ ๋๋น
4. ๋ณต์ (Replication) ๐
์ฌ๋ฌ ์๋ฒ์ ๋ฐ์ดํฐ๋ฅผ ๋ณต์ ํ์ฌ ํ ์๋ฒ๊ฐ ์ฃฝ์ด๋ ๋ค๋ฅธ ์๋ฒ์์ ์๋น์ค ๊ณ์
ํนํ WAL(Write-Ahead Logging)์ด๋ผ๋ ๊ธฐ๋ฒ์ด ๋ง์ด ์ฌ์ฉ๋ผ. ์ด๊ฑด ๋ฐ์ดํฐ๋ฅผ ์ค์ ๋ก ๋ณ๊ฒฝํ๊ธฐ ์ ์ ๋จผ์ ๋ก๊ทธ์ ๊ธฐ๋กํ๋ ๋ฐฉ์์ด์ผ. ๊ทธ๋์ ๋ง์ฝ ์์คํ ์ด ๊ฐ์๊ธฐ ์ฃฝ๋๋ผ๋, ์ฌ์์ํ ๋ ๋ก๊ทธ๋ฅผ ๋ณด๊ณ ์ด๋๊น์ง ์ฒ๋ฆฌํ๋์ง ์ ์ ์๊ณ , ์๋ฃ๋์ง ์์ ํธ๋์ญ์ ์ ๋กค๋ฐฑํ๊ณ ์๋ฃ๋ ํธ๋์ญ์ ์ ๋ค์ ์ ์ฉํ ์ ์์ด! ๐ฏ
๐ ์ง์์ฑ ์ค์ ์๋๋ฆฌ์ค
์ค์ ์ํฉ์ ์๋ฎฌ๋ ์ด์ ํด๋ณด์:
์๋๋ฆฌ์ค: ์จ๋ผ์ธ ์ผํ๋ชฐ์์ ๊ณ ๊ฐ์ด 100๋ง์์ง๋ฆฌ ์ํ์ ๊ตฌ๋งคํ์ด.
14:30:00 - ํธ๋์ญ์
์์ ๐
14:30:01 - ์ฃผ๋ฌธ ์ ๋ณด ์์ฑ
14:30:02 - ๊ฒฐ์ ์ฒ๋ฆฌ
14:30:03 - ์ฌ๊ณ ์ฐจ๊ฐ
14:30:04 - COMMIT ์๋ฃ โ
14:30:05 - ๐ฅ ๊ฐ์๊ธฐ ์ ์ ๋ฐ์!
14:35:00 - ์์คํ
์ฌ์์ ๐
14:35:10 - ๋ฐ์ดํฐ๋ฒ ์ด์ค ๋ณต๊ตฌ ์์
14:35:15 - ๋ก๊ทธ ๋ถ์: 14:30:04์ COMMIT ํ์ธ
14:35:20 - ๋ณต๊ตฌ ์๋ฃ: ์ฃผ๋ฌธ ๋ฐ์ดํฐ ์ ์ ํ์ธ โ
๋ณด๋ค์ํผ COMMIT์ด ์๋ฃ๋ ํ์ ์ ์ ์ด ๋ฐ์ํ์ง๋ง, ์์คํ ์ด ์ฌ์์๋๋ฉด์ ๋ก๊ทธ๋ฅผ ๋ถ์ํด ๋ฐ์ดํฐ๋ฅผ ์๋ฒฝํ๊ฒ ๋ณต๊ตฌํ์ด! ์ด๊ฒ ๋ฐ๋ก ์ง์์ฑ์ด์ผ. ๊ณ ๊ฐ์ 100๋ง์์ง๋ฆฌ ์ฃผ๋ฌธ์ด ์ฌ๋ผ์ง์ง ์๊ณ ์์ ํ๊ฒ ๋ณด์กด๋ ๊ฑฐ์ง! ๐ฐโจ
๐ฌ ํธ๋์ญ์ ์ ์๋ช ์ฃผ๊ธฐ
์, ์ด์ ํธ๋์ญ์ ์ด ์ค์ ๋ก ์ด๋ป๊ฒ ๋์ํ๋์ง ๊ทธ ์๋ช ์ฃผ๊ธฐ๋ฅผ ์ดํด๋ณผ๊น? ํธ๋์ญ์ ์ ๋ง์น ์ฌ๋์ ์ธ์์ฒ๋ผ ์ฌ๋ฌ ๋จ๊ณ๋ฅผ ๊ฑฐ์ณ๊ฐ๋ฉฐ ์งํ๋ผ. ๐ฑโก๏ธ๐ณ
๐ ํธ๋์ญ์ ์ํ ์์ธ ์ค๋ช
1. Active (ํ์ฑ ์ํ) ๐ข
ํธ๋์ญ์
์ด ์์๋์ด ์คํ ์ค์ธ ์ํ์ผ. ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ๋ํ ์ฝ๊ธฐ/์ฐ๊ธฐ ์ฐ์ฐ๋ค์ด ์ํ๋๊ณ ์์ด. ์ด ์ํ์์๋ ์์ง ์ด๋ค ๋ณ๊ฒฝ์ฌํญ๋ ํ์ ๋์ง ์์์ด.
2. Partially Committed (๋ถ๋ถ ์๋ฃ ์ํ) ๐ก
ํธ๋์ญ์
์ ๋ง์ง๋ง ์ฐ์ฐ๊น์ง ๋ชจ๋ ์คํํ์ง๋ง, ์์ง ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์๊ตฌ์ ์ผ๋ก ๋ฐ์๋์ง ์์ ์ํ์ผ. ์ด ์์ ์์๋ ๋ณ๊ฒฝ์ฌํญ๋ค์ด ๋ฉ๋ชจ๋ฆฌ(๋ฒํผ)์๋ง ์กด์ฌํ๊ณ ์์ด.
3. Committed (์๋ฃ ์ํ) โ
ํธ๋์ญ์
์ด ์ฑ๊ณต์ ์ผ๋ก ์๋ฃ๋์ด ๋ชจ๋ ๋ณ๊ฒฝ์ฌํญ์ด ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์๊ตฌ์ ์ผ๋ก ์ ์ฅ๋ ์ํ์ผ. ์ด์ ์ด ๋ณ๊ฒฝ์ฌํญ๋ค์ ๋ค๋ฅธ ํธ๋์ญ์
์์๋ ๋ณผ ์ ์์ด.
4. Failed (์คํจ ์ํ) โ
ํธ๋์ญ์
์คํ ์ค์ ์ค๋ฅ๊ฐ ๋ฐ์ํ์ฌ ๋ ์ด์ ์ ์์ ์ผ๋ก ์งํํ ์ ์๋ ์ํ์ผ. ์ด ์ํ๊ฐ ๋๋ฉด ์๋์ผ๋ก Aborted ์ํ๋ก ์ ํ๋ผ.
5. Aborted (์ฒ ํ ์ํ) ๐
ํธ๋์ญ์
์ด ์ทจ์๋์ด ๋ชจ๋ ๋ณ๊ฒฝ์ฌํญ์ด ๋กค๋ฐฑ๋ ์ํ์ผ. ๋ฐ์ดํฐ๋ฒ ์ด์ค๋ ํธ๋์ญ์
์์ ์ ์ ์ํ๋ก ์์ ํ ๋ณต๊ตฌ๋ผ.
โ๏ธ ํธ๋์ญ์ ์ ์ด ๋ช ๋ น์ด (TCL)
ํธ๋์ญ์ ์ ์ ์ดํ๊ธฐ ์ํ SQL ๋ช ๋ น์ด๋ค์ TCL(Transaction Control Language)์ด๋ผ๊ณ ํด. ์ฃผ์ ๋ช ๋ น์ด๋ค์ ํ๋์ฉ ์ดํด๋ณด์! ๐ฎ
๐ฏ ์ฃผ์ TCL ๋ช ๋ น์ด
BEGIN / START TRANSACTION - ํธ๋์ญ์
์์
COMMIT - ํธ๋์ญ์
ํ์
ROLLBACK - ํธ๋์ญ์
์ทจ์
SAVEPOINT - ์ ์ฅ์ ์ค์
SET TRANSACTION - ํธ๋์ญ์
์์ฑ ์ค์
๐ BEGIN / START TRANSACTION
ํธ๋์ญ์ ์ ์์ํ๋ ๋ช ๋ น์ด์ผ. ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์คํ ์ ๋ฐ๋ผ BEGIN ๋๋ START TRANSACTION์ ์ฌ์ฉํด.
-- MySQL, PostgreSQL
START TRANSACTION;
-- SQL Server
BEGIN TRANSACTION;
-- Oracle (์๋ฌต์ ์ผ๋ก ์์๋๋ฏ๋ก ๋ช
์์ ์ ์ธ ๋ถํ์)
-- ํ์ง๋ง ๋ช
์์ ์ผ๋ก ์์ํ๋ ค๋ฉด
SET TRANSACTION;
โ COMMIT
ํธ๋์ญ์ ์ ๋ชจ๋ ์์ ์ ํ์ ํ๊ณ ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ์๊ตฌ์ ์ผ๋ก ๋ฐ์ํ๋ ๋ช ๋ น์ด์ผ. COMMIT์ ์คํํ๋ฉด ๋ ์ด์ ๋กค๋ฐฑํ ์ ์์ด!
BEGIN TRANSACTION;
INSERT INTO orders (user_id, product_id, quantity, price)
VALUES (1001, 2001, 2, 50000);
UPDATE products
SET stock = stock - 2
WHERE product_id = 2001;
UPDATE users
SET points = points - 50000
WHERE user_id = 1001;
-- ๋ชจ๋ ์์
์ด ์ฑ๊ณตํ์ผ๋ฏ๋ก ํ์
COMMIT;
โฉ๏ธ ROLLBACK
ํธ๋์ญ์ ์ ๋ชจ๋ ์์ ์ ์ทจ์ํ๊ณ ์์ ์ ์ํ๋ก ๋๋๋ฆฌ๋ ๋ช ๋ น์ด์ผ. ์ค๋ฅ๊ฐ ๋ฐ์ํ๊ฑฐ๋ ์๋์ ์ผ๋ก ์ทจ์ํ๊ณ ์ถ์ ๋ ์ฌ์ฉํด.
BEGIN TRANSACTION;
UPDATE accounts SET balance = balance - 1000000 WHERE account_id = 'A001';
-- ์์ก ํ์ธ
IF (SELECT balance FROM accounts WHERE account_id = 'A001') < 0 THEN
-- ์์ก์ด ๋ถ์กฑํ๋ฉด ๋กค๋ฐฑ
ROLLBACK;
PRINT '์์ก์ด ๋ถ์กฑํฉ๋๋ค.';
ELSE
UPDATE accounts SET balance = balance + 1000000 WHERE account_id = 'B001';
COMMIT;
END IF;
๐ SAVEPOINT
ํธ๋์ญ์ ๋ด์์ ์ค๊ฐ ์ ์ฅ์ ์ ๋ง๋๋ ๋ช ๋ น์ด์ผ. ์ ์ฒด๋ฅผ ๋กค๋ฐฑํ์ง ์๊ณ ํน์ ์ง์ ๊น์ง๋ง ๋กค๋ฐฑํ ์ ์์ด์ ์ ๋ง ์ ์ฉํด! ๐ฏ
BEGIN TRANSACTION;
-- ์ฒซ ๋ฒ์งธ ์์
INSERT INTO orders (order_id, user_id, total) VALUES (1, 100, 50000);
SAVEPOINT sp1;
-- ๋ ๋ฒ์งธ ์์
UPDATE inventory SET stock = stock - 1 WHERE product_id = 200;
SAVEPOINT sp2;
-- ์ธ ๋ฒ์งธ ์์
INSERT INTO payments (order_id, amount) VALUES (1, 50000);
SAVEPOINT sp3;
-- ์ธ ๋ฒ์งธ ์์
์ ๋ฌธ์ ๊ฐ ์๋ค๋ฉด sp2๊น์ง๋ง ๋กค๋ฐฑ
ROLLBACK TO sp2;
-- ๋๋จธ์ง๋ ์ ์งํ๊ณ ์ปค๋ฐ
COMMIT;
SAVEPOINT๋ฅผ ์ฌ์ฉํ๋ฉด ๋ณต์กํ ํธ๋์ญ์ ์์ ๋ถ๋ถ์ ์ธ ๋กค๋ฐฑ์ด ๊ฐ๋ฅํด์ ธ์ ํจ์ฌ ์ ์ฐํ๊ฒ ์ฒ๋ฆฌํ ์ ์์ด! ๐
๐ ๋์์ฑ ์ ์ด (Concurrency Control)
์ค์ ๋ฐ์ดํฐ๋ฒ ์ด์ค ํ๊ฒฝ์์๋ ์๋ง์ ํธ๋์ญ์ ๋ค์ด ๋์์ ์คํ๋ผ. ์ด๋ ๋ฐ์ํ ์ ์๋ ๋ฌธ์ ๋ค์ ๋ฐฉ์งํ๊ณ ๋ฐ์ดํฐ์ ์ผ๊ด์ฑ์ ์ ์งํ๊ธฐ ์ํ ๊ธฐ๋ฒ์ด ๋ฐ๋ก ๋์์ฑ ์ ์ด์ผ! ๐ฆ
๐ Lock (์ ๊ธ) ๊ธฐ๋ฒ
Lock์ ์ฌ๋ฌ ํธ๋์ญ์ ์ด ๋์์ ๊ฐ์ ๋ฐ์ดํฐ์ ์ ๊ทผํ๋ ๊ฒ์ ์ ์ดํ๋ ๊ฐ์ฅ ๊ธฐ๋ณธ์ ์ธ ๋ฐฉ๋ฒ์ด์ผ. ๋ง์น ํ์ฅ์ค ๋ฌธ์ ์ ๊ทธ๋ ๊ฒ์ฒ๋ผ, ํ ํธ๋์ญ์ ์ด ๋ฐ์ดํฐ๋ฅผ ์ฌ์ฉํ๋ ๋์ ๋ค๋ฅธ ํธ๋์ญ์ ์ ์ ๊ทผ์ ์ ํํ๋ ๊ฑฐ์ง! ๐ช๐
| Lock ์ข ๋ฅ | ์ค๋ช | ํน์ง |
|---|---|---|
| Shared Lock (S-Lock) | ๊ณต์ ์ ๊ธ, ์ฝ๊ธฐ ์ ๊ธ | ์ฌ๋ฌ ํธ๋์ญ์
์ด ๋์์ ์ฝ๊ธฐ ๊ฐ๋ฅ ๐ ์ฐ๊ธฐ๋ ๋ถ๊ฐ๋ฅ โ๏ธโ |
| Exclusive Lock (X-Lock) | ๋ฐฐํ์ ์ ๊ธ, ์ฐ๊ธฐ ์ ๊ธ | ํ๋์ ํธ๋์ญ์
๋ง ์ ๊ทผ ๊ฐ๋ฅ ๐ ์ฝ๊ธฐ/์ฐ๊ธฐ ๋ชจ๋ ๋ ์ |
๐ญ Lock ํธํ์ฑ ๋งคํธ๋ฆญ์ค
ํ์ฌ Lock์ด S-Lock์ผ ๋:
โข ๋ค๋ฅธ ํธ๋์ญ์
์ S-Lock ์์ฒญ: โ
ํ์ฉ
โข ๋ค๋ฅธ ํธ๋์ญ์
์ X-Lock ์์ฒญ: โ ๋๊ธฐ
ํ์ฌ Lock์ด X-Lock์ผ ๋:
โข ๋ค๋ฅธ ํธ๋์ญ์
์ S-Lock ์์ฒญ: โ ๋๊ธฐ
โข ๋ค๋ฅธ ํธ๋์ญ์
์ X-Lock ์์ฒญ: โ ๋๊ธฐ
โ ๏ธ Deadlock (๊ต์ฐฉ์ํ)
Lock์ ์ฌ์ฉํ๋ค ๋ณด๋ฉด Deadlock์ด๋ผ๋ ๋ฌธ์ ๊ฐ ๋ฐ์ํ ์ ์์ด. ๋ ๊ฐ ์ด์์ ํธ๋์ญ์ ์ด ์๋ก๊ฐ ๊ฐ์ง Lock์ ๊ธฐ๋ค๋ฆฌ๋ฉด์ ๋ฌดํ์ ๋๊ธฐํ๋ ์ํฉ์ด์ผ. ๐ฑ
๐ Deadlock ๋ฐ์ ์๋๋ฆฌ์ค
์๊ฐ T1:
โข ํธ๋์ญ์
A: ๋ฐ์ดํฐ X์ Lock ํ๋ ๐
โข ํธ๋์ญ์
B: ๋ฐ์ดํฐ Y์ Lock ํ๋ ๐
์๊ฐ T2:
โข ํธ๋์ญ์
A: ๋ฐ์ดํฐ Y์ Lock ์์ฒญ (๋๊ธฐ ์ค...) โณ
โข ํธ๋์ญ์
B: ๋ฐ์ดํฐ X์ Lock ์์ฒญ (๋๊ธฐ ์ค...) โณ
๊ฒฐ๊ณผ: ์๋ก๊ฐ ์๋ก๋ฅผ ๊ธฐ๋ค๋ฆฌ๋ ๊ต์ฐฉ์ํ! ๐ฅ
Deadlock์ ํด๊ฒฐํ๋ ๋ฐฉ๋ฒ์ ํฌ๊ฒ ๋ ๊ฐ์ง์ผ:
1. Deadlock Prevention (์๋ฐฉ) ๐ก๏ธ
์ ์ด์ Deadlock์ด ๋ฐ์ํ์ง ์๋๋ก ์ค๊ณํ๋ ๋ฐฉ๋ฒ. ์๋ฅผ ๋ค์ด, ๋ชจ๋ ํธ๋์ญ์
์ด ๊ฐ์ ์์๋ก ๋ฐ์ดํฐ์ ์ ๊ทผํ๋๋ก ๊ฐ์ ํ๋ ๊ฑฐ์ผ.
2. Deadlock Detection & Recovery (ํ์ง ๋ฐ ํ๋ณต) ๐
Deadlock์ด ๋ฐ์ํ๋ฉด ๊ฐ์งํด์ ํ๋์ ํธ๋์ญ์
์ ๊ฐ์ ๋ก ๋กค๋ฐฑ์ํค๋ ๋ฐฉ๋ฒ. ๋๋ถ๋ถ์ DBMS๊ฐ ์ด ๋ฐฉ์์ ์ฌ์ฉํด.
๐ฏ 2PL (Two-Phase Locking) ํ๋กํ ์ฝ
๊ฐ์ฅ ๋๋ฆฌ ์ฌ์ฉ๋๋ Lock ํ๋กํ ์ฝ์ด์ผ. ํธ๋์ญ์ ์ ๋ ๋จ๊ณ๋ก ๋๋ ์ Lock์ ๊ด๋ฆฌํด:
Phase 1: Growing Phase (ํ์ฅ ๋จ๊ณ) ๐
โข Lock๋ง ํ๋ํ ์ ์๊ณ , ํด์ ๋ ๋ถ๊ฐ๋ฅ
โข ํ์ํ ๋ชจ๋ Lock์ ํ๋ํ๋ ๋จ๊ณ
Phase 2: Shrinking Phase (์ถ์ ๋จ๊ณ) ๐
โข Lock๋ง ํด์ ํ ์ ์๊ณ , ์๋ก์ด ํ๋์ ๋ถ๊ฐ๋ฅ
โข ํ๋ํ Lock๋ค์ ์์ฐจ์ ์ผ๋ก ํด์ ํ๋ ๋จ๊ณ
2PL์ ์ฌ์ฉํ๋ฉด ์ง๋ ฌ์ฑ(Serializability)์ด ๋ณด์ฅ๋์ด์ ๋์์ ์คํ๋๋ ํธ๋์ญ์ ๋ค์ด ์์ฐจ์ ์ผ๋ก ์คํ๋ ๊ฒ๊ณผ ๊ฐ์ ๊ฒฐ๊ณผ๋ฅผ ์ป์ ์ ์์ด! โจ
๐ช ์ค์ ์์ : ์จ๋ผ์ธ ์ผํ๋ชฐ ์์คํ
์ด๋ก ๋ง ๋ฐฐ์ฐ๋ฉด ์ฌ๋ฏธ์์ง! ๐ ์ค์ ๋ก ์ด๋ป๊ฒ ์ฌ์ฉ๋๋์ง ์ฌ๋ฅ๋ท ๊ฐ์ ํ๋ซํผ์ ๊ฒฐ์ ์์คํ ์ ์๋ก ๋ค์ด ๊ตฌ์ฒด์ ์ธ ์ฝ๋๋ฅผ ์ดํด๋ณด์!
๐ณ ์๋๋ฆฌ์ค: ์ฌ๋ฅ ๊ตฌ๋งค ํ๋ก์ธ์ค
์ฌ์ฉ์๊ฐ ์ฌ๋ฅ๋ท์์ ์ด๋ค ์ฌ๋ฅ์ ๊ตฌ๋งคํ๋ค๊ณ ๊ฐ์ ํด๋ณด์. ๋ค์๊ณผ ๊ฐ์ ์์ ๋ค์ด ์์์ ์ผ๋ก ์ฒ๋ฆฌ๋์ด์ผ ํด:
1๏ธโฃ ๊ตฌ๋งค์์ ํฌ์ธํธ ์ฐจ๊ฐ
2๏ธโฃ ํ๋งค์์ ํฌ์ธํธ ์ฆ๊ฐ
3๏ธโฃ ์ฃผ๋ฌธ ์ ๋ณด ์์ฑ
4๏ธโฃ ์ฌ๋ฅ ํ๋งค ํ์ ์ฆ๊ฐ
5๏ธโฃ ์๋ฆผ ๋ฐ์ก (์ ํ์ )
-- ์ฌ๋ฅ ๊ตฌ๋งค ํธ๋์ญ์
BEGIN TRANSACTION;
DECLARE @buyer_id INT = 1001;
DECLARE @seller_id INT = 2001;
DECLARE @talent_id INT = 5001;
DECLARE @price INT = 50000;
DECLARE @buyer_balance INT;
-- 1. ๊ตฌ๋งค์ ์์ก ํ์ธ
SELECT @buyer_balance = points
FROM users
WHERE user_id = @buyer_id;
-- ์์ก ๋ถ์กฑ ์ฒดํฌ
IF @buyer_balance < @price
BEGIN
ROLLBACK;
RAISERROR('ํฌ์ธํธ๊ฐ ๋ถ์กฑํฉ๋๋ค.', 16, 1);
RETURN;
END
-- ์ ์ฅ์ ์ค์
SAVEPOINT before_payment;
-- 2. ๊ตฌ๋งค์ ํฌ์ธํธ ์ฐจ๊ฐ
UPDATE users
SET points = points - @price,
updated_at = GETDATE()
WHERE user_id = @buyer_id;
-- 3. ํ๋งค์ ํฌ์ธํธ ์ฆ๊ฐ (์์๋ฃ 10% ์ฐจ๊ฐ)
UPDATE users
SET points = points + (@price * 0.9),
updated_at = GETDATE()
WHERE user_id = @seller_id;
-- 4. ์ฃผ๋ฌธ ์ ๋ณด ์์ฑ
INSERT INTO orders (buyer_id, seller_id, talent_id, amount, status, created_at)
VALUES (@buyer_id, @seller_id, @talent_id, @price, 'COMPLETED', GETDATE());
DECLARE @order_id INT = SCOPE_IDENTITY();
-- 5. ์ฌ๋ฅ ํ๋งค ํ์ ์ฆ๊ฐ
UPDATE talents
SET sales_count = sales_count + 1,
updated_at = GETDATE()
WHERE talent_id = @talent_id;
-- 6. ๊ฑฐ๋ ๋ด์ญ ๊ธฐ๋ก
INSERT INTO transactions (order_id, type, amount, created_at)
VALUES (@order_id, 'PURCHASE', @price, GETDATE());
-- ๋ชจ๋ ์์
์ฑ๊ณต ์ ์ปค๋ฐ
COMMIT;
-- ์ฑ๊ณต ๋ฉ์์ง
PRINT '์ฌ๋ฅ ๊ตฌ๋งค๊ฐ ์๋ฃ๋์์ต๋๋ค!';
PRINT '์ฃผ๋ฌธ๋ฒํธ: ' + CAST(@order_id AS VARCHAR);
์ ์ฝ๋๋ฅผ ๋ณด๋ฉด ์ฌ๋ฌ ํ ์ด๋ธ์ ๋ํ ์์ ๋ค์ด ํ๋์ ํธ๋์ญ์ ์ผ๋ก ๋ฌถ์ฌ์์ด. ์ค๊ฐ์ ์ด๋ค ๋ฌธ์ ๊ฐ ๋ฐ์ํ๋๋ผ๋ ROLLBACK๋์ด์ ๋ฐ์ดํฐ ๋ถ์ผ์น๊ฐ ๋ฐ์ํ์ง ์์! ๐ฏ
๐ ๋์ ๊ตฌ๋งค ์ฒ๋ฆฌ ์์
๊ฐ์ ์ฌ๋ฅ์ ์ฌ๋ฌ ๋ช ์ด ๋์์ ๊ตฌ๋งคํ๋ ค๊ณ ํ ๋๋ ์ด๋ป๊ฒ ์ฒ๋ฆฌํ ๊น? ๊ฒฉ๋ฆฌ ์์ค๊ณผ Lock์ ํ์ฉํ ์์ ๋ฅผ ๋ณด์:
-- ๊ฒฉ๋ฆฌ ์์ค ์ค์
SET TRANSACTION ISOLATION LEVEL REPEATABLE READ;
BEGIN TRANSACTION;
DECLARE @talent_id INT = 5001;
DECLARE @available_slots INT;
DECLARE @max_slots INT;
-- ์ฌ๋ฅ์ ๋จ์ ์ฌ๋กฏ ํ์ธ (X-Lock ํ๋)
SELECT @available_slots = available_slots,
@max_slots = max_slots
FROM talents WITH (XLOCK, ROWLOCK)
WHERE talent_id = @talent_id;
-- ์ฌ๋กฏ ํ์ธ
IF @available_slots <= 0
BEGIN
ROLLBACK;
RAISERROR('์ฃ์กํฉ๋๋ค. ํด๋น ์ฌ๋ฅ์ ๋ง๊ฐ๋์์ต๋๋ค.', 16, 1);
RETURN;
END
-- ์ฌ๋กฏ ์ฐจ๊ฐ
UPDATE talents
SET available_slots = available_slots - 1
WHERE talent_id = @talent_id;
-- ๋๋จธ์ง ๊ตฌ๋งค ํ๋ก์ธ์ค...
-- (ํฌ์ธํธ ์ฐจ๊ฐ, ์ฃผ๋ฌธ ์์ฑ ๋ฑ)
COMMIT;
PRINT '๊ตฌ๋งค๊ฐ ์๋ฃ๋์์ต๋๋ค!';
WITH (XLOCK, ROWLOCK)๋ฅผ ์ฌ์ฉํด์ ํด๋น ํ์ ๋ฐฐํ์ ์ ๊ธ์ ๊ฑธ์์ด. ์ด๋ ๊ฒ ํ๋ฉด ๋ค๋ฅธ ํธ๋์ญ์
์ด ๋์์ ๊ฐ์ ์ฌ๋ฅ์ ๊ตฌ๋งคํ๋ ค๊ณ ํด๋ ์์ฐจ์ ์ผ๋ก ์ฒ๋ฆฌ๋์ด์ ์ฌ๋กฏ์ด ์์๊ฐ ๋๋ ๋ฌธ์ ๋ฅผ ๋ฐฉ์งํ ์ ์์ด! ๐
๐จ ํธ๋์ญ์ ์ฌ์ฉ ์ ์ฃผ์์ฌํญ
ํธ๋์ญ์ ์ ๊ฐ๋ ฅํ์ง๋ง, ์๋ชป ์ฌ์ฉํ๋ฉด ์ฑ๋ฅ ๋ฌธ์ ๋ ๋ฐ๋๋ฝ์ ์ ๋ฐํ ์ ์์ด. ์ค๋ฌด์์ ๊ผญ ์ง์ผ์ผ ํ ์ฃผ์์ฌํญ๋ค์ ์์๋ณด์! โ ๏ธ
โฑ๏ธ 1. ํธ๋์ญ์ ์ ๊ฐ๋ฅํ ์งง๊ฒ ์ ์งํ๋ผ
โ ๋์ ์:
BEGIN TRANSACTION;
-- ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์
UPDATE accounts SET balance = balance - 10000 WHERE id = 1;
-- ์ธ๋ถ API ํธ์ถ (์๊ฐ์ด ์ค๋ ๊ฑธ๋ฆผ!)
EXEC sp_send_email @to='user@example.com', @subject='๊ฒฐ์ ์๋ฃ';
-- ํ์ผ ์ฒ๋ฆฌ (์๊ฐ์ด ์ค๋ ๊ฑธ๋ฆผ!)
EXEC sp_generate_pdf @order_id=12345;
-- ๋ค๋ฅธ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์
INSERT INTO logs (message) VALUES ('Payment completed');
COMMIT;
์ด๋ ๊ฒ ํ๋ฉด ํธ๋์ญ์ ์ด ๋๋ฌด ์ค๋ ์ ์ง๋์ด์ ๋ค๋ฅธ ํธ๋์ญ์ ๋ค์ด ๋๊ธฐํ๊ฒ ๋ผ! ๐ฐ
โ ์ข์ ์:
-- ํธ๋์ญ์
์ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์
๋ง!
BEGIN TRANSACTION;
UPDATE accounts SET balance = balance - 10000 WHERE id = 1;
INSERT INTO logs (message) VALUES ('Payment completed');
COMMIT;
-- ์ธ๋ถ ์์
์ ํธ๋์ญ์
๋ฐ์์
EXEC sp_send_email @to='user@example.com', @subject='๊ฒฐ์ ์๋ฃ';
EXEC sp_generate_pdf @order_id=12345;
ํธ๋์ญ์ ๋ด์์๋ ์์ํ๊ฒ ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์ ๋ง ์ํํ๊ณ , ์ธ๋ถ API ํธ์ถ์ด๋ ํ์ผ ์ฒ๋ฆฌ๋ ํธ๋์ญ์ ๋ฐ์์ ์ฒ๋ฆฌํด! ๐ฏ
๐ฏ 2. ์ ์ ํ ๊ฒฉ๋ฆฌ ์์ค์ ์ ํํ๋ผ
๋ฌด์กฐ๊ฑด ๋์ ๊ฒฉ๋ฆฌ ์์ค์ด ์ข์ ๊ฒ ์๋์ผ. ์ํฉ์ ๋ง๋ ์ ์ ํ ์์ค์ ์ ํํด์ผ ํด:
| ์ํฉ | ๊ถ์ฅ ๊ฒฉ๋ฆฌ ์์ค | ์ด์ |
|---|---|---|
| ๋จ์ ์กฐํ | READ COMMITTED | ์ฑ๋ฅ๊ณผ ์ผ๊ด์ฑ์ ๊ท ํ โ๏ธ |
| ํต๊ณ ๋ฆฌํฌํธ | READ UNCOMMITTED | ์ ํ๋๋ณด๋ค ์๋ ์ฐ์ ๐ |
| ๊ธ์ต ๊ฑฐ๋ | SERIALIZABLE | ๋ฐ์ดํฐ ์ ํฉ์ฑ ์ต์ฐ์ ๐ |
| ์ฌ๊ณ ๊ด๋ฆฌ | REPEATABLE READ | ์ผ๊ด๋ ์ฝ๊ธฐ ๋ณด์ฅ ๐ |
๐ 3. ๋ฐ๋๋ฝ์ ๋ฐฉ์งํ๋ผ
๋ฐ๋๋ฝ์ ๋ฐฉ์งํ๊ธฐ ์ํ ์ค์ ํ๋ค:
โ
ํญ์ ๊ฐ์ ์์๋ก ํ
์ด๋ธ์ ์ ๊ทผํ๊ธฐ
๋ชจ๋ ํธ๋์ญ์
์ด A โ B โ C ์์๋ก ์ ๊ทผํ๋ฉด ๋ฐ๋๋ฝ ๋ฐ์ ํ๋ฅ ์ด ํฌ๊ฒ ์ค์ด๋ค์ด!
โ
์ธ๋ฑ์ค๋ฅผ ์ ์ ํ ์ฌ์ฉํ๊ธฐ
์ธ๋ฑ์ค๊ฐ ์์ผ๋ฉด ํ
์ด๋ธ ์ ์ฒด์ Lock์ด ๊ฑธ๋ ค์ ๋ฐ๋๋ฝ ์ํ์ด ๋์์ ธ.
โ
ํธ๋์ญ์
ํฌ๊ธฐ๋ฅผ ์๊ฒ ์ ์งํ๊ธฐ
ํธ๋์ญ์
์ด ์งง์์๋ก Lock ์ ์ง ์๊ฐ์ด ์งง์์ ธ์ ์ถฉ๋ ๊ฐ๋ฅ์ฑ์ด ์ค์ด๋ค์ด.
โ
ํ์์์ ์ค์ ํ๊ธฐ
๋ฌดํ์ ๋๊ธฐํ์ง ์๋๋ก ์ ์ ํ ํ์์์์ ์ค์ ํด.
๐พ 4. ๋กค๋ฐฑ ๊ฐ๋ฅ์ฑ์ ํญ์ ๊ณ ๋ คํ๋ผ
ํธ๋์ญ์ ์ด ๋กค๋ฐฑ๋ ์ ์๋ค๋ ๊ฑธ ํญ์ ์ผ๋์ ๋๊ณ ์ฝ๋๋ฅผ ์์ฑํด์ผ ํด:
BEGIN TRY
BEGIN TRANSACTION;
-- ๋ฐ์ดํฐ๋ฒ ์ด์ค ์์
๋ค
UPDATE inventory SET stock = stock - 1 WHERE product_id = 100;
INSERT INTO orders (product_id, quantity) VALUES (100, 1);
COMMIT;
-- ์ปค๋ฐ ์ฑ๊ณต ํ์๋ง ์คํ๋์ด์ผ ํ๋ ์์
EXEC sp_send_confirmation_email;
END TRY
BEGIN CATCH
-- ์ค๋ฅ ๋ฐ์ ์ ๋กค๋ฐฑ
IF @@TRANCOUNT > 0
ROLLBACK;
-- ์ค๋ฅ ๋ก๊น
INSERT INTO error_logs (error_message, error_time)
VALUES (ERROR_MESSAGE(), GETDATE());
-- ์ค๋ฅ ์ฌ๋ฐ์
THROW;
END CATCH;
๐ 5. ํธ๋์ญ์ ๋ก๊ทธ๋ฅผ ๋ชจ๋ํฐ๋งํ๋ผ
ํธ๋์ญ์ ๋ก๊ทธ๊ฐ ๋๋ฌด ์ปค์ง๋ฉด ์ฑ๋ฅ ๋ฌธ์ ๊ฐ ๋ฐ์ํ ์ ์์ด. ์ ๊ธฐ์ ์ผ๋ก ๋ชจ๋ํฐ๋งํ๊ณ ๊ด๋ฆฌํด์ผ ํด:
๐ ์ฒดํฌํด์ผ ํ ์ฌํญ๋ค:
โข ํธ๋์ญ์
๋ก๊ทธ ํ์ผ ํฌ๊ธฐ
โข ์ฅ์๊ฐ ์คํ ์ค์ธ ํธ๋์ญ์
โข ๋น๋ฒํ ๋กค๋ฐฑ ๋ฐ์
โข ๋ฐ๋๋ฝ ๋ฐ์ ๋น๋
โข Lock ๋๊ธฐ ์๊ฐ
๐ NoSQL๊ณผ ํธ๋์ญ์
์์ฆ์ MongoDB, Redis, Cassandra ๊ฐ์ NoSQL ๋ฐ์ดํฐ๋ฒ ์ด์ค๋ ๋ง์ด ์ฌ์ฉ๋์ง? ๐ NoSQL์์๋ ํธ๋์ญ์ ์ด ์ด๋ป๊ฒ ์ฒ๋ฆฌ๋ ๊น?
๐ MongoDB์ ํธ๋์ญ์
MongoDB๋ 4.0 ๋ฒ์ ๋ถํฐ ๋ค์ค ๋ฌธ์ ํธ๋์ญ์ ์ ์ง์ํ๊ธฐ ์์ํ์ด. ํ์ง๋ง ์ ํต์ ์ธ RDBMS์๋ ์กฐ๊ธ ๋ค๋ฅธ ๋ฐฉ์์ผ๋ก ๋์ํด:
// MongoDB ํธ๋์ญ์
์์ (Node.js)
const session = client.startSession();
try {
session.startTransaction();
// ๊ณ์ข A์์ ์ฐจ๊ฐ
await accountsCollection.updateOne(
{ accountId: 'A001' },
{ $inc: { balance: -1000 } },
{ session }
);
// ๊ณ์ข B์ ์ถ๊ฐ
await accountsCollection.updateOne(
{ accountId: 'B001' },
{ $inc: { balance: 1000 } },
{ session }
);
// ๊ฑฐ๋ ๋ด์ญ ๊ธฐ๋ก
await transactionsCollection.insertOne(
{ from: 'A001', to: 'B001', amount: 1000, date: new Date() },
{ session }
);
await session.commitTransaction();
console.log('ํธ๋์ญ์
์ฑ๊ณต! โ
');
} catch (error) {
await session.abortTransaction();
console.log('ํธ๋์ญ์
์คํจ, ๋กค๋ฐฑ๋จ โ');
throw error;
} finally {
session.endSession();
}
โก Redis์ ํธ๋์ญ์
Redis๋ MULTI, EXEC, DISCARD ๋ช
๋ น์ด๋ก ํธ๋์ญ์
์ ์ง์ํด. ํ์ง๋ง ACID์ I(Isolation)๋ ์๋ฒฝํ๊ฒ ๋ณด์ฅ๋์ง ์์:
// Redis ํธ๋์ญ์
์์
MULTI
SET account:A:balance 9000
SET account:B:balance 11000
LPUSH transactions "A->B:1000"
EXEC
// ๋๋ ์กฐ๊ฑด๋ถ ํธ๋์ญ์
(WATCH ์ฌ์ฉ)
WATCH account:A:balance
balance = GET account:A:balance
if balance >= 1000:
MULTI
DECRBY account:A:balance 1000
INCRBY account:B:balance 1000
EXEC
else:
UNWATCH
๐ฏ NoSQL ํธ๋์ญ์ ์ฌ์ฉ ์ ๊ณ ๋ ค์ฌํญ
์ฅ์ : โ
โข ์ํ์ ํ์ฅ์ฑ์ด ๋ฐ์ด๋จ
โข ๋์ฉ๋ ๋ฐ์ดํฐ ์ฒ๋ฆฌ์ ์ ๋ฆฌ
โข ์ ์ฐํ ์คํค๋ง
๋จ์ : โ ๏ธ
โข ACID ๋ณด์ฅ์ด ์ ํ์ ์ผ ์ ์์
โข ๋ณต์กํ ํธ๋์ญ์
์ฒ๋ฆฌ๊ฐ ์ด๋ ค์
โข ์กฐ์ธ ์ฐ์ฐ์ด ๋นํจ์จ์
๐ก ๊ฒฐ๋ก :
๊ฐ๋ ฅํ ํธ๋์ญ์
์ด ํ์ํ๋ฉด RDBMS๋ฅผ, ํ์ฅ์ฑ๊ณผ ์ฑ๋ฅ์ด ์ค์ํ๋ฉด NoSQL์ ์ ํํ๋, ์ต๊ทผ์๋ ๋ ๊ฐ์ง๋ฅผ ํผํฉํด์ ์ฌ์ฉํ๋ ํด๋ฆฌ๊ธ๋ ํผ์์คํด์ค(Polyglot Persistence) ํจํด๋ ๋ง์ด ์ฌ์ฉ๋ผ!
๐ ํธ๋์ญ์ ๋ฒ ์คํธ ํ๋ํฐ์ค
์ง๊ธ๊น์ง ๋ฐฐ์ด ๋ด์ฉ์ ๋ฐํ์ผ๋ก ์ค๋ฌด์์ ๊ผญ ์ง์ผ์ผ ํ ๋ฒ ์คํธ ํ๋ํฐ์ค๋ฅผ ์ ๋ฆฌํด๋ณผ๊ฒ! ๐
1๏ธโฃ ํธ๋์ญ์ ๋ฒ์๋ฅผ ์ต์ํํ๋ผ
๊ผญ ํ์ํ ์์ ๋ง ํธ๋์ญ์ ์ ํฌํจ์์ผ. ๋คํธ์ํฌ ํธ์ถ, ํ์ผ I/O, ๋ณต์กํ ๊ณ์ฐ ๋ฑ์ ํธ๋์ญ์ ๋ฐ์์ ์ฒ๋ฆฌํด!
2๏ธโฃ ๋ช ์์ ์ผ๋ก ํธ๋์ญ์ ์ ๊ด๋ฆฌํ๋ผ
์๋ ์ปค๋ฐ ๋ชจ๋์ ์์กดํ์ง ๋ง๊ณ , BEGIN, COMMIT, ROLLBACK์ ๋ช ์์ ์ผ๋ก ์ฌ์ฉํด์ ์๋๋ฅผ ๋ช ํํ ํด!
3๏ธโฃ ์ ์ ํ ๊ฒฉ๋ฆฌ ์์ค์ ์ ํํ๋ผ
๋ฌด์กฐ๊ฑด ๋์ ๊ฒฉ๋ฆฌ ์์ค์ด ์๋๋ผ, ๋น์ฆ๋์ค ์๊ตฌ์ฌํญ์ ๋ง๋ ์ ์ ํ ์์ค์ ์ ํํด. ์ฑ๋ฅ๊ณผ ์ผ๊ด์ฑ์ ๊ท ํ์ ๋ง์ถฐ!
4๏ธโฃ ์์ธ ์ฒ๋ฆฌ๋ฅผ ์ฒ ์ ํ ํ๋ผ
๋ชจ๋ ๊ฐ๋ฅํ ์์ธ ์ํฉ์ ๊ณ ๋ คํ๊ณ , ์ ์ ํ ๋กค๋ฐฑ ์ฒ๋ฆฌ๋ฅผ ๊ตฌํํด. try-catch-finally ํจํด์ ํ์ฉํด!
5๏ธโฃ ๋ฐ๋๋ฝ์ ์๋ฐฉํ๋ผ
์ผ๊ด๋ ์์๋ก ๋ฆฌ์์ค์ ์ ๊ทผํ๊ณ , ํ์์์์ ์ค์ ํ๊ณ , ํธ๋์ญ์ ์ ์งง๊ฒ ์ ์งํด!
6๏ธโฃ ๋ก๊น ๊ณผ ๋ชจ๋ํฐ๋ง์ ๊ตฌ์ถํ๋ผ
ํธ๋์ญ์ ์ ์์, ์ข ๋ฃ, ์คํจ๋ฅผ ๋ก๊น ํ๊ณ , ์ฑ๋ฅ ์งํ๋ฅผ ๋ชจ๋ํฐ๋งํด์ ๋ฌธ์ ๋ฅผ ์กฐ๊ธฐ์ ๋ฐ๊ฒฌํด!
7๏ธโฃ ํ ์คํธ๋ฅผ ์ฒ ์ ํ ํ๋ผ
์ ์ ์ผ์ด์ค๋ฟ๋ง ์๋๋ผ ๋กค๋ฐฑ ์๋๋ฆฌ์ค, ๋์์ฑ ํ ์คํธ, ์ฅ์ ์ํฉ ํ ์คํธ๋ ๊ผญ ์ํํด!
8๏ธโฃ ๋ฌธ์ํ๋ฅผ ์ ํ๋ผ
๋ณต์กํ ํธ๋์ญ์ ๋ก์ง์ ์ฃผ์๊ณผ ๋ฌธ์๋ก ์ ์ค๋ช ํด๋์ด์ผ ๋์ค์ ์ ์ง๋ณด์ํ ๋ ๋์์ด ๋ผ!
๐ฌ ๋ง๋ฌด๋ฆฌํ๋ฉฐ
์, ์ฌ๊ธฐ๊น์ง ํธ๋์ญ์ ๊ณผ ACID ํน์ฑ์ ๋ํด ๊น์ด ์๊ฒ ์์๋ดค์ด! ๐ ์ฒ์์ ์ด๋ ต๊ฒ ๋๊ปด์ก์ ์๋ ์์ง๋ง, ํ๋์ฉ ์ฐจ๊ทผ์ฐจ๊ทผ ์ดํดํ๋ค ๋ณด๋ฉด ๊ทธ๋ ๊ฒ ์ด๋ ค์ด ๊ฐ๋ ์ ์๋์ผ.
ํธ๋์ญ์ ์ ๋ฐ์ดํฐ๋ฒ ์ด์ค์ ํต์ฌ ๊ฐ๋ ์ด๊ณ , ์ค๋ฌด์์ ์ ๋ง์ ๋ง ์ค์ํด. ํนํ ๊ธ์ต, ์ ์์๊ฑฐ๋, ์์ฝ ์์คํ ๊ฐ์ด ๋ฐ์ดํฐ ์ ํฉ์ฑ์ด ์ค์ํ ์์คํ ์์๋ ํ์์ ์ด์ง! ๐ผ
๐ฏ ํต์ฌ ์์ฝ
ํธ๋์ญ์
: ๋ฐ์ดํฐ๋ฒ ์ด์ค์์ ์ํ๋๋ ์์
์ ๋
ผ๋ฆฌ์ ๋จ์
ACID: Atomicity, Consistency, Isolation, Durability
์์์ฑ: All or Nothing - ์ ๋ถ ์ฑ๊ณต ๋๋ ์ ๋ถ ์คํจ
์ผ๊ด์ฑ: ํธ๋์ญ์
์ ํ๋ก ๋ฐ์ดํฐ ๋ฌด๊ฒฐ์ฑ ์ ์ง
๊ฒฉ๋ฆฌ์ฑ: ๋์ ์คํ๋๋ ํธ๋์ญ์
๋ค์ ๋
๋ฆฝ์ฑ ๋ณด์ฅ
์ง์์ฑ: ์ปค๋ฐ๋ ๋ฐ์ดํฐ๋ ์๊ตฌ์ ์ผ๋ก ์ ์ฅ
ํ๋ก๊ทธ๋๋ฐ์ ๊ณต๋ถํ๋ฉด์ ์ด๋ฐ ๊ฐ๋ ๋ค์ ์ ๋๋ก ์ดํดํ๊ณ ์์ผ๋ฉด, ๋ ์์ ์ ์ด๊ณ ์ ๋ขฐํ ์ ์๋ ์์คํ ์ ๋ง๋ค ์ ์์ด. ๊ทธ๋ฆฌ๊ณ ๋ฉด์ ์์๋ ์ ๋ง ์์ฃผ ๋์ค๋ ์ง๋ฌธ์ด๋๊น ๊ผญ ์์งํด๋๊ธธ ๋ฐ๋ผ! ๐
ํน์ ๋ ๊ถ๊ธํ ๊ฒ ์๊ฑฐ๋, ์ค๋ฌด์์ ํธ๋์ญ์ ๊ด๋ จ ๋ฌธ์ ๋ฅผ ๊ฒช๊ณ ์๋ค๋ฉด, ์ฌ๋ฅ๋ท์ ์ง์์ธ์ ์ฒ์ด๋ ์ ๋ฌธ๊ฐ๋ค์๊ฒ ์ง๋ฌธํด๋ณด๋ ๊ฒ๋ ์ข์ ๋ฐฉ๋ฒ์ด์ผ. ํจ๊ป ๋ฐฐ์ฐ๊ณ ์ฑ์ฅํ๋ ๊ฒ ํ๋ก๊ทธ๋๋ฐ์ ๋งค๋ ฅ์ด๋๊น! ๐ฑ
์, ์ด์ ์ง์ ์ฝ๋๋ฅผ ์์ฑํด๋ณด๋ฉด์ ํธ๋์ญ์ ์ ์ฒดํํด๋ด! ์ด๋ก ๋ง ์๋ ๊ฒ๋ณด๋ค ์ง์ ํด๋ณด๋ ๊ฒ ๋ฐฑ๋ฐฐ ๋ซ๊ฑฐ๋ . ํ์ดํ ! ๐ชโจ
๊ด๋ จ ํค์๋
๋๊ธ ์์ฑ
์ด ๊ธ์ ๋ํ ์ฌ๋ฌ๋ถ์ ์๊ฐ์ ๋ค๋ ค์ฃผ์ธ์
๋ก๊ทธ์ธ์ด ํ์ํฉ๋๋ค
๋๊ธ์ ์์ฑํ๋ ค๋ฉด ๋จผ์ ๋ก๊ทธ์ธํด์ฃผ์ธ์.
๋๊ธ 0
์ง์์ธ์ ์ฒ - ์ง์ ์ฌ์ฐ๊ถ ๋ณดํธ ๊ณ ์ง
์ง์ ์ฌ์ฐ๊ถ ๋ณดํธ ๊ณ ์ง
- ์ ์๊ถ ๋ฐ ์์ ๊ถ: ๋ณธ ์ปจํ ์ธ ๋ ์ฌ๋ฅ๋ท์ ๋ ์ AI ๊ธฐ์ ๋ก ์์ฑ๋์์ผ๋ฉฐ, ๋ํ๋ฏผ๊ตญ ์ ์๊ถ๋ฒ ๋ฐ ๊ตญ์ ์ ์๊ถ ํ์ฝ์ ์ํด ๋ณดํธ๋ฉ๋๋ค.
- AI ์์ฑ ์ปจํ ์ธ ์ ๋ฒ์ ์ง์: ๋ณธ AI ์์ฑ ์ปจํ ์ธ ๋ ์ฌ๋ฅ๋ท์ ์ง์ ์ฐฝ์๋ฌผ๋ก ์ธ์ ๋๋ฉฐ, ๊ด๋ จ ๋ฒ๊ท์ ๋ฐ๋ผ ์ ์๊ถ ๋ณดํธ๋ฅผ ๋ฐ์ต๋๋ค.
- ์ฌ์ฉ ์ ํ: ์ฌ๋ฅ๋ท์ ๋ช ์์ ์๋ฉด ๋์ ์์ด ๋ณธ ์ปจํ ์ธ ๋ฅผ ๋ณต์ , ์์ , ๋ฐฐํฌ, ๋๋ ์์ ์ ์ผ๋ก ํ์ฉํ๋ ํ์๋ ์๊ฒฉํ ๊ธ์ง๋ฉ๋๋ค.
- ๋ฐ์ดํฐ ์์ง ๊ธ์ง: ๋ณธ ์ปจํ ์ธ ์ ๋ํ ๋ฌด๋จ ์คํฌ๋ํ, ํฌ๋กค๋ง, ๋ฐ ์๋ํ๋ ๋ฐ์ดํฐ ์์ง์ ๋ฒ์ ์ ์ฌ์ ๋์์ด ๋ฉ๋๋ค.
- AI ํ์ต ์ ํ: ์ฌ๋ฅ๋ท์ AI ์์ฑ ์ปจํ ์ธ ๋ฅผ ํ AI ๋ชจ๋ธ ํ์ต์ ๋ฌด๋จ ์ฌ์ฉํ๋ ํ์๋ ๊ธ์ง๋๋ฉฐ, ์ด๋ ์ง์ ์ฌ์ฐ๊ถ ์นจํด๋ก ๊ฐ์ฃผ๋ฉ๋๋ค.
์์ง ๋๊ธ์ด ์์ต๋๋ค.