0

我有单独的资产表用于存储不同类型的物理和逻辑资产,例如:-

  1. 车辆表(ID、型号、EngineSize、Drivername、lastMaintenanceDate)
  2. 服务器表(ID、IP、OSName 等...)
  3. 虚拟机(ID、大小等)。
  4. VM_IP (VM_ID,IP)

现在我遇到的问题是:-

  1. 对于 server 表和 VM_IP 表中的 IP 列,我需要此列在这两个表中是唯一的,因此例如数据库不应允许服务器和 VM 具有相同的 IP。在当前的设计中,我只能单独保证表的唯一性。那么任何人都可以就我如何在数据库级别处理这个独特的要求提出建议。

问候

::编辑::

我目前有以下数据库结构:-

在此处输入图像描述

目前我看到以下几点: -

  1. 我在基础 Asset 表中引入了多余的 AssetTypeID 列,这样我就可以知道资产类型而无需连接表。这可能会破坏规范化。

  2. 在我的上述架构中,我无法控制(在数据库级别)哪些资产应该有 IP,哪些资产不应该有 IP,以及哪些资产可以/不能有多个 IP。那么有没有办法改进我的架构来处理这两点。

提前感谢您的帮助。

4

4 回答 4

2

创建 IP 表并使用外键

于 2013-06-27T09:30:52.143 回答
1

如果我在设计层面遇到问题,我会再添加两个表:

  1. 一个valid_IP表(包含有效的 IP 范围)
  2. A Network_Enabeled,可能具有 IP 的所有实体的基表,例如 Server 表、VM_IP ……此基表的主键将是子表的主键。

在 Network_Enabeled 表中,拥有来自 valid_IP 表的外键并在字段上设置唯一键将是答案。
希望有所帮助。

于 2013-06-27T09:45:21.393 回答
0

You can use an indexed view.

CREATE VIEW YourViewName with SCHEMABINDING
as
    ...
GO

CREATE UNIQUE CLUSTERED INDEX IX_YourIndexName
    on YourViewName  (..., ...)
于 2013-06-27T09:11:00.200 回答
0

根据您的编辑,您可以在资产表上引入一个超级键并使用各种约束来强制执行您正在寻找的大部分内容:

create table Asset (
    AssetID int not null primary key,
    AssetTypeID int not null
    --Skip all of the rest, foreign keys, etc, irrelevant to example
    ,constraint UQ_Asset_TypeCheck
        UNIQUE (AssetID,AssetTypeID) --This is the superkey
)

以上意味着该AssetTypeID列现在可以在其他表中检查/强制执行,并且不存在不一致的风险

create table Servers (
    AssetID int not null primary key,
    AssetTypeID as 1 persisted,
    constraint FK_Servers_Assets FOREIGN KEY (AssetID)
        references Asset (AssetID), --Strictly, this will become redundant
    constraint FK_Servers_Assets_TypeCheck FOREIGN KEY (AssetID,AssetTypeID)
        references Asset (AssetID,AssetTypeID)
)

因此,在上面,我们强制此表中的所有条目实际上必须是正确的资产类型,方法是使其成为一个固定的计算列,然后在外键中使用返回到超键。

--So on for other asset types
create table Asset_IP (
    AssetID int not null,
    IPAddress int not null primary key, --Wrong type, for IPv6
    AssetTypeID int not null,
    constraint FK_Asset_IP_Assets FOREIGN KEY (AssetID)
        references Asset (AssetID), --Again, redundant
    constraint CK_Asset_Types CHECK (
        AssetTypeID in (1/*,  Other types allowed IPs */)),
    constraint FK_Asset_IP_Assets_TypeCheck FOREIGN KEY (AssetID,AssetTypeID)
        references Asset (AssetID,AssetTypeID)
)

现在,在上面,我们再次引用超级键以确保我们有一个本地(此表)正确的AssetTypeID值,然后我们可以在检查约束中使用它来限制哪些资产类型实际上是该表中允许的条目。

create unique index UQ_Asset_SingleIPs on Asset_IP (AssetID)
   where AssetTypeID in (1/* Type IDs that are only allowed 1 IP address */)

最后,对于某些AssetTypeID值,我们确保该表仅包含一行AssetID

我希望这能给您足够的想法,让您了解如何根据类型实现各种检查。如果您愿意/需要,您现在可以构建一些视图(其余代码将通过这些视图进行交互),这些视图隐藏了额外的列并提供触发器来简化INSERT语句。

在旁注中,我建议在表命名时选择一个约定并坚持它。我的首选是使用复数/集体名称,除非该表仅打算包含一行。所以我会重命名AssetAssets,例如,或Asset_IP作为Asset_IPs。目前,你有一个混合物。

于 2013-06-28T08:28:33.210 回答