存储未知数量的相似但独特的实体的最佳关系数据库设计是什么

What is the optimal relational database design for storing an unknown number of similar but unique entities

我们正在设计的数据库允许 用户 向多个第 3 方 服务 进行身份验证,主要是社交媒体(twitter、facebook 等) .将会有数量未知且数量不断增加的此类服务。每个 服务 都需要一组唯一的身份验证数据,这与其他 服务.

不标准

一个 用户可以验证许多 服务,但他们只能使用 服务 的每种类型 之一进行身份验证。

可能的解决方案:

A​​) 这个问题最直接的解决方案是简单地为每个服务添加一个包含 user table 的列,其中包含 JSON 身份验证为那个服务。但是,这会在数据库中留下大量空值,从而违反规范化。例如,当有 50 个这样的集成时会发生什么?

B) 每个服务在数据库中都有自己的 table。 JSON 不再需要,因为可以正确描述每个字段。然后需要为每个服务查找 table "user_has_service"。这是一个 table,它只包含两个外键,一个用于用户,一个用于服务,将它们链接在一起。这个选项似乎是最正确的,但效率很低,并且会进行许多操作来确定用户拥有哪些服务,并且随着服务数量的增加而增加。我也相信在这种情况下,查找 table 的 ID 字段需要是 userservice[=39= 的某种哈希值] 在一起,这样就不可能重复插入。

根本不是数据库专家,我已经研究这个问题很长时间了。有什么想法吗?

您可以设置:

  • 一个名为 services 的引用 table 列出了所有可用的服务,其中包含 service_id(主键)、service_namedescriptions 等等。每项服务在 table.

  • 中表示为一条记录
  • a table 调用了 services_properties 来存储服务的属性;这个 table 有 3 列:service_idservices 的主键的外键)、property_nameproperty_value。可以在 service_id/propery_value 元组上设置唯一约束以避免重复。每个服务在services_propertiestable中都有几条记录。这种灵活的结构让您可以根据需要为每个服务存储尽可能多的不同属性,而无需为每个服务创建新的 table

  • 映射 table 称为 user_services,将用户与服务相关联。列将是 service_iduser_id,作为 services table 和 users table 的主键的外键。您可以查询这个table,轻松列出每个用户订阅的服务。

A) The most direct solution ... JSON

你是对的,选项A是严重错误的。它打破了 Codds 的第一范式,因此它不是关系型的。数据库中的 NULL 表示规范化不完整,这会导致复杂的 SQL 代码。不惜一切代价避免。

similar but unique

需要说明的是,它们是服务所独有的。 {LoginName; UserName; Email; UserId; etc} 都是相似的,这仅在实现意义上是正确的,而不是在数据中。

I may need to sketch this out.

这是个好主意。视觉数据模型要有效得多,因为 (a) 大脑比文本更容易理解它,并且 (b) 因此可以计算出细节;矛盾;丢失的位;等等。视觉上比文本更容易进行每次迭代。

其次,我们自 1987 年(1984 年为封闭组)以来就拥有可视化建模工具,并于 1993 年成为标准。希望您能欣赏符合标准的工具模型优于本土或公司提供的模型。它显示所有技术细节而不是一小部分。

Is there a name for this strategy

它是普通的旧关系数据建模,其中包括规范化(确保符合 Codd 的范式,而不是实施 NF 的疯狂是零散的渐进步骤)。

障碍物

需要理解和消除的一个问题是这个。 "theoreticians" 在 "relational" 的旗帜下推销和传播 1960 年代的记录归档系统。每个文件中都有一个 Record IDs 。该方法确保数据库保持物理状态,而不是逻辑状态,这正是 Codd 用他的关系模型克服的问题:一个逻辑数据库,因此对于任何查询方来说都非常容易导航,是最新的;计划;或计划外。

1960年代的RFS与post-1970关系数据库的本质区别是:

  • 而 RFS 通过物理指针 (Record ID) 维护文件之间的引用,而关系数据库通过逻辑键维护表之间的引用。
  • 根据 Codd,逻辑键是 "made up from the data"
    • (系统伪造的数据不是"made up from the data")
    • (使用 SQL 命令 PRIMARY KEY 不会神奇地为数据添加关系键的属性和质量:如果你使用 PRIMARY KEY RecordID 你就处于 1960 年代的物理范式中, 不是 post-1970 关系范式)
  • Logical Keys 提供 Relational Integrity(与 Referential Integrity 不同,Referential Integrity 是 SQL 的普通功能),远优于 1960 年代的 RFS 获得的
  • 以及更出色的速度和力量(远低于 JOINs 和更小的组数)

关系数据库

因此,根据 Codd,我将以关系数据模型的形式给您答案。

  • 只是关系完整性的一个例子:

    • UserServiceProperty 中的 ServiceProperty FK 元素被限制为 ServiceProperty 中的 PK(特定组合)
    • 具有 Facebook.Email 的 UserServiceProperty 行被阻止
    • 基于 Record ID 的 1960 年代的 RFS,"theoreticians" 推广为 "relational" 不能做到这一点,允许出现诸如那个的各种错误。
  • 我所有的数据模型都在 IDEF1X 中呈现,这是自 1993 年以来的关系数据库建模标准

  • 我的IDEF1X Introduction是初学者必读的

  • IDEF1X Anatomy给逝去的人一个温习

  • 如果您无法直接从数据模型读取 谓词,请告诉我,我会生成它们以文本形式显示。

有问题欢迎提问,越具体越好