Mysql
 sql >> база данни >  >> RDS >> Mysql

MySQL Създаване на таблици с външни ключове, даващи errno:150

Имах същия проблем с ALTER TABLE ADD FOREIGN KEY .

След един час установих, че тези условия трябва да бъдат изпълнени, за да не се получи грешка 150:

  1. Родителската таблица трябва да съществува, преди да дефинирате външен ключ, за да я препратите. Трябва да дефинирате таблиците в правилния ред:първо родителска таблица, след това дъщерна таблица. Ако и двете таблици се позовават една на друга, трябва да създадете една таблица без FK ограничения, след това да създадете втората таблица, след което да добавите FK ограничението към първата таблица с ALTER TABLE .

  2. И двете таблици трябва да поддържат ограничения на външния ключ, т.е. ENGINE=InnoDB . Други механизми за съхранение безшумно игнорират дефинициите на външни ключове, така че не връщат грешка или предупреждение, но FK ограничението не се запазва.

  3. Референтните колони в родителската таблица трябва да са най-лявата колона на ключ. Най-добре е ключът в родителския елемент да е PRIMARY KEY или UNIQUE KEY .

  4. Дефиницията на FK трябва да препраща към колоната(ите) на PK в същия ред като дефиницията на PK. Например, ако FK REFERENCES Parent(a,b,c) тогава PK на родителя не трябва да се дефинира в колони в ред (a,c,b) .

  5. PK колоната(ите) в родителската таблица трябва да бъде от същия тип данни като колоната(ите) на FK в дъщерната таблица. Например, ако PK колона в родителската таблица е UNSIGNED , не забравяйте да дефинирате UNSIGNED за съответната колона в полето Child table.

    Изключение:дължината на низовете може да е различна. Например, VARCHAR(10) може да се позовава на VARCHAR(20) или обратно.

  6. Всяка колона(и) на FK от низов тип трябва да има същия набор от знаци и съпоставяне като съответната(ите) PK колона(и).

  7. Ако вече има данни в дъщерната таблица, всяка стойност в колоната(ите) на FK трябва да съответства на стойност в колоната(ите) на родителската таблица PK. Проверете това със заявка като:

    SELECT COUNT(*) FROM Child LEFT OUTER JOIN Parent ON Child.FK = Parent.PK 
    WHERE Parent.PK IS NULL;
    

    Това трябва да върне нула (0) несъвпадащи стойности. Очевидно тази заявка е общ пример; трябва да замените имената на вашите таблици и колони.

  8. Нито таблицата Родител, нито таблицата Дъще могат да бъдат TEMPORARY таблица.

  9. Нито таблицата Родител, нито таблицата Дъще могат да бъдат PARTITIONED таблица.

  10. Ако декларирате FK с ON DELETE SET NULL опция, тогава колоната(ите) на FK трябва да бъде нула.

  11. Ако декларирате име на ограничение за външен ключ, името на ограничението трябва да бъде уникално в цялата схема, а не само в таблицата, в която е дефинирано ограничението. Две таблици може да нямат собствено ограничение със същото име.

  12. Ако има други FK в други таблици, сочещи към същото поле, за което се опитвате да създадете новия FK, и те са неправилно оформени (т.е. различно съпоставяне), те първо трябва да бъдат съгласувани. Това може да е резултат от минали промени, където SET FOREIGN_KEY_CHECKS = 0; е използвано с непоследователна връзка, дефинирана по погрешка. Вижте отговора на @andrewdot по-долу за инструкции как да идентифицирате тези проблемни FK.

Надявам се това да помогне.



  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Оптимизиране на MySQL търсене с използване на харесвания и заместващи знаци

  2. Как да изчислим дневните активни потребители (DAU) в MySQL

  3. Как да вмъкнете данни от една таблица на база данни в друга таблица на база данни в Mysql

  4. Автоматизиране на внедряване на база данни на MySQL

  5. 15 полезни съвета за настройка и оптимизация на MySQL/MariaDB