การตรวจสอบตารางด้วยทริกเกอร์
สร้างประวัติการตรวจสอบด้วยทริกเกอร์ AFTER INSERT/UPDATE/DELETE ที่เขียนข้อมูลลงในตาราง audit_log
การตรวจสอบตารางด้วยทริกเกอร์ เป็นบทเรียน SQL Academy ฟรีบน CoddyKit นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน คุณสามารถอ่านบทเรียนทั้งหมดด้านล่างฟรี — จากนั้นลองปฏิบัติด้วยตัวคุณเองในเบราว์เซอร์พร้อมตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7 บทเรียนนี้เป็นส่วนหนึ่งของเส้นทางการเรียน SQL Academy และความก้าวหน้าของคุณจะซิงค์ข้ามเว็บและแอป CoddyKit คอร์ส SQL Academy มีบทเรียนทั้งหมด 4 บทเรียน
เหตุใดจึงต้องมีการตรวจสอบ
บันทึกการตรวจสอบช่วยตอบว่า "ใครเปลี่ยนแปลงอะไร เมื่อใด" จำเป็นต่อการปฏิบัติตามข้อกำหนด (HIPAA, SOX, การสืบสวนตามสิทธิ์ในการลบข้อมูลของ GDPR) และการสืบหาสาเหตุเชิงปฏิบัติการ
ตารางตรวจสอบ
ตารางศูนย์กลางหนึ่งตารางจะบันทึกการเปลี่ยนแปลงทุกครั้ง:
CREATE TABLE audit_log (
id BIGSERIAL PRIMARY KEY,
ts TIMESTAMPTZ NOT NULL DEFAULT NOW(),
user_name TEXT NOT NULL DEFAULT CURRENT_USER,
table_name TEXT NOT NULL,
action TEXT NOT NULL, -- INSERT, UPDATE, DELETE
row_id TEXT,
old_data JSONB,
new_data JSONB
);ฟังก์ชันทริกเกอร์ตรวจสอบ
ฟังก์ชันเดียวที่นำกลับมาใช้ซ้ำได้กับหลายตาราง:
CREATE OR REPLACE FUNCTION audit_row()
RETURNS TRIGGER AS $$
BEGIN
INSERT INTO audit_log (table_name, action, row_id, old_data, new_data)
VALUES (
TG_TABLE_NAME,
TG_OP,
COALESCE(NEW.id::TEXT, OLD.id::TEXT),
CASE WHEN TG_OP IN ('UPDATE','DELETE') THEN to_jsonb(OLD) END,
CASE WHEN TG_OP IN ('INSERT','UPDATE') THEN to_jsonb(NEW) END
);
RETURN COALESCE(NEW, OLD);
END;
$$ LANGUAGE plpgsql;แนบทริกเกอร์กับตาราง
สร้างทริกเกอร์เมื่อ AFTER INSERT/UPDATE/DELETE:
CREATE TRIGGER trg_audit_users
AFTER INSERT OR UPDATE OR DELETE ON users
FOR EACH ROW EXECUTE FUNCTION audit_row();to_jsonb(NEW)
เทคนิค to_jsonb จะจับภาพทั้งแถวแบบทั่วไป โดยไม่ต้องเขียนโค้ดแยกตามคอลัมน์ ใช้ได้กับทุกตารางที่มีคอลัมน์ id
ติดตามผู้กระทำ
หากแอปทำงานโดยใช้ผู้ใช้ฐานข้อมูลรายเดียว CURRENT_USER ก็ไม่เพียงพอ ให้ส่งผู้ใช้ของแอปผ่าน GUC ของเซสชัน:
-- App sets:
SET LOCAL app.user_id = '42';
-- Trigger reads:
INSERT INTO audit_log (... actor_id ...) VALUES (..., current_setting('app.user_id', true)::BIGINT);ตรวจสอบคอลัมน์เฉพาะ
ใช้ส่วนคำสั่ง WHEN ของทริกเกอร์เพื่อเลือกตรวจสอบเฉพาะกรณี:
CREATE TRIGGER trg_audit_role_change
AFTER UPDATE OF role ON users
FOR EACH ROW WHEN (OLD.role IS DISTINCT FROM NEW.role)
EXECUTE FUNCTION audit_role_change();ตารางตรวจสอบแยกตามตาราง
อีกทางเลือกหนึ่งคือสร้างตารางตรวจสอบหนึ่งตารางต่อตารางจริง เช่น users_audit โดยใช้โครงสร้างเดียวกันพร้อมข้อมูลเมตาสำหรับตรวจสอบ สอบถามได้ง่ายกว่า แต่ต้องดูแล DDL มากขึ้น
ตรวจสอบเฉพาะส่วนต่าง
จัดเก็บเฉพาะคอลัมน์ที่เปลี่ยนแปลง:
INSERT INTO audit_log (table_name, action, changes)
VALUES (
TG_TABLE_NAME, TG_OP,
(SELECT jsonb_object_agg(key, value)
FROM jsonb_each(to_jsonb(NEW))
WHERE NEW.* IS DISTINCT FROM OLD.* AND to_jsonb(NEW)->key IS DISTINCT FROM to_jsonb(OLD)->key)
);ประสิทธิภาพของตารางตรวจสอบ
ตารางตรวจสอบจะเติบโตอย่างรวดเร็วในระบบที่มีการใช้งานสูง ให้แบ่งพาร์ทิชันตามเวลา:
CREATE TABLE audit_log (...) PARTITION BY RANGE (ts);
CREATE TABLE audit_log_2024_q1 PARTITION OF audit_log
FOR VALUES FROM ('2024-01-01') TO ('2024-04-01');ข้อแลกเปลี่ยนด้านประสิทธิภาพ
ตอนนี้การ INSERT/UPDATE/DELETE แต่ละครั้งจะเขียนแถวที่สองเพิ่มด้วย สำหรับตารางที่มีการเขียนข้อมูลจำนวนมาก วิธีนี้อาจทำให้การรับส่งข้อมูลเพิ่มขึ้นเป็นสองเท่า โปรดทดสอบ เฝ้าติดตาม และตัดสินใจว่าข้อแลกเปลี่ยนนี้คุ้มค่าหรือไม่
กรณีที่ไม่ควรใช้ทริกเกอร์ฐานข้อมูล
หากคุณต้องเชื่อมต่อกับบัสเหตุการณ์ จัดคิวเหตุการณ์ด้วย NOTIFY หรือ LISTEN หรือใช้เครื่องมือการจำลองแบบเชิงตรรกะ / CDC (Debezium) แทนทริกเกอร์
สรุป
ทริกเกอร์ตรวจสอบเป็นวิธีที่ง่ายที่สุดในการบันทึกประวัติ
- ใช้ฟังก์ชันทั่วไปหนึ่งฟังก์ชันร่วมกับ to_jsonb(NEW/OLD)
- แนบฟังก์ชันกับทุกตารางที่ต้องตรวจสอบ
- แบ่งพาร์ทิชันตารางตรวจสอบตามเวลา
- ติดตามผู้กระทำของแอปอย่างชัดเจนผ่าน GUC
ตรวจสอบอย่างรวดเร็ว
ภายในฟังก์ชันทริกเกอร์ตรวจสอบ คุณจะจับแถวใหม่เป็น JSONB แบบทั่วไปได้อย่างไร?
เรียนรู้ SQL ด้วย AI tutor — ฟรี
เขียนและเรียกใช้โค้ดจริงในเบราว์เซอร์ของคุณ รับความช่วยเหลือทันทีจาก AI tutor 24/7 และเรียนรู้ต่อจากที่คุณหยุดบนเว็บหรือในแอป
- คอร์ส
- 46
- บทเรียน
- 183
คำถามที่พบบ่อย
บทเรียน “การตรวจสอบตารางด้วยทริกเกอร์” ฟรีหรือไม่
ใช่ — ข้อความเต็มของ “การตรวจสอบตารางด้วยทริกเกอร์” ฟรีให้อ่านที่นี่บนเว็บ เพื่อปฏิบัติแบบโต้ตอบ (ตัวแก้ไขโค้ดในตัวและติวเตอร์ AI ตลอด 24/7) และปลดล็อคส่วนที่เหลือของคอร์ส SQL Academy ให้อัปเกรดเป็น CoddyKit PRO คอร์ส SQL Academy มีบทเรียนทั้งหมด 4 บทเรียน
คุณจะเรียนรู้อะไรในบทเรียน “การตรวจสอบตารางด้วยทริกเกอร์”
สร้างประวัติการตรวจสอบด้วยทริกเกอร์ AFTER INSERT/UPDATE/DELETE ที่เขียนข้อมูลลงในตาราง audit_log คุณปฏิบัติ SQL Academy ด้วยโค้ดที่ใช้งานได้จริงที่คุณเรียกใช้โดยตรงในเบราว์เซอร์ และติวเตอร์ AI ตลอด 24/7 ตอบคำถามของคุณขณะที่คุณไปผ่านบทเรียน
คุณต้องมีประสบการณ์ก่อนที่จะเริ่มเรียน SQL Academy หรือไม่
ไม่จำเป็นต้องมีประสบการณ์มาก่อน SQL Academy บน CoddyKit ออกแบบมาสำหรับผู้เริ่มต้นไปจนถึงผู้เรียนขั้นสูง คุณสามารถเริ่มต้นที่นี่หรือเริ่มจากตัวแรกและเรียนด้วยความเร็วของคุณเอง นี่คือบทเรียนที่ 4 จากทั้งหมด 4 บทเรียน
บทเรียน “การตรวจสอบตารางด้วยทริกเกอร์” ใช้เวลานานแค่ไหน
บทเรียน CoddyKit ส่วนใหญ่ใช้เวลาประมาณ 5–10 นาที แต่ละบทเรียนจึงสั้นและเป็นแบบโต้ตอบ คุณสามารถก้าวหน้าอย่างต่อเนื่องและกลับมาเรียนต่อจากตรงที่เพิ่งหยุดบนเว็บและแอปได้เลย
ฉันเขียนและรันโค้ดในบทเรียน SQL Academy นี้ได้ไหม
ได้ บทเรียน SQL Academy ทุกบทมีตัวแก้ไขโค้ดในตัว คุณจึงเขียนและรันโค้ดจริงได้เลยในเบราว์เซอร์ และได้รับข้อเสนอแนะจาก AI ในทันที — ไม่ต้องติดตั้งในเครื่องของคุณ
บทเรียนทั้งหมดในหลักสูตรนี้
- โครงสร้างทริกเกอร์: BEFORE/AFTER, FOR EACH ROW
- พื้นฐานฟังก์ชัน PL/pgSQL
- บล็อก DO และโค้ดนิรนาม
- การตรวจสอบตารางด้วยทริกเกอร์