Câu lệnh INSERT ... ON DUPLICATE KEY UPDATE (upsert) yêu cầu bảng có Primary Key hoặc Unique Index trên cột cần kiểm tra trùng lặp. Để thêm ràng buộc này cho cột hiện có, dùng ALTER TABLE ... ADD CONSTRAINT ... UNIQUE.
Ví dụ minh họa
Tạo bảng (chưa có unique trên Name):
mysql> CREATE TABLE DemoTable1459 (
Name VARCHAR(20),
Score INT
);
Thêm Unique Constraint tên Name_const trên cột Name:
mysql> ALTER TABLE DemoTable1459
ADD CONSTRAINT Name_const UNIQUE (Name);
Kiểm tra cấu trúc (Key = UNI):
mysql> SHOW INDEX FROM DemoTable1459;
Thử INSERT ... ON DUPLICATE KEY UPDATE
mysql> INSERT INTO DemoTable1459 VALUES ('Chris', 57)
ON DUPLICATE KEY UPDATE Score = Score + 10;
-- Query OK, 1 row affected (INSERT mới)
mysql> INSERT INTO DemoTable1459 VALUES ('David', 89)
ON DUPLICATE KEY UPDATE Score = Score + 10;
-- Query OK, 1 row affected (INSERT mới)
mysql> INSERT INTO DemoTable1459 VALUES ('Chris', 78)
ON DUPLICATE KEY UPDATE Score = Score + 10;
-- Query OK, 2 rows affected (UPDATE: Score 57 → 67)
Kết quả cuối:
mysql> SELECT * FROM DemoTable1459;
+-------+-------+ | Name | Score | +-------+-------+ | Chris | 67 | | David | 89 | +-------+-------+
Giải thích
- Lần 1: 'Chris' chưa có → INSERT mới (Score=57).
- Lần 2: 'David' chưa có → INSERT mới (Score=89).
- Lần 3: 'Chris' đã có (vi phạm UNIQUE) → UPDATE: Score = 57 + 10 = 67. MySQL báo
2 rows affectedcho UPDATE (1 row matched + 1 row changed).
Các cách tạo Unique Constraint
| Cú pháp | Mô tả |
|---|---|
ALTER TABLE t ADD CONSTRAINT name UNIQUE (col) | Có tên constraint (khuyên dùng) |
ALTER TABLE t ADD UNIQUE (col) | Tự động đặt tên |
ALTER TABLE t ADD UNIQUE INDEX idx_name (col) | Tạo unique index (tương đương) |
CREATE UNIQUE INDEX idx_name ON t (col) | Cú pháp riêng cho index |
| Khi CREATE TABLE | Name VARCHAR(20) UNIQUE hoặc CONSTRAINT name UNIQUE (Name) |
Composite Unique (Nhiều cột)
-- Unique trên cặp (UserId, CourseId) - một user chỉ đăng ký 1 khóa học 1 lần ALTER TABLE Enrollments ADD CONSTRAINT uq_user_course UNIQUE (UserId, CourseId);
Lưu ý
- Dữ liệu hiện có phải không trùng lặp trên cột unique mới — nếu có trùng,
ALTER TABLEsẽ lỗi. - Unique index cho phép nhiều
NULL(trừ SQL Server). ON DUPLICATE KEY UPDATEchỉ hoạt động với PK hoặc Unique Key — không hoạt động với index thường (non-unique).