Вопрос

Я должен создать базу данных с двумя таблицами в MySQL, но скрипт завершается с ошибкой 150 (проблема с внешним ключом).Я дважды проверил, чтобы поля внешнего ключа были одинаковыми в обеих таблицах, и я не могу найти никакой ошибки.

Вот сценарий:

 SET @OLD_UNIQUE_CHECKS=@@UNIQUE_CHECKS, UNIQUE_CHECKS=0;
 SET @OLD_FOREIGN_KEY_CHECKS=@@FOREIGN_KEY_CHECKS, FOREIGN_KEY_CHECKS=0;
 SET @OLD_SQL_MODE=@@SQL_MODE, SQL_MODE='TRADITIONAL';

 DROP SCHEMA IF EXISTS `testdb`;
 CREATE SCHEMA IF NOT EXISTS `testdb` DEFAULT CHARACTER SET utf8 COLLATE utf8_unicode_ci ;
 USE `testdb`;

 DROP TABLE IF EXISTS `testdb`.`table1` ;

 CREATE  TABLE IF NOT EXISTS `testdb`.`table1` (
   `id` INT UNSIGNED NOT NULL ,
   `field1` VARCHAR(50) NULL ,
   PRIMARY KEY (`id`) )

 ENGINE = InnoDB;


 DROP TABLE IF EXISTS `testdb`.`table2` ;

 CREATE  TABLE IF NOT EXISTS `testdb`.`table2` (
   `id` INT NOT NULL AUTO_INCREMENT ,
   `field1` VARCHAR(50) NULL ,
   `date` DATE NULL ,
   `cnt` INT NULL ,
   PRIMARY KEY (`id`) ,
   INDEX `FK_table2_table1` (`field1` ASC) ,
   CONSTRAINT `FK_table2_table1`
   FOREIGN KEY (`field1`)
   REFERENCES `testdb`.`table1` (`field1` )
   ON DELETE NO ACTION
   ON UPDATE NO ACTION)

 ENGINE = InnoDB;

 SET SQL_MODE=@OLD_SQL_MODE;
 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS;
 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS;

Я пробовал это в Windows и Ubuntu с разными версиями MySQL и не сработало.

Есть какие-нибудь идеи?

Это было полезно?

Решение

table1.field1 на нем не определен индекс.

Требуется разместить FOREIGN KEY ограничение на field1.

С этим:

 CREATE  TABLE IF NOT EXISTS `testdb`.`table1` (
   `id` INT UNSIGNED NOT NULL ,
   `field1` VARCHAR(50) NULL ,
   KEY ix_table1_field1 (field1),
   PRIMARY KEY (`id`) )
 ENGINE = InnoDB;

Затем все должно работать так, как ожидалось.

Другие советы

Работая с MySQL Workbench и MySQL 5.5.27, я столкнулся с аналогичной проблемой.В моем случае проблема была с полями типа INT.Ошибочно в одной таблице это было значение INT БЕЗ знака, а в таблице ссылок это было значение INT.

В зависимости от версии MySQL вам может потребоваться сначала создать индекс в table1.field1.

Один из ответов здесь предлагает отключить проверку целостности внешнего ключа.Это ПЛОХАЯ идея.Здесь есть два вероятных виновника:

  • Несоответствие типа данных между ссылочным первичным ключом и ссылающимся внешним ключом
  • Индексы.Любые внешние ключи, которые вы индексируете, должны быть НЕ НУЛЕВЫМИ

Еще один намек:

Даже когда ваши типы данных кажутся одинаковыми - в моем случае оба столбца имели VARCHAR(50) - этого недостаточно.

Вам также необходимо убедиться, что оба столбца имеют одинаковый COLLATION.

Еще одна причина, хотя и немного похожая на другие:Я имел в виду таблицу, в которой, как оказалось, был движок MyISAM вместо InnoDB.

MySQL также выдаст эту ошибку, если вы неправильно введете имя ссылающейся таблицы.Некоторое время я рвала на себе волосы , пока не поняла , что пропустила букву в foreign key (column1) references mistyped_table(column1)

Одним из вариантов (в зависимости от конкретного случая) было бы отключить проверку целостности MySQL:

SET FOREIGN_KEY_CHECKS = 0;

Если ничего не работает, попробуйте это:

Имя внешнего ключа является дубликатом уже существующего ключа.Убедитесь, что имя вашего внешнего ключа уникально в вашей базе данных.Просто добавьте несколько случайных символов в конец имени вашего ключа, чтобы проверить это.

В моем случае одна таблица использовала ограничения внешнего ключа для другой таблицы, которая еще не существовала.Это происходило из-за большого файла makefile, так что это было не так очевидно, как я ожидал.

На случай, если у кого-то все еще возникают проблемы с этим, я перепробовал все решения выше (за исключением SET FOREIGN_KEY_CHECKS) и ничего не сработало.Проблема заключалась в том, что при обращении к первой таблице некоторые базы данных учитывают регистр имен таблиц.Я думаю, это странно, так как я никогда раньше не видел этого в MySQL, Oracle, а теперь это случилось со мной на MariaDB.

Например:

Создайте таблицу, если не существует CADASTRO_MAQUINAS ( Идентификатор переменной(16), Первичный ключ (Id) );

Создать таблицу, если информация не существует ( Параметр Id_Maquina VARCHAR(16) НЕ равен НУЛЮ, ОГРАНИЧЕНИЕ FK_infos_cadastro_maquinas Внешний ключ (Id_Maquina) ссылается на кадастровый номер (Id) );

Если я попытаюсь создать вторую таблицу, используя cadastro_maquinas (строчные буквы) вместо CADASTRO_MAQUINAS, я получу эту ошибку.

Я использовал MySQL workBench.Проблема в том, что вы не можете использовать один и тот же foreign key name, они должны быть unique.Таким образом, если более чем одна таблица будет ссылаться на один и тот же внешний ключ, каждый раз должен быть unique дано имя.

У меня была аналогичная ошибка в одной из моих таблиц.При установке флажка параметры сортировки столбцов отличались, что сработало после того, как оба столбца были переведены на один и тот же тип сортировки.

После прочтения большей части предлагаемого здесь решения.Я просто подумал, что было бы полезно, если бы я просто перечислил все возможности, которые могли бы вызвать эту ошибку.

1, Проверьте РЕГИСТР столбца 2, Проверьте сопоставление столбцов 3, Проверьте, существует ли ключ, созданный в обеих таблицах для столбца (уникальный, первичный)

В моем случае я получил старое определение таблицы MyISAM в одной из таблиц, и, очевидно, я не смог создать для нее внешний ключ из другой таблицы.Может быть, это кому-то поможет.

Таким образом, это может произойти из-за несоответствий между двумя определениями баз данных / полей, попробуйте проверить:

Field Type
Field Collation
Table Engine

Для меня проблема заключалась в использовании CONSTRAINT в CREATE TABLE запрос.

Вы также можете столкнуться с той же ошибкой при попытке сослаться на составной ключ в вашем внешнем ключе.

Например:

CREATE TABLE `article` (
  `id` int(10) unsigned NOT NULL,
  `type` enum('X','Y','Z') NOT NULL,
  PRIMARY KEY (`id`,`type`)
) ENGINE InnoDB;

CREATE TABLE `t1` (
  `user_id` int(10) unsigned NOT NULL,
  `type` enum('X','Y','Z') NOT NULL,
  `article_id` int(10) unsigned NOT NULL,
  CONSTRAINT `user_access_article_ibfk_2` FOREIGN KEY (`article_id`, `type`) REFERENCES `article` (`id`, `type`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB

В этом случае важно использовать article_id и поле type в определении FK в том же порядке, в каком они отображаются в определении ПЕРВИЧНОГО КЛЮЧА таблицы article.

В моем случае, вероятно, это была ошибка сервера, из-за которой была удалена таблица с тем же именем.Удаление всей shcema и ее повторное создание решило проблему.

В очень странных случаях ваша база данных может быть повреждена.В моем случае у меня не было никаких внешних ключей в таблице, и помогло только переименование таблицы или смена движка.

Оказалось, InnoDB был сломан, видите: https://dba.stackexchange.com/questions/86853/1025-error-on-rename-of-table-errno-150-table-was-deleted-while-tried-to-a?lq=1

Если вы работаете с mysql workbench и получаете эту ошибку для таблицы отношений, возможно, для вас найдется быстрое решение:просто удалите его, и пусть mysql workbench воссоздаст его для вас.Затем скопируйте sql.Исправлена моя проблема с errno 150.

Я получил эту ошибку при попытке использовать внешний ключ для ссылки на неуникальное поле.(который по - видимому не допускается)

Когда у меня возникла эта проблема, это было из-за того, что я установил идентификатор в первой таблице равным unsigned принимая во внимание, что внешнего ключа во второй таблице не было.Делая их обоих unsigned починил это для меня.

Всегда сначала создавайте главные / родительские таблицы, а затем создавайте свои подробные / дочерние таблицы.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top