MySQLのinsert on duplicate key update と replace構文の違い

忘れてたので思い出しながらメモ

TL;DR

  • upsert構文として、insert on duplicate key update と replace構文の2つがある
  • 似たような挙動だけど違う
  • insert on duplicate key update はupdate
  • replace構文はdelete insert になる。

実際にやってみた

こういうテーブルを作ってみる

CREATE TABLE `replace_sample` (
  `id` bigint(20) NOT NULL AUTO_INCREMENT,
  `email` varchar(255) NOT NULL,
  `name` varchar(100) NOT NULL,
  PRIMARY KEY (`id`),
  UNIQUE KEY `email` (`email`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4
insert into replace_sample(email,name)values('taro@example.com','taro'), ('jiro@example.com','jiro');
mysql> select * from replace_sample;
+----+------------------+------+
| id | email            | name |
+----+------------------+------+
|  1 | taro@example.com | taro |
|  2 | jiro@example.com | jiro |
+----+------------------+------+

insert on duplicate key update を投げる

mysql> insert into replace_sample(email, name) values('taro@example.com', 'saburo') on duplicate key update name='saburo';
Query OK, 2 rows affected (0.00 sec)

mysql> select * from replace_sample;
+----+------------------+--------+
| id | email            | name   |
+----+------------------+--------+
|  1 | taro@example.com | saburo |
|  2 | jiro@example.com | jiro   |
+----+------------------+--------+
2 rows in set (0.01 sec)

replace構文を投げる

mysql> replace into replace_sample(email,name) values('taro@example.com', 'ichiro');
Query OK, 2 rows affected (0.00 sec)

mysql> select * from replace_sample;
+----+------------------+--------+
| id | email            | name   |
+----+------------------+--------+
|  2 | jiro@example.com | jiro   |
|  3 | taro@example.com | ichiro |
+----+------------------+--------+
2 rows in set (0.01 sec)

delete - insert されているのがわかる

リンク