繁体   English   中英

事实表分区:如何处理ETL中的更新?

[英]Fact table partitioning: how to handle updates in ETL?

我们正在尝试为包含大约400M行的数据仓库事实表实现表分区。 我们的ETL从前一个加载中向后50天(源行系统时间戳的新行,修改行)从源系统获取数据。 因此,在每个ETL循环中都会有新行,以及更新Fact表中相应行的旧行。 我们的想法是在Fact表中插入新行并更新修改后的行。

分区列是date(int,YYYYMMDD),我们正在考虑按月分区。

就我而言,表分区可以通过快速分区切换操作简化我们的插入。 我们可以拆分最近的分区以创建新的空闲分区,将新行加载到临时表(使用日期约束,例如最近一个月),然后使用分区切换操作将新行“移动”到分区的事实表中。 但是我们如何处理应该更新Fact表中相应行的修改行? 这些行可以包含上个月的数据。 分区切换有帮助吗? 通常INSERTUPDATE行由ETL工具(例如我们的SSIS)或MERGE语句确定。 分区在这种情况下如何工作?

我再看一下设计,试着弄清楚是否有更新的方法。 以下是更新事实表的一些含义:

性能:更新是完全记录的事务。 大事实表也有大量的数据可供读写。

多维数据集:更新事实表需要重新处理受影响的分区。 随着事实表的不断增长,立方体处理时间也将继续增加。

预算:快速存储是昂贵的。 更新大事实表将需要大量快速读写。

纯粹理论:除非初始值是错误(即用户输入15,000美元而不是1,500美元),否则不应更改事实表。 任何非错误情况都将改变最初记录的事务。

有什么变化? 变化的部分真的是维度的属性吗? 如果是这样,是否可以将它们移动到维度并使用“缓慢变化的维度”类型任务处理更改?

另一种可能性,这可以通过抵消交易来实现吗? 例:

最初的InvoiceAmount是10.00美元。 会计后来增加了1.25美元的税收,然后向客户收取11.25美元的费用。 而不是将值更新为$ 11.25,插入1.25美元的记录。 发票的总金额仍然是11.25美元,您可以执行最少日志记录的插入而不是完全记录的更新来完成。

不仅在理论上更新事实表是一个坏主意,它随着事实表的增长而变得非常昂贵且不可扩展。 您将阅读和编写更多数据,从存储子系统中需要更多IOPS。 当您准备好进行分析时,立方体处理会引发更多问题。

您还必须经常证明管理层为什么需要为数据仓库提供如此多的IOPS。 是否有商业价值/理由需要所有这些IOPS用于不断变化的“事实”表?

如果您无法找到事实表上的更新方法,那么至少要建立一个以只读方式确定数据的截止点。 否则,你永远无法扩展。

切换在这里没有帮助。

也许您可以在不同的行范围内使用多个线程同时执行更新。 这可能会加速它。 注意不要触发锁升级,以便获得良好的并发性。

还要确保主要按聚簇索引的升序排序更新行。 这有助于磁盘IO(这种技术可能不适用于多线程)。

更新事实记录的原因有很多,因为事实中存在非标识属性。 除非您计划“先删除”然后“插入”,否则您无法避免更新。 您不能简单地说“将度量标准增量记录为新事实”。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM