3

一个用户是一个人,一个人有一个公司-用户->人是一对一的,人->公司是多对一的。

person_id 是 USER 表中的 FK。company_id 是 PERSON 表中的 FK。

PERSON 可能不是 USER,但 USER 始终是 PERSON。

如果 company_id 在 user 表中,我可以根据用户名和 company_id 创建一个唯一键,但它不是,如果是,它将是数据的重复。

目前,我正在 RoseDB 管理器包装代码中实现唯一用户名/公司 ID 规则,但感觉不对。如果可以的话,我想在数据库级别定义唯一规则,但我不确定如何处理它。我试过这样的事情:

alter table user add unique(used_id,person.company_id);

但这不起作用。

通过阅读文档,我找不到任何类似的示例。我是在尝试添加不存在的功能,还是在这里遗漏了什么?

4

3 回答 3

1

好吧,没有什么简单的东西可以满足您的需求。不过,您可能可以使用BEFORE INSERTBEFORE UPDATE triggers强制执行您需要的约束。有关如何处理使触发器失败的问题,请参阅有关引发 MySQL 错误的 SO 问题。

于 2009-09-20T21:55:42.013 回答
1

您可以UNIQUE在表中定义约束Person

CREATE TABLE Company (
 company_id SERIAL PRIMARY KEY
) ENGINE=InnoDB;

CREATE TABLE Person (
 person_id SERIAL PRIMARY KEY,
 company_id BIGINT UNSIGNED,
 UNIQUE KEY (person_id, company_id),
 FOREIGN KEY (company_id) REFERENCES Company (company_id)
) ENGINE=InnoDB;

CREATE TABLE User (
 person_id BIGINT UNSIGNED PRIMARY KEY,
 FOREIGN KEY (person_id) REFERENCES Person (person_id)
) ENGINE=InnoDB;

但实际上即使在表中也不需要唯一约束Person,因为person_id它本身就已经是唯一的。给定的person_id人不可能引用两家公司。

所以我不确定你要解决什么问题。


回复您的评论:

这并不能解决允许相同用户名存在于不同公司的问题。

因此,您希望给定的用户名在一家公司中是唯一的,但在不同的公司中可用?从你原来的问题中我不清楚。

因此,如果您没有许多其他特定于用户的属性,我会将 User 与 Person 结合起来并添加一个“ is_user”列。或者只是依赖于隐含地认为具有非空 cryptpass 的人是根据定义的用户。

然后你的跨表UNIQUE约束问题就消失了。

于 2009-09-20T22:54:47.060 回答
1

你的PERSON桌子有更多的属性吗?我问的原因是你想要实现的是一个典型的推论表:

USERS桌子:

  • user_id (pk)

USER_COMPANY_XREF(nee PERSON) 表:

  • user_id (pk, fk)
  • company_id (pk, fk)
  • EFFECTIVE_DATE(非空)
  • EXPIRY_DATE(非空)

COMPANIES桌子:

  • company_id (pk)

表的主键USER_COMPANY_XREF是一个复合键,USERS.user_id允许COMPANIES.company_id您将用户与多个公司相关联,同时不复制USERS表中的数据,并提供参考完整性。

于 2009-09-20T22:55:05.980 回答