如何在多个表中强制使用唯一身份验证

Sun*_*nov 5 mysql sql database database-design data-modeling

我在MySQL服务器中有以下表:

Companies:
- UID (unique)
- NAME
- other relevant data

Offices:
- UID (unique)
- CompanyID
- ExternalID
- other data

Employees:
- UID (unique)
- OfficeID
- ExternalID
- other data
Run Code Online (Sandbox Code Playgroud)

在每一个中,UID是由数据库创建的唯一标识符.

有外键可以确保UID上Employee - > Office - > Company之间的链接.

办公室和员工中的ExternalID字段是公司(我的客户实际)提供给我的应用程序的ID.客户端没有(也不关心)我自己的ID,我的应用程序从它们收到的所有数据都是根据它们的ID(即我的表中的ExternalID)来识别的.

即客户端使用伪语言的请求就像"我是公司X,更新我的员工Y的数据".

我需要对CompanyID和Employees.ExternalID的组合强制执行唯一性,因此在我的数据库中,同一公司的员工不会有重复的ExternalID.

我在考虑3种可能的解决方案:

  1. 更改Employees的架构以包含CompanyID,并在两个字段上创建唯一约束.

  2. 强制执行触发器,在Employees中更新/插入时验证唯一性.

  3. 强制检查应用程序级别(即我的接收服务).

我的替代方案 - dbadmin-in-me sais(3)是最糟糕的解决方案,因为它不会在应用程序错误或其他情况下保护数据库不一致,并且很可能是最慢的.

触发器解决方案可能是我想要的,但它可能会变得复杂,特别是如果需要在单个语句中执行多个插入/更新,并且我不确定性能与(1).

并且(1)看起来是最快速和最简单的方法,但有点违背我对关系模型的理解.

SO DB专家对每种方法的利弊有何看法,特别是如果有可能增加额外的间接水平 - 即公司 - >办公室 - >部门 - >员工,同样的独特性需要保留(公司职员).

OMG*_*ies 3

你是对的 - #1 是最好的选择。
诚然,乍一看我会质疑它(因为走捷径),但了解业务规则以确保员工只与一家公司相关 - 这是有道理的。

此外,我还有一个外键将员工表中的公司 ID 与办公室表中的公司 ID 相关联。否则,您允许员工与没有办公室的公司有关联。除非这是可以接受的...

如果无法在数据模型中演示关系,则触发器是最后的手段,并且从应用程序提供逻辑服务意味着逻辑是集中的 - 没有机会出现不良数据,除非有人放弃约束(这意味着您会遇到更大的问题) )。