开发者社区 问答 正文

MySQL创建带有外键给errno的表:150

我正在尝试使用两个外键在MySQL中创建一个表,这些外键引用了其他2个表中的主键,但出现了errno:150错误,它不会创建该表。

这是所有3个表的SQL:

CREATE TABLE role_groups ( role_group_id int(11) NOT NULL AUTO_INCREMENT, name varchar(20), description varchar(200), PRIMARY KEY (role_group_id) ) ENGINE=InnoDB;

CREATE TABLE IF NOT EXISTS roles ( role_id int(11) NOT NULL AUTO_INCREMENT, name varchar(50), description varchar(200), PRIMARY KEY (role_id) ) ENGINE=InnoDB;

create table role_map ( role_map_id int not null auto_increment, role_id int not null, role_group_id int not null, primary key(role_map_id), foreign key(role_id) references roles(role_id), foreign key(role_group_id) references role_groups(role_group_id) ) engine=InnoDB; 任何帮助将不胜感激。

展开
收起
保持可爱mmm 2020-05-08 10:59:48 581 分享 版权
1 条回答
写回答
取消 提交回答
  • 我也有同样的问题ALTER TABLE ADD FOREIGN KEY。

    一个小时后,我发现必须满足以下条件才能不出现错误150:

    父表必须存在,然后才能定义外键以引用它。您必须以正确的顺序定义表:首先是父表,然后是子表。如果两个表相互引用,则必须创建一个没有FK约束的表,然后创建第二个表,然后使用将该FK约束添加到第一个表ALTER TABLE。

    这两个表都必须支持外键约束,即ENGINE=InnoDB。其他存储引擎静默忽略外键定义,因此它们不返回任何错误或警告,但不会保存FK约束。

    父表中被引用的列必须是键的最左列。如果“父项”中的键为PRIMARY KEY或,则为最佳UNIQUE KEY。

    FK定义必须以与PK定义相同的顺序引用PK列。例如,如果为FK,REFERENCES Parent(a,b,c)则不得在order列上定义父级的PK (a,c,b)。

    父表中的PK列必须与子表中的FK列具有相同的数据类型。例如,如果父表中的PK列为UNSIGNED,请确保UNSIGNED在子表字段中为相应的列定义。

    例外:字符串的长度可能不同。例如,VARCHAR(10)可以引用VARCHAR(20),反之亦然。

    任何字符串类型的FK列都必须具有与相应PK列相同的字符集和排序规则。

    如果子表中已经有数据,则FK列中的每个值都必须与父表PK列中的值匹配。使用以下查询来检查此内容:

    SELECT COUNT(*) FROM Child LEFT OUTER JOIN Parent ON Child.FK = Parent.PK WHERE Parent.PK IS NULL; 这必须返回零(0)个不匹配的值。显然,该查询是一个通用示例。您必须替换表名和列名。

    父表和子表都不能是TEMPORARY表。

    父表和子表都不能是PARTITIONED表。

    如果使用ON DELETE SET NULL选项声明FK ,则FK列必须为空。

    如果为外键声明约束名称,则约束名称在整个架构中必须唯一,而不仅在定义该约束的表中是唯一的。两个表可能没有相同名称的约束。

    如果其他表中的其他FK指向您要为其创建新FK的相同字段,并且它们的格式不正确(即不同的排序规则),则需要首先使其一致。这可能是由于过去的更改而导致的,这种更改SET FOREIGN_KEY_CHECKS = 0;是由于错误定义的不一致关系而被使用的。有关如何识别这些问题FK的说明,请参见下面的@andrewdotn的答案。

    希望这可以帮助。来源:stack overflow

    2020-05-08 11:00:09
    赞同 展开评论