การแก้ไขปัญหา Multiple Foreign Key
ใน MySQL: คู่มือทีละขั้นตอน
เมื่อทำงานกับฐานข้อมูล โดยเฉพาะใน MySQL คุณอาจพบสถานการณ์ที่ต้องการเพิ่มคีย์ต่างประเทศหลายตัวที่อ้างอิงถึงตารางหลักเดียวกัน ซึ่งสิ่งนี้อาจเป็นเรื่องที่ท้าทาย โดยเฉพาะอย่างยิ่งในปัญหาที่ผู้ใช้หลายคนเผชิญ เช่น การเชื่อมโยงผู้ขายที่แตกต่างกันภายในตารางรายละเอียดการจัดส่ง ในโพสต์นี้เราจะสำรวจคำถามทั่วไปเกี่ยวกับคีย์ต่างประเทศหลายตัว โดยให้แนวทางที่มีโครงสร้างรวมถึงแนวทางปฏิบัติที่ดีที่สุด และแนะนำคุณผ่านกระบวนการแก้ไขปัญหา
ปัญหา
ลองนึกภาพว่าคุณมีตาราง SHIPPING_DETAILS
ที่รับผิดชอบในการติดตามผู้ให้บริการจัดส่ง (เช่น FedEx หรือ UPS) และผู้ให้บริการในการจัดการผลิตภัณฑ์ (ลองคิดถึง Dunder Mifflin) ในกรณีนี้ หลายคอลัมน์ในรายละเอียดการจัดส่งต้องอิงอ้างถึงตารางหลักเดียวกัน คือ VENDOR
อย่างไรก็ตาม อาจมีปัญหาเกิดขึ้นเมื่อคุณพยายามสร้างข้อกำหนดคีย์ต่างประเทศสำหรับคอลัมน์เหล่านี้ เช่น ไม่สามารถกำหนดคีย์ต่างประเทศหลายตัวได้
ผู้ใช้งานมักพบข้อผิดพลาดเช่น:
Can't create table './<DB_NAME>/SHIPPING_GRID.frm' (errno: 150)
ข้อผิดพลาดนี้มักจะชี้ให้เห็นถึงปัญหากับการกำหนดคีย์ต่างประเทศหรือลักษณะข้อมูลที่เกี่ยวข้อง
ภาพรวมของแนวทางแก้ไข
ในการแก้ไขปัญหาการกำหนดคีย์ต่างประเทศหลายตัวใน MySQL ให้ทำตามขั้นตอนต่อไปนี้:
-
กำหนดโครงสร้างตารางอย่างถูกต้อง: ตรวจสอบให้แน่ใจว่าตาราง
VENDOR
ของคุณมีคีย์หลักที่ไม่ซ้ำกันซึ่งเข้ากันได้กับคอลัมน์คีย์ต่างประเทศในตารางSHIPPING_DETAILS
ของคุณ -
แก้ไขประเภทตาราง: ให้แน่ใจว่าทั้งสองตาราง (
VENDOR
และSHIPPING_GRID
) มีประเภทเป็นInnoDB
ซึ่งเป็นสิ่งสำคัญ เนื่องจากข้อกำหนดคีย์ต่างประเทศไม่สนับสนุนในเครื่องจัดเก็บข้อมูลอื่น เช่น MyISAM -
ตรวจสอบความเข้ากันได้ของประเภทข้อมูล: ยืนยันว่าประเภทข้อมูลของคีย์ต่างประเทศตรงกับประเภทข้อมูลของคีย์หลักที่มันอ้างอิง ตัวอย่างเช่น หาก
VENDOR.no
ถูกกำหนดเป็นINT(6)
คีย์ต่างประเทศทั้งหมดต้องเป็นประเภทเดียวกัน -
หลีกเลี่ยงการกำหนดคีย์หลักซ้ำกัน: ตรวจสอบให้แน่ใจว่า SQL ของคุณไม่รวมข้อกำหนดคีย์หลักที่ซ้ำกันโดยไม่ตั้งใจ สิ่งนี้อาจนำไปสู่ข้อผิดพลาดขณะสร้างตาราง
ตัวอย่างโค้ด
นี่คือตัวอย่างที่ถูกต้องว่า ตาราง SHIPPING_GRID
ของคุณจะถูกกำหนดอย่างถูกต้องอย่างไรหลังจากพิจารณาจุดด้านบน:
CREATE TABLE SHIPPING_GRID(
id INT NOT NULL AUTO_INCREMENT PRIMARY KEY COMMENT 'Unique ID for each row',
shipping_vendor_no INT(6) NOT NULL COMMENT 'Foreign key to VENDOR.no for the shipping vendor (vendors_type must be 3)',
start_vendor_no INT(6) NOT NULL COMMENT 'Foreign key to VENDOR.no for the vendor being shipped from',
end_vendor_no INT(6) NOT NULL COMMENT 'Foreign key to the VENDOR.no for the vendor being shipped to',
shipment_duration INT(1) DEFAULT 1 COMMENT 'Duration in whole days shipment will take',
price FLOAT(5,5) NOT NULL COMMENT 'Price in US dollars per shipment lbs (down to 5 decimal places)',
is_flat_rate TINYINT(1) DEFAULT 0 COMMENT '1 if is flat rate regardless of weight, 0 if price is by lbs',
INDEX (shipping_vendor_no),
INDEX (start_vendor_no),
INDEX (end_vendor_no),
FOREIGN KEY (shipping_vendor_no) REFERENCES VENDOR (no),
FOREIGN KEY (start_vendor_no) REFERENCES VENDOR (no),
FOREIGN KEY (end_vendor_no) REFERENCES VENDOR (no)
) ENGINE=InnoDB;
ข้อคิดสำคัญ
- ประเภทข้อมูลสำคัญ: ตรวจสอบให้แน่ใจว่าคอลัมน์คีย์ต่างประเทศตรงกับประเภทข้อมูลของคีย์หลักที่ถูกอ้างอิงเสมอ
- ใช้ InnoDB: หากคุณกำลังตั้งค่าคีย์ต่างประเทศข้ามตาราง การใช้เครื่องยนต์
InnoDB
เป็นสิ่งที่จำเป็น - หลีกเลี่ยงการซ้ำซ้อน: หากคุณพบว่า SQL ของคุณสร้างข้อผิดพลาด ให้ตรวจสอบการกำหนดซ้ำหรือลักษณะทางไวยากรณ์ให้ดี
ด้วยการปฏิบัติตามแนวทางเหล่านี้ คุณสามารถสร้างตารางของคุณด้วยคีย์ต่างประเทศหลายตัวได้อย่างมีประสิทธิภาพ และหลีกเลี่ยงข้อผิดพลาดที่พบบ่อยที่เกี่ยวข้องกับข้อกำหนดคีย์ต่างประเทศ ขอให้โชคดีในการทำงานกับ MySQL ของคุณและสนุกกับการเขียนโค้ด!