我们正在Snowflake数据库中使用Data Vault方法实施新的数据存储。我们的目的是尽可能坚持最新的标准和最佳实践,例如仅插入方法,并尝试避免各种反模式,例如在可行的情况下驱动键关系(有关驱动键的讨论,请参阅此处的评论(。
以下是我们数据中与一段时间内分配给酒店的评级相关的部分数据的简化示例(例如酒店星级或类似评级(。
其中心是将属性连接到评级的表。以下示例显示了单个属性针对两个不同方案的评级历史记录。
PropertyRatingID PropertyID RatingSchemeID RatingID EffectiveDate
1 1 1 1 2020-01-01
2 1 1 2 2020-01-02
3 1 1 1 2020-01-03
4 1 2 3 2020-01-02
5 1 2 4 2020-01-03
有关数据结构的相关信息。
- PropertyRatingID是确保唯一性的身份密钥,没有商业意义。
- 在任何给定时间,一个物业只能对一个方案有一个评级,但可以在多个方案下评级
- 物业ID,评级计划ID和生效日期不需要是 独特的组合。
- ValidDate 不表示将记录输入到系统中的日期,并且可以按相当长的持续时间回溯到过去,从而在生效日期和应用更改的日期之间形成双时间情况。
- PropertyID、RatingSchemeID 和 RatingID 都是提供描述性数据的其他表的外键。在我们的模型中,属性已经作为一个独立的中心存在。
上述时间线如下图所示。
Date Scheme1Rating Scheme2Rating
2020-01-01 1 NULL
2020-01-02 2 3
2020-01-03 1 4
2020-01-04 1 4
我最初尝试对此进行建模是为RatingID构建一个中心,一个属性和评级之间的链接,以及一个连接到链接的卫星,使用PropertyRatingID保存所有其他信息(主要是BrandID和EffectiveDate(,使其具有多活动性。事实证明,这很难使用,因为背后的驱动键会发生变化(PropertyID和BrandID分布在链路和卫星之间(。
就情况的偶然性而言,重点将放在获取最近记录的一组生效日期(即最新的系统日期(上,以创建一段时间内的评级历史记录,例如 ValidEndDate 等同于原始表上的LEAD(EffectiveDate) OVER(PARTITION BY PropertyID,RatingID ORDER BY EffectiveDate ASC)
。虽然我们不会定期使用过去系统时代的值记录,但我们有时会临时查看这些记录,以解释报告期之间历史记录的变化。
一个简单的解决方案是跨源系统中的多个表联接,以平展数据,将其分开,并根据评级计划生成附属数据,并将其直接附加到属性中心。这将为我们提供一个短期解决方案,但将是不灵活的(任何新的评级方案都需要一个新的集线器(,并且仍然要求这些卫星是多活的,以保持源系统中当前的多个有效日期。
我相信理想的解决方案至少需要一个与驱动键相关的集线器,并且可能需要第二个与属性评级分配相关的集线器。我的大部分阅读(见上一个链接和这篇文章(暗示我的卫星应该连接到集线器而不是链接。
使用数据保管库方法对此进行建模的有效方法是什么?
我对讨论所提出的解决方案的回报感兴趣,例如额外的"弱"集线器与解决更复杂的查询中的驱动关键问题。
据我了解,这种情况更像是一个带有 PropertyID 的 LINK/SAT,RatingSchemeID 作为 LINK 自然键(链接到 Property 和 RatingScheme HUB(和 SAT 中的 RatingID(挂在链接上(。