การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง
ทำความเข้าใจว่ารูปแบบใดของ ALTER TABLE ใช้การล็อก ACCESS EXCLUSIVE และเขียนตารางใหม่ และรูปแบบใดเปลี่ยนเฉพาะข้อมูลกำกับ
การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง เป็นบทเรียน SQL Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 1 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน SQL Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส SQL Academy มีบทเรียนทั้งหมด 4 บทเรียน
ปัญหาการปรับเปลี่ยนฐานข้อมูลในระบบจริง
สำหรับฐานข้อมูลขนาดเล็ก ALTER TABLE ทำงานได้ทันที แต่สำหรับตารางที่ใช้งานอยู่และมีขนาด 500GB คำสั่งเดียวกันอาจล็อกการเขียนไว้นาน 20 นาที การทราบว่า ALTER ใดปลอดภัยและ ALTER ใดไม่ปลอดภัยจึงเป็นสิ่งจำเป็น
ระดับการล็อก
การล็อกของ PostgreSQL มีหลายระดับ:
- ACCESS SHARE — การเลือกข้อมูล
- ROW EXCLUSIVE — การเขียนข้อมูล
- SHARE / SHARE ROW EXCLUSIVE — DDL ที่ทำงานร่วมกับการอ่านข้อมูล
- EXCLUSIVE — บล็อกการเลือกข้อมูล
- ACCESS EXCLUSIVE — บล็อก EVERYTHING
ALTER TABLE ใช้การล็อกระดับใด
ALTER ส่วนใหญ่ใช้การล็อกระดับ ACCESS EXCLUSIVE — จะบล็อกทั้งผู้อ่านและผู้เขียนจนกว่าจะทำงานเสร็จ
ALTER ที่รวดเร็ว (เปลี่ยนเฉพาะข้อมูลเมตา)
ALTER บางรูปแบบเปลี่ยนเฉพาะแค็ตตาล็อก และทำงานเสร็จภายในไม่กี่มิลลิวินาที แม้กับตารางขนาดใหญ่มาก:
ALTER TABLE t RENAME COLUMN a TO b;
ALTER TABLE t ALTER COLUMN a SET DEFAULT ...;
ALTER TABLE t ADD COLUMN x INT; -- nullable, no default: metadata only (PG 11+)
ALTER TABLE t ADD COLUMN x INT NOT NULL DEFAULT 0; -- metadata only PG 11+ if default is constantALTER ที่ช้า (เขียนตารางใหม่)
ALTER เหล่านี้จะเขียนตารางทั้งตารางใหม่:
ALTER TABLE t ALTER COLUMN x TYPE BIGINT; -- when types not binary-compatible
ALTER TABLE t SET LOGGED;
CLUSTER t USING idx; -- physically reorders rows
VACUUM FULL t; -- rewrites whole tableการเพิ่ม NOT NULL อย่างปลอดภัย
สำหรับตารางขนาดใหญ่:
-- BAD: full table scan + ACCESS EXCLUSIVE lock
ALTER TABLE t ALTER COLUMN x SET NOT NULL;
-- BETTER:
ALTER TABLE t ADD CONSTRAINT x_not_null CHECK (x IS NOT NULL) NOT VALID;
ALTER TABLE t VALIDATE CONSTRAINT x_not_null; -- scans without exclusive lock
-- then drop the CHECK and add NOT NULL (still cheap because already validated):
ALTER TABLE t ALTER COLUMN x SET NOT NULL;
ALTER TABLE t DROP CONSTRAINT x_not_null;การเพิ่มคีย์ต่างประเทศแบบออนไลน์
ใช้เทคนิค NOT VALID แบบเดียวกัน:
ALTER TABLE orders
ADD CONSTRAINT orders_user_fk FOREIGN KEY (user_id) REFERENCES users(id) NOT VALID;
ALTER TABLE orders VALIDATE CONSTRAINT orders_user_fk;ปัญหาการรอการล็อก
ALTER ที่กำลังรอการล็อกระดับ ACCESS EXCLUSIVE จะต่อคิวอยู่หลังธุรกรรมที่ทำงานเป็นเวลานานทุกธุรกรรม ธุรกรรมใหม่ก็จะต่อคิวอยู่หลัง ALTER เช่นกัน ทำให้เกิดห่วงโซ่ของ query ที่ถูกบล็อก
การจำกัดเวลารอการล็อก
อย่าปล่อยให้การปรับเปลี่ยนฐานข้อมูลค้างอยู่ตลอดไป:
SET lock_timeout = '5s';
ALTER TABLE t ...;
-- ERROR if it can't get the lock in 5s — retry.ลูปการลองใหม่
การปรับเปลี่ยนฐานข้อมูลควรลองใหม่เมื่อเกิด lock_timeout:
for (let i = 0; i < 20; i++) {
try {
await client.query('SET lock_timeout = 5000');
await client.query('ALTER TABLE ...');
break;
} catch (e) {
if (e.code === '55P03') continue; // lock_not_available
throw e;
}
}การใช้การจำกัดเวลาของคำสั่งเพื่อความปลอดภัย
จำกัดระยะเวลาที่คำสั่งแต่ละคำสั่งภายในการปรับเปลี่ยนฐานข้อมูลจะทำงานได้:
SET statement_timeout = '30s';เครื่องมือที่ช่วยได้
- strong_migrations (Rails)
- django-migrate-zero-downtime
- pg-osc (การเปลี่ยนแปลงสคีมาออนไลน์ของ Postgres)
- pgRoll
สรุป
การปรับเปลี่ยนฐานข้อมูลแบบออนไลน์ต้องคำนึงถึง:
- ALTER ใดเปลี่ยนเฉพาะข้อมูลเมตา และ ALTER ใดเขียนตารางใหม่
- การใช้ NOT VALID + VALIDATE กับข้อจำกัด
- การตั้งค่า lock_timeout และการลองใหม่
- การหลีกเลี่ยงธุรกรรมที่ทำงานเป็นเวลานานและบล็อกการปรับเปลี่ยนฐานข้อมูล
แบบทดสอบสั้น ๆ
คุณเพิ่มข้อจำกัด NOT NULL ให้กับตารางขนาด 500GB ด้วย ALTER TABLE เพียงครั้งเดียว การเขียนข้อมูลจะเกิดอะไรขึ้น
คำถามที่พบบ่อย
บทเรียน “การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง” ฟรีหรือไม่
ใช่ — ข้อความเต็มของ “การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส SQL Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส SQL Academy มีบทเรียนทั้งหมด 4 บทเรียน
คุณจะเรียนรู้อะไรในบทเรียน “การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง”
ทำความเข้าใจว่ารูปแบบใดของ ALTER TABLE ใช้การล็อก ACCESS EXCLUSIVE และเขียนตารางใหม่ และรูปแบบใดเปลี่ยนเฉพาะข้อมูลกำกับ คุณปฏิบัติ SQL Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน
คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน SQL Academy หรือไม่
ไม่จำเป็นต้องมีประสบการณ์มาก่อน SQL Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 1 จากทั้งหมด 4 บทเรียน
บทเรียน “การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง” ใช้เวลานานแค่ไหน
บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย
ฉันเขียนและรันโค้ดในบทเรียน SQL Academy นี้ได้ไหม
ได้ บทเรียน SQL Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ
บทเรียนทั้งหมดในหลักสูตรนี้
- การย้ายข้อมูลแบบออนไลน์: เหตุผลที่ ALTER TABLE ล็อกตาราง
- ดัชนีแบบทำงานพร้อมกัน (CREATE INDEX CONCURRENTLY)
- การเปลี่ยนชื่อคอลัมน์โดยไม่หยุดให้บริการ
- เครื่องมือ: Flyway, Liquibase, Sqitch