【问题标题】:MySQL Errno 150MySQL 错误 150
【发布时间】:2013-04-20 01:58:43
【问题描述】:

我正在创建一些简单的表,但我无法通过这个外键错误,我不知道为什么。这是下面的脚本。

create TABLE Instructors (

ID varchar(10),
First_Name varchar(50) NOT NULL,
Last_Name varchar(50) NOT NULL,
PRIMARY KEY (ID)
);

create table Courses (

Course_Code varchar(10),
Title varchar(50) NOT NULL,
PRIMARY KEY (Course_Code)

);


create table Sections (
Index_No int,
Course_Code varchar(10),
Instructor_ID varchar(10),
PRIMARY KEY (Index_No),
FOREIGN KEY (Course_Code) REFERENCES Courses(Course_Code)
    ON DELETE cascade
    ON UPDATE cascade,
FOREIGN KEY (Instructor_ID) REFERENCES Instructors(ID)
    ON DELETE set default

);

错误代码:1005。无法创建表 '336_project.sections' (errno: 150)

我的数据类型似乎相同,语法似乎正确。谁能指出我在这里看不到的东西?

我正在使用 MySQL Workbench 5.2

【问题讨论】:

    标签: mysql foreign-keys mysql-workbench


    【解决方案1】:

    如果您关联不同类型的列,例如,也会发生此错误。源表中的 int 和目标表中的 BigInt。

    【讨论】:

    • 或者引用的表没有InnoDB引擎
    • 这是我的问题。我正在使用 Laravel,我的父列是“增量”列。我不得不将参考列更改为 unsignedInteger。
    【解决方案2】:

    如果您使用 InnoDB 引擎,ON DELETE SET DEFAULT 是您的问题。以下是手册的摘录:

    虽然 MySQL 服务器允许 SET DEFAULT,但 InnoDB 将其拒绝为无效。 InnoDB 表不允许使用此子句的 CREATE TABLE 和 ALTER TABLE 语句。

    您可以使用ON DELETE CASCADEON DELETE SET NULL,但不能使用ON DELETE SET DEFAULT。还有更多信息here

    【讨论】:

    • 您好,感谢您的快速回复。我尝试更改为 SET NULL ,但它仍然不起作用。我什至删除了所有 ON UPDATE/DELETE 行,但仍然给我错误。我应该指定要使用的特定引擎吗?
    • 忽略最后一条评论,我已修复。你是对的,我不得不将默认值更改为 null,而且我还为每个外键引用创建了索引。一旦我这样做了,它就起作用了!
    • @Sixers17 - 你知道,当我在这里尝试你的CREATE TABLE 语句时,我唯一需要做的就是将它们更改为ON DELETE SET NULL。我不必添加索引。也就是说,无论如何最好在你的 FK 上都有索引,所以一切都很好:)
    • 嗯,有趣,我想知道为什么我的没有索引就不能工作。
    • 我注意到您也不能将列设置为NOT NULL。发现将 ON DELETE RESTRICT 列迁移到 ON DELETE SET NULL 列。
    【解决方案3】:

    你可以跑

    SHOW ENGINE INNODB STATUS
    

    以人类可读的格式读取失败的原因

    例如

    ------------------------
    LATEST FOREIGN KEY ERROR
    ------------------------
    150331 15:51:01 Error in foreign key constraint of table foobar/#sql-413_81:
    FOREIGN KEY (`user_id`) REFERENCES `foobar`.`users`(`id`) ON DELETE SET NULL ON UPDATE CASCADE:
    You have defined a SET NULL condition though some of the columns are defined as NOT NULL.
    

    【讨论】:

    • 这是宝藏!这也有助于诊断其他问题。
    【解决方案4】:

    为了创建引用另一个表的FOREIGN KEY,两个表中的键应该是PRIMARY KEY,并且具有相同的数据类型。

    在您的表部分中,PRIMARY KEY 具有不同的数据类型,即 INT,但在另一个表中,它的类型是 VARCHAR

    【讨论】:

      【解决方案5】:

      如果您根本没有指定 ON DELETE 而是尝试从 InnoDB 表中引用 MISAM 表,也可能是这种情况:

      CREATE TABLE `table1`(
          `id` INT UNSIGNED NOT NULL,
          `name` VARCHAR(255) NOT NULL,
          PRIMARY KEY (`id`)
      ) ENGINE=MYISAM CHARACTER SET UTF8;
      
      CREATE TABLE `table2`(
          `id` INT UNSIGNED NOT NULL AUTO_INCREMENT,
          `table1_id` INT UNSIGNED NOT NULL,
          `some_value` VARCHAR(255) NOT NULL,
      
      
          PRIMARY KEY (`id`),
          KEY `fk_table1_id`(`table1_id`),
      
          CONSTRAINT FOREIGN KEY (`table1_id`) REFERENCES `table1`(`id`)
      ) ENGINE=INNODB CHARACTER SET UTF8;
      

      上面会抛出errno 150。还需要将第一个表更改为 InnoDB 才能正常工作。

      【讨论】:

        【解决方案6】:

        失败了

        ON DELETE set default 
        

        我以前没有遇到过,我也没有在手册中看到它(但是已经很晚了)

        更新

        刚刚在manual看到这个

        虽然 MySQL 服务器允许 SET DEFAULT,但它被拒绝为 InnoDB 无效。使用此 CREATE TABLE 和 ALTER TABLE 语句 InnoDB 表不允许使用子句。

        我猜你可能正在使用 InnoDB 表?

        【讨论】:

        • 我应该把 Engine=InnoDB 放在表声明之后吗?
        【解决方案7】:

        为了完整起见 - 如果您对当时未定义的表进行外部引用,您也会收到此错误;

        【讨论】:

          【解决方案8】:

          这里的问题出在数据库引擎中(table1 MYISAM 和 table2 ENGINE)。 要设置 FOREIGN KEY,

          • 两个表必须使用相同的 ENGINE 和相同的字符集。
          • 父列中的 PK 列和 FK 列的数据类型和排序规则类型必须相同。

          希望你有一个想法。

          【讨论】:

            【解决方案9】:

            确保表类型是 InnoDB,MyISAM 不支持外键,afaik。

            【讨论】:

              猜你喜欢
              • 2010-10-23
              • 2018-04-14
              • 1970-01-01
              • 1970-01-01
              • 1970-01-01
              • 2012-07-21
              • 2012-06-22
              相关资源
              最近更新 更多