ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails は、子のテーブル(注文など)に、親のテーブル(顧客など)に存在しない値を入れようとしたときのエラーです。 逆に、子から参照されている親を消そうとすると 1451 になります。

エラー 起きたこと 直し方
1452 Cannot add or update a child row 子に、親に無い値を入れようとした 先に親を登録する/値の間違いを直す
1451 Cannot delete or update a parent row 子から使われている親を消そう・変えようとした 先に子を消す/ON DELETE の動きを決める
3730 Cannot drop table ... referenced by a foreign key 子から参照されている親のテーブルを DROP 子の外部キーを先に消す
1701 Cannot truncate a table referenced in a foreign key 親を TRUNCATE DELETE を使う、または子を先に

確認環境:MySQL 8.0.46(InnoDB)(確認日 2026年10月11日)。顧客(customers2)と注文(orders2)の2つのテーブルで再現しました。

本記事の内容は、ご自由にお使いください。
ご利用の際は、出典として本ページへのリンクを記載いただけますようお願いします。

(記載例)出典:株式会社RJC「MySQL ERROR 1452の直し方|外部キー制約エラー」

再現と、エラー文の読み方

CREATE TABLE customers2 (id int PRIMARY KEY, name varchar(20));
CREATE TABLE orders2 (
  id int PRIMARY KEY,
  customer_id int NOT NULL,
  CONSTRAINT fk_orders_customer FOREIGN KEY (customer_id) REFERENCES customers2 (id)
);
INSERT INTO customers2 VALUES (1, '佐藤'), (2, '鈴木');
INSERT INTO orders2 VALUES (11, 3);          -- 顧客 3 はいない
ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails
(`mig`.`orders2`, CONSTRAINT `fk_orders_customer` FOREIGN KEY (`customer_id`) REFERENCES `customers2` (`id`))
部分 意味
`mig`.`orders2` 子のテーブル(入れようとした側)
FOREIGN KEY (`customer_id`) 子の列(入れようとした値の列)
REFERENCES `customers2` (`id`) 親のテーブルと列(ここに値が必要)

「orders2.customer_id に入れた値が、customers2.id に無い」と読みます。エラー文には値そのものは出ないので、入れようとした値(ここでは 3)を確かめ、親に存在するかを調べます。

SELECT * FROM customers2 WHERE id = 3;      -- 0 件なら、親が無い

1452 のよくある原因

原因 例
データを入れる順番が逆 移行で、注文を先に入れ、顧客をあとから入れる
値の間違い 存在しない ID・0・空文字が入ってくる(画面の初期値など)
親を消したあと 別の処理が先に顧客を消していた
既存の子データに、親の無い行がある ALTER TABLE ... ADD FOREIGN KEY が 1452 で失敗する
ALTER TABLE child2 ADD CONSTRAINT fk_child FOREIGN KEY (cid) REFERENCES customers2 (id);
ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails (`mig`.`#sql-1c4_78`, ...)

外部キーを後から追加するときは、テーブル名が #sql-... という一時的な名前で表示されました。 既存のデータに、親の無い行があるという意味です。

親の無い子データを探す

SELECT o.id, o.customer_id
FROM orders2 o
LEFT JOIN customers2 c ON c.id = o.customer_id
WHERE c.id IS NULL;
id  customer_id
11  3
12  99

LEFT JOIN で親がつながらなかった行が、親の無い子データです。親を登録するか、子のデータを直す・消すかを決めます。

1451:親を消そうとしたとき

DELETE FROM customers2 WHERE id = 1;
ERROR 1451 (23000): Cannot delete or update a parent row: a foreign key constraint fails
(`mig`.`orders2`, CONSTRAINT `fk_orders_customer` FOREIGN KEY (`customer_id`) REFERENCES `customers2` (`id`))

顧客 1 には注文があるため、消せません。親の ID を変える UPDATE も同じエラーになりました。

方法 内容
子を先に消す DELETE FROM orders2 WHERE customer_id = 1; → 親を消す
外部キーに ON DELETE CASCADE 親を消すと子も一緒に消える
外部キーに ON DELETE SET NULL 親を消すと子の列が NULL になる(列が NULL 可のとき)
消さずに「無効」の印を付ける 顧客に deleted_at などの列を持たせる

ON DELETE の動きの違いは、関連記事の「外部キーON DELETE CASCADE|SET NULL・RESTRICT比較」で詳しく比べています。

データ移行の順番

入れる(INSERT・取り込み) 消す(DELETE)
親 → 子(顧客 → 注文 → 注文明細) 子 → 親(注文明細 → 注文 → 顧客)

テーブルの数が多く順番を決めにくい場合に、FOREIGN_KEY_CHECKS を 0 にする方法もありますが、次の注意があります。

注意:FOREIGN_KEY_CHECKS=0 で入れた不整合は、後から別の更新を止める

SET FOREIGN_KEY_CHECKS = 0;
INSERT INTO orders2 VALUES (11, 3), (12, 99);   -- 親の無い行が入る(エラーにならない)
SET FOREIGN_KEY_CHECKS = 1;                      -- 戻してもエラーにならない

FOREIGN_KEY_CHECKS を 1 に戻しても、入れてしまった行はチェックされませんでした(MySQL 公式マニュアルでも、戻したときに既存のデータは確かめないとされています)。そして、その行はあとで関係のない更新を止めました。

その行への更新 結果
UPDATE orders2 SET customer_id = 99 WHERE id = 12(同じ値) エラーにならない(変更なし)
UPDATE orders2 SET id = 13 WHERE id = 12(外部キーと関係ない列) ERROR 1452

外部キーの列を変えていないのに 1452 になるので、原因が分かりにくくなります。FOREIGN_KEY_CHECKS = 0 で取り込んだあとは、必ず上の LEFT JOIN で、親の無い行が無いかを確かめます。

外部キーを作るときのエラー

CREATE TABLE bad_fk (id int PRIMARY KEY, cid bigint, FOREIGN KEY (cid) REFERENCES customers2 (id));
ERROR 3780 (HY000): Referencing column 'cid' and referenced column 'id' in foreign key constraint 'bad_fk_ibfk_1' are incompatible.

子の列と親の列の型が違う(bigint と int)と、外部キーを作れませんでした。公式マニュアルでは、整数の型は大きさと符号(UNSIGNED かどうか)、文字列の型は文字コードと照合順序までそろえる必要があるとされています。

もっと詳しく調べる:LATEST FOREIGN KEY ERROR

SHOW ENGINE INNODB STATUS\G
LATEST FOREIGN KEY ERROR
------------------------
... update orders2 set id=13 where id=12
Foreign key constraint fails for table `mig`.`orders2`:
  CONSTRAINT `fk_orders_customer` FOREIGN KEY (`customer_id`) REFERENCES `customers2` (`id`)
Trying to add in child table, in index fk_orders_customer tuple:
...

直近の外部キーのエラーで、実行した SQL と、どの制約に引っかかったかが残ります。アプリから実行した SQL が分からないときに使えます。

確認の手順(チェックリスト)

順番 確認すること 方法
1 1452 か 1451 か 1452 は子に入れる、1451 は親を消す・変える
2 子の列と親の表・列 エラー文の FOREIGN KEY (...) REFERENCES ... (...)
3 入れようとした値が親にあるか SELECT * FROM 親 WHERE id = 値
4 親の無い子データ LEFT JOIN で 親.id IS NULL
5 入れる・消す順番 入れるのは親→子、消すのは子→親
6 FOREIGN_KEY_CHECKS=0 を使ったか 戻したあとに LEFT JOIN で確かめる

よくある質問

Q. 外部キーを外せば解決しますか。 A. エラーは出なくなりますが、親の無い注文のような不整合なデータが入るようになります。外部キーは、データの整合性を DB が守ってくれる仕組みなので、入れる順番や値を直すほうを選びます。

Q. NULL を入れたらどうなりますか。 A. 子の列が NULL を許可していれば、NULL は外部キーのチェックの対象外です(親が無いことを表せます)。NOT NULL の列なら、確認環境では ERROR 1048: Column 'customer_id' cannot be null という、外部キーとは別のエラーになりました。

まとめ

  • 1452 は子に親の無い値、1451 は子が使っている親を消す・変える
  • エラー文の FOREIGN KEY (子の列) REFERENCES 親の表 (親の列) を読み、値が親にあるか確かめる
  • 入れるのは親→子、消すのは子→親
  • 親の無い子データは LEFT JOIN で 親.id IS NULL
  • FOREIGN_KEY_CHECKS=0 で入れた不整合は、戻しても残り、あとで関係のない更新を 1452 で止める
  • 外部キーを作るときは、型・符号・文字コードをそろえる(3780)

参考・出典

確認日はいずれも 2026年10月11日です。

  • MySQL 8.0 Reference Manual「FOREIGN KEY Constraints」:https://dev.mysql.com/doc/refman/8.0/en/create-table-foreign-keys.html

本記事の内容は、ご自由にお使いください。
ご利用の際は、出典として本ページへのリンクを記載いただけますようお願いします。

(記載例)出典:株式会社RJC「MySQL ERROR 1452の直し方|外部キー制約エラー」

株式会社RJC ― SI事業・SES事業・AI駆動開発。RJCは一緒に成長を楽しめる会社です。

WE ARE HIRING

RJCで一緒に開発しながら、
成長を楽しみませんか?

RJCは、Web・モバイル・AIを活用した開発プロジェクトで、テックリードやPM・PMOも活躍するシステム開発会社です。会社を知る、待遇を確かめる、話を聞いてみる。気になるところ見てみてください!

  • 127日年間休日
  • 12時間平均残業時間
  • 毎日ガチャ遊びココロも大切にする福利厚生。アマギフなどの賞品ラインナップ!

ほかにも、チケットレストラン、書籍読み放題、2年ごとの慰労報奨(休暇 or 金一封)、11期連続の黒字決算。

ABOUT RJC RJCがどんな会社か知る 考え方、研修、働き方、福利厚生、社員の前職まで。RJCのことが丸わかり! RJC丸わかりページへ JOB DESCRIPTION 仕事内容・待遇を見てみる 仕事内容、給与・待遇、選考の流れ。経験者も未経験も!応募前に知りたいこと、まとめました! 募集要項を見る ENTRY エントリーする エントリーは1〜2分・履歴書不要です。まずは話を聞いてみたい、という方でも歓迎です! エントリーフォームへ

RJCで一緒に開発しながら、 成長を楽しみませんか?