外键是mysql中的主键

时间:2012-02-23 08:43:50

标签: mysql sql insert foreign-keys

我有两个依赖表

CREATE TABLE posts
(
post_id int(11) unsigned NOT NULL AUTO_INCREMENT,
title varchar(255),
PRIMARY KEY(post_id)
) ENGINE=InnoDB

CREATE TABLE post_meta
(
post_id int(11) unsigned REFERENCES posts(post_id) ON DELETE CASCADE,
info varchar(255),
PRIMARY KEY(post_id)
) ENGINE=InnoDB

问题1:INSERT进入posts后,post_meta不接受错误Duplicate entry XX for key 'PRIMARY的值。我该如何修改表结构?

问题2:如何设置在post_metaINSERT INTO posts中创建相应的行?我的意思是在post_meta中创建一行时,在posts中创建一个空行(仅具有FK的id)。换句话说,在第二列中没有任何INSERT的两列中具有相同的行数。

1 个答案:

答案 0 :(得分:3)

您当前的实现看起来不像标准化形式。您确定需要将数据分成两个不同的表吗?也许

CREATE TABLE posts
(
post_id int(11) unsigned NOT NULL AUTO_INCREMENT,
title varchar(255),
info varchar(255),
PRIMARY KEY(post_id)
) ENGINE=InnoDB

会吗?

推测:如果你因为安全问题而这样做,那么MySQL supports Column-level privileges

如果由于某些原因使数据规范化是不可接受的,那么你可以在两个表中创建post_id主键(不要使它成为外键!)并在表posts上添加INSERT和DELETE触发器这将插入或删除post_meta中的相应行。

<强>更新

您在评论中说,您可以在post_meta表格中拥有与posts中的单个记录相对应的多条记录。这会改变很多

  1. 您不得在表post_id的{​​{1}}上使用主键。主键必须在表范围内是唯一的。
  2. 您可以设置外键(您已经尝试过的那个) - 这将确保使用帖子自动删除元数据。
  3. 如果确实需要在post_meta上定义PRIMARY KEY,那么您应该向post_meta表添加一个新的(可能是auto_increment字段)并将其用作主键。 (此外,即使没有主键,表也可以存在,但它违反了大多数数据库指南)
  4. 如果您需要为每个帖子自动创建元记录,那么您可以在我已经建议的post_meta上添加INSERT触发器。另一种方法是使用存储过程(仅存储过程)将记录添加到posts - 在此SP中,您可以编写一些SQL以将必要的记录插入posts