Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> MySQL

ใช้ Function เป็น Default Value ใน MySQL ไม่ได้ - ใช้ Trigger แทน

MySQL ไม่รองรับ การใช้ Function (เช่น NOW(), UUID(), RAND()) เป็น DEFAULT VALUE โดยตรง (ยกเว้น CURRENT_TIMESTAMP สำหรับ TIMESTAMP/DATETIME)

วิธีแก้: ใช้ BEFORE INSERT TRIGGER

1. สร้างตาราง

CREATE TABLE TbLFunctionTrigger (
    id CHAR(36),  -- สำหรับ UUID
    username VARCHAR(100)
);

2. สร้าง Trigger ก่อน Insert

DELIMITER //
CREATE TRIGGER insertBef
BEFORE INSERT ON TbLFunctionTrigger
FOR EACH ROW
BEGIN
    IF NEW.id IS NULL OR NEW.id = '' THEN
        SET NEW.id = UUID();
    END IF;
END //
DELIMITER ;

3. ทดสอบ Insert

INSERT INTO TbLFunctionTrigger (username) VALUES ('John');
INSERT INTO TbLFunctionTrigger (username) VALUES ('Jane');

SELECT * FROM TbLFunctionTrigger;
+--------------------------------------+----------+
| id                                   | username |
+--------------------------------------+----------+
| 550e8400-e29b-41d4-a716-446655440000 | John     |
| 550e8400-e29b-41d4-a716-446655440001 | Jane     |
+--------------------------------------+----------+

ตัวอย่าง Default Values อื่นๆ ด้วย Trigger

Default Timestamp (หากไม่ใช่ TIMESTAMP Column)

CREATE TRIGGER set_created_at
BEFORE INSERT ON my_table
FOR EACH ROW
SET NEW.created_at = IFNULL(NEW.created_at, NOW());

Default Random Number

CREATE TRIGGER set_random_token
BEFORE INSERT ON tokens
FOR EACH ROW
SET NEW.token = FLOOR(RAND() * 1000000);

Default จาก Table อื่น

CREATE TRIGGER set_default_category
BEFORE INSERT ON products
FOR EACH ROW
BEGIN
    IF NEW.category_id IS NULL THEN
        SELECT id INTO NEW.category_id FROM categories WHERE is_default = 1 LIMIT 1;
    END IF;
END;

ข้อจำกัดของ Trigger Default

  • เพิ่ม Overhead เล็กน้อยตอน INSERT
  • ไม่ทำงานกับ LOAD DATA INFILE (บาง Version)
  • Debug ยากกว่า Default Value ธรรมดา
  • ต้องระวัง Recursive Trigger

MySQL 8.0.13+ รองรับ Functional Default

-- MySQL 8.0.13+ รองรับได้บาง Function
CREATE TABLE t (
    id INT PRIMARY KEY,
    created_at DATETIME DEFAULT (NOW()),  -- Works!
    uuid_val CHAR(36) DEFAULT (UUID())    -- Works!
);

⚠️ แต่ยังมีข้อจำกัด: ไม่รองรับ Subquery, Stored Functions, Variables