跳至主要内容

深入解读 Snowflake 动态表:现代数据管道

了解 Snowflake 动态表如何通过由 Snowflake 托管的自动刷新,简化复杂且对时间敏感的 ETL 流程。
· 15分钟 阅读

使用 AI 探索

Snowflake 的动态表(Dynamic Tables)是数据工程师管道工具箱中的强大工具。它们本质上是基于底层表执行转换查询并生成新表的自动化刷新流程。 

动态表简化了对数据新鲜度要求高且需要复杂 SQL 转换的数据编排管道。它们使用基于延迟(lag)的时序机制,根据基础表的变化来刷新目标表。

近期的增强进一步提升了其能力,实现了近实时的数据传播,并与 Snowflake 生态系统更深度集成(可通过这门入门课程回顾)。 

本指南将介绍动态表的工作原理、如何有效实施,以及如何监控与优化性能。读完后,您将能够评估并测试这些实现是否契合您组织的数据需求。

什么是 Snowflake 动态表?

动态表是 Snowflake 提供的全托管数据库对象类型,用于简化和自动化数据管道。 

与其使用外部编排工具或尝试将手动刷新与源表更新对齐,不如让动态表根据源数据的变化和设定的新鲜度目标自动更新。这使数据从业者能够构建灵活的转换,并在数据变化时按需更新。

与视图不同,视图在查询时才计算结果;动态表保持已计算状态,从而提高查询速度。同样,虽然物化视图也提供缓存数据,但动态表可以使用连接(join)、并集(union)和嵌套视图等能力,这是物化视图所不支持的。

动态表最初被引入是为弥合传统ELT 管道与事件驱动架构之间的差距,代表了 Snowflake 在声明式、具备依赖意识的数据处理方面的持续投入。 

您只需编写定义动态表的 SQL SELECT 查询,并设定 TARGET_LAG 以决定刷新频率。 

例如,TARGET_LAG 为 5 分钟意味着动态表相较于基础表的滞后不超过 5 分钟。更妙的是,所有这一切由 Snowflake 的内部刷新引擎管理,无需我们自行设计复杂的管道!

理解 Snowflake 动态表

为有效实施动态表,我们将深入了解 Snowflake 的底层技术实现,从而把握其优劣势。

基础架构与运行机制

与物化视图类似,动态表提供持久且自动化的数据刷新行为。但不同于物化视图的是,它们支持更复杂的转换,如并集和连接。 

这使我们可以创建多个较小的动态表,再将其汇聚到更大的动态表中。

一个关键创新是 Snowflake 使用自动依赖图。您可以创建在基础表更新时自动更新的聚合动态表,或者使用有向无环图(DAG)构建多层动态表。这通过更新基础暂存表来工作,进而触发下游动态表更新。 

一旦这些中间动态表完成更新,最终的聚合动态表也会更新。整个过程由 Snowflake 的刷新工作器监测数据更新,确保源表按最新数据进行刷新。

image describign two workflows, one which shows a aggregate dynamic table using only base tables and the other using intermediate dynamic tables to build one larger dynamic table

摘自 Snowflake 动态表创建文档

刷新机制详解

创建动态表时,您可控的主要机制包括刷新模式、延迟以及仓库参数。动态表支持两种刷新模式:

  • 增量模式:Snowflake 分析自上次刷新以来的变化,并将其合并到表中
  • 全量模式:每次刷新都重新计算整张表并完全替换

您可以手动指定刷新模式,或在初次创建动态表时使用 REFRESH_MODE = AUTO。需注意,使用 AUTO 时,该模式在创建时确定,之后不会更新。如果 Snowflake 判定增量刷新低效,将改用全量刷新。

WAREHOUSE 设置决定用于计算资源的虚拟仓库。请根据您的计算与存储需求选择合适的仓库。

或许最重要的概念是延迟。最常见的设定方式是使用 TARGET_LAG,即定义源数据与动态表之间可接受的延迟。如果您在较复杂的管道中工作,且其他动态表依赖当前动态表,则可以设置 TARGET_LAG = DOWNSTREAM。 

将 TARGET_LAG 设为 DOWNSTREAM 后,系统会参考依赖当前动态表的下游动态表的时序来确定刷新。

动态表与传统表、视图、物化视图的差异总结

来源概念

动态表继承的特性

动态表的改进点

传统表

持久化存储;可复用的下游依赖

自动维护与刷新;无需手动数据加载或触发器

视图

声明式 SQL 逻辑;无需过程式代码

结果物化以提升性能;通过 TARGET_LAG 管理新鲜度

物化视图

自动刷新;状态管理

支持复杂转换;跨阶段的依赖跟踪集成

依赖管理

每个动态表都会组成 DAG,便于 Snowflake 在多张表之间协调刷新。这在多阶段管道中可确保正确性与效率。

Snowsight 提供用于探索 DAG 的可视化界面,展示依赖关系、刷新时间和延迟指标。这对调试与影响分析极具优势。有关 Snowflake 架构如何运作的更多信息,请阅读这篇Snowflake 数据管道文章。

关键特性与对比优势

下面来看看动态表的一些其他关键特性及其优势。 

相较传统架构的优势

动态表在 Snowflake 内原生处理依赖跟踪和刷新逻辑,从而不再需要外部编排(如 Airflow 或 dbt Cloud)。

这带来多方面优势,包括:

  • 编排更简化:无需 cron 任务或手写刷新逻辑。
  • 内置变更数据捕获(CDC)支持:原生支持增量处理。
  • 统一监控:在 Snowsight 中可查看刷新状态、延迟与血缘关系。
  • 查询重写支持:Snowflake 可利用动态表的血缘来优化查询。

这些特性让动态表在需要最新或近实时数据的场景中表现出色,例如实时看板与 CDC 工作流。此外,您可以将多个动态表串联,完成多阶段转换。

实时数据处理与变更数据捕获(CDC)

动态表不再用 CRON 任务定义手动刷新时间线,而是依靠 TARGET_LAG 与源表对齐。对于流式实时数据表,这意味着一旦动态表超过设定的滞后,就会自动更新。

虽然它们很相似,但动态表常被作为流(Streams)和物化视图的替代方案。若您需要数据始终最新,且仅在单一基础表上应用简单逻辑,物化视图非常适合。 

Streams 适用于手动实现 CDC 并理解数据随时间的变化。当您希望用一种简单方式,为复杂的转换查询实施定期更新时,动态表则是理想之选。

关于在 Snowflake 中如何组织数据的更多考量,这门Snowflake 数据建模课程是极好的资源。

实施 Snowflake 动态表

下面通过语法范式与最佳实践演示如何配置动态表。上手并不难,但深入理解各参数有助于发挥其最大效用。

实施框架与语法

以下是以 raw_sales 为基础表创建动态表的示例代码。先浏览一下,我们随后进行拆解。

# Your Dynamic Table parameters
CREATE OR REPLACE Dynamic Table sales_agg
  TARGET_LAG = '5 minutes'
  WAREHOUSE = 'prod_wh'
  REFRESH_MODE = auto
  INITIALIZE = on_create
  AS

# Your SQL query for the table itself
SELECT
  store_id,
  SUM(amount) AS total_sales,
  COUNT(*) AS sale_count
FROM raw_sales
GROUP BY store_id;

后半部分很直观:这是定义表数据的 SELECT 语句。SELECT 之前的是创建参数: 

  • TARGET_LAG:如上所述,用于指定新鲜度要求。可设定具体时间范围,或在被其他动态表消费时写为 “DOWNSTREAM”。
  • WAREHOUSE:决定计算资源。请选择合适的 Snowflake 仓库,以性价比地生成表。
  • REFRESH_MODE:可显式设为 INCREMENTAL 或 FULL。此处选 AUTO 交由 Snowflake 判定最优方式。
  • INITIALIZE:决定初始化时机。ON_CREATE 表示创建即初始化;ON_SCHEDULE 则在达到第一个延迟周期时初始化。

请注意,Snowflake 要求开启变更跟踪以正确支持增量刷新,这会在增量动态表上自动启用! 

若需手动检查,可使用 ALTER TABLE 命令。开启变更跟踪还允许时间旅行(time travel),以便在需要时恢复历史版本。

CLONE 与 ICEBERG

动态表的两个细节在于克隆(cloning)以及将其连接到 Snowflake Iceberg 表(基于外部Apache Iceberg 表构建)。 

对于 Iceberg 表,配置时并无变化。基于 Snowflake Iceberg 表构建动态表的主要好处是:可持续处理外部数据,而无需持续摄取或复制数据。

借助 Snowflake 的时间旅行,我们可以使用 CLONE 命令复制动态表的旧版本,如下:

CREATE Dynamic Table clone_sales_agg
CLONE sales_agg
AT (OFFSET => -24*60*60) –-24 hours ago
TARGET_LAG = DOWNSTREAM
WAREHOUSE = sales_wh

需要注意的是,克隆表可能不会保留源表的全部元数据,并会占用额外存储空间。请谨慎克隆,确保确有必要。

示例数据搭建

建议动手练习搭建动态表以测试其功能。以下是测试动态表的一般步骤:

  • 创建带时间戳的简单 raw_sales 表。
  • 定期插入新行。
  • 使用 TARGET_LAG = '1 minute' 观察刷新行为。

您可以创建一个监测 S3 存储桶的流,并定期上传数据。随着数据变化,观察动态表如何更新。可参考本教程以简单方式设置Snowflake 数据摄取,并参考这篇教程了解在 Snowflake 中创建表的更多信息。

监控与管理动态表

Snowflake 提供多种工具帮助您有效监控与管理动态表,例如使用 Snowsight 或 SQL 查询。请确保您的账户具备相应的监控权限!

监控方法与工具

使用 Snowsight 监控动态表很简单:

  • 进入 Data 并选择 Databases
  • 选择包含您动态表的数据库与架构(schema)
  • 选择Dynamic Tables 选项卡
  • 这里会列出可选的表,您可以点击查看详细信息。

Snowsight 可提供丰富信息,如动态表的创建信息、DAG、刷新历史与指标。

使用 SQL 实现相同功能时,可用 SHOW DYNAMIC TABLES 命令。 

例如,如需查看所有与销售相关的动态表:

SHOW Dynamic Tables LIKE ‘sales_%' IN SCHEMA mydb.myschema;

这会返回表的创建时间、大小、目标延迟及最新状态等信息。

管理与修改动态表

您可能会需要修改或暂停动态表。Snowflake 提供了简便方式。

暂停表可使用 ALTER DYNAMIC TABLE 与 SUSPEND:

ALTER Dynamic Table sales_agg SUSPEND;

稍后恢复同理,使用 RESUME:

ALTER Dynamic Table sales_agg RESUME;

要修改参数,也可使用 ALTER DYNAMIC TABLE 并通过 SET 设置具体参数:

ALTER Dynamic Table sales_agg SET TARGET_LAG = '10 minutes';

管理依赖并尽量减少运行中断的最佳方式,是确保不要暂停关键表。若计划调整延迟,请了解这将如何影响下游表的时序。 

应对运行约束

动态表非常有用,但仍存在一些限制与注意事项。

架构约束与局限

在账户与来源类型方面存在一些限制。目前包括:

  • 每个账户最多 50,000 个动态表(截至 2025 年年中)。
  • 并非所有 Snowflake 对象类型都可作为来源(如 streams)
  • 动态表查询不会记录在 ACCESS_HISTORY 审计视图中

其他需要考虑的包括克隆、时间旅行和访问控制。时间旅行较为简单,其最小值为 1 天,无法将 DATA_RETENTION_TIME_IN_DAYS 设为 0 来关闭时间旅行。 

克隆动态表时,请注意并非所有元数据都会被保留;同时,Iceberg 动态表无法被克隆。若克隆依赖于某个 Iceberg 动态表的动态表,该 Iceberg 动态表不会被迁移到新位置。

创建和使用动态表需要在父数据库与架构上具备 CREATE DYNAMIC TABLE、SELECT 和 USAGE 权限。 

牢记这些约束,将有助于您更顺利地使用动态表!

性能优化技巧

由于实现方式简单,系统很容易被过载。一个常见错误是把动态表当作实时数据管道使用。动态表并非用来取代实时数据源;我们应综合考虑时序与数据时效性需求。例如,遵循以下最佳实践:

  • 尽量使用 REFRESH_MODE = incremental,避免每次加载都重建整张动态表
  • 调优 TARGET_LAG,在成本与数据新鲜度之间取得平衡。
  • 选择合适规模的 WAREHOUSE,优化计算资源使用
  • 将大型转换拆分为更小的分阶段表。
  • 编写高效 SQL,避免大量连接与深层嵌套的 SELECT。

遵循这些建议可让动态表稳定运行。合理使用能以较低成本显著简化关键数据管道,而滥用则可能埋下后患!

定价与成本考量

如前所述,使用动态表会产生存储与计算成本。我们将介绍如何理解并在 Snowflake 中管理这些成本的策略。

成本构成

动态表的成本主要来自两方面:存储与计算。每部分又包含若干子项,下面分别说明。

动态表的存储成本

在存储方面,您需为每个动态表的物化结果付费。时间旅行、故障保护存储与克隆等也会产生额外费用。 

一个例外是动态 Iceberg 表,其数据存储在外部,因此不产生 Snowflake 存储费用。您可以通过尽量精简动态表,或减少克隆与时间旅行来控制成本。

动态表的计算成本

计算成本主要由两部分构成:虚拟仓库与云服务(Cloud Services)计算。虚拟仓库用于初始化与刷新表,类似运行查询所产生的成本。 

云服务计算更多与 Snowflake 提供的自动化相关,包括识别底层对象的变化、维护 DAG 等。可将其理解为 Snowflake 为保持动态表运转所做的后台工作。 

这取决于您定义的表延迟,成本与该频率直接相关。

全面了解这些成本的组合方式,请参阅Snowflake 成本文档,其中有详细拆解。

成本监控与节省

Snowflake 通过 Snowsight 让这些成本的监控变得容易。照常前往 Monitoring 下的 Dynamic Tables,在动态表页面的 Refresh History 选项卡即可查看仓库用量(credits)。

如果想查看账户的整体使用情况,也可以运行以下查询:

SELECT * FROM SNOWFLAKE.ACCOUNT_USAGE.METERING_HISTORY;

这会输出账户在不同服务上的费用,可与动态表关联分析。 

此外,建议先在独立仓库中测试,以充分了解该动态表的仓库成本;熟悉成本后再迁移到共享仓库。

若要节省成本,可考虑使用自动暂停。被暂停的动态表仅收取存储费用,不产生刷新相关费用。 

您还可以使用临时(transient)动态表以免除故障保护存储成本。此外,将 TARGET_LAG 优化到合适频率,并尽可能采用增量刷新,也能显著节省计算成本。 

一如既往,编写高质量 SQL 与优化转换逻辑,也是降低计算资源使用的有效方法。

Snowflake 动态表的使用场景

凡是希望用基于延迟且自管理的简化管道,替代复杂易碎、基于时间触发重载的 ETL 管道的地方,都可用动态表。

企业级部署模式

以下是一些可能适合您所在行业的部署用例。

对于金融类组织,定期刷新交易数据(例如欺诈检测或拒付)可能很有用。 

在无需秒级实时的前提下,我们可以为系统健康看板设定 10 分钟的 TARGET_LAG。也许您有一个数据科学模型将所有欺诈警报写入一张表,第三方拒付监测系统写入另一张表。 

无需复杂的 Airflow DAG,就能将两者简单聚合到一张汇总表中,从而简化并提升查询性能。

在零售分析中,我们可能关注不同区域的表现。各区域或许有各自的中心库并定期推送数据,但不同步。与其为每个数据库定制 ETL 刷新时序,不如构建一个动态表,基于各表的滞后来按需聚合。这能降低管道复杂度并减少持续维护。

其他场景还包括:

  • 实时行为分析:汇总实时客户行为,概览新兴趋势
  • CDC 工作流:为业务变更维持近实时数据,跟踪运营问题
  • 数据金库建模:数据到达即增量写入,作为数据摄取的唯一来源

结语

Snowflake 动态表是简化复杂、基于时间触发的 ETL 管道的利器。它在自动化、灵活性与性能之间实现了优雅平衡。请牢记一些最佳实践,例如先在非关键管道上测试以理解刷新行为、监控延迟与成本指标、并通过可视化 DAG 理解依赖关系。

动态表并非在所有场景下都能完全替代 Streams 与 Tasks,但它为减少代码量、提升效率提供了强健的新选择。合理使用,能大幅提升工作效率。想了解更多 Snowflake 信息与 SQL 回顾,请查看以下资源:

Snowflake 动态表常见问题

什么是 Snowflake 动态表?它与视图或物化视图有何不同?

动态表是由 Snowflake 全面托管的对象,会对 SQL 查询结果进行物化并自动保持更新。与按需计算结果的视图不同,也区别于转换能力受限的物化视图,动态表支持复杂逻辑、增量刷新与编排化依赖。

Snowflake 如何决定何时刷新动态表?

刷新由 TARGET_LAG 参数决定,该参数指定源数据变化与动态表更新之间允许的最大延迟。Snowflake 会使用分配的虚拟仓库,自动触发刷新以满足该延迟要求。

我可以用动态表替代管道中的 Streams 和 Tasks 吗?

很多情况下可以。动态表提供更简单的配置与内置的刷新调度,非常适合多数 CDC 与转换型管道。但若需要高度自定义、事件驱动或过程式逻辑,Streams 与 Tasks 可能更合适。

如果动态表的底层数据频繁变化,会发生什么?

Snowflake 会通过安排更频繁的刷新来满足 TARGET_LAG。如果底层数据变化频率超过刷新能力,您可能会看到计算成本上升,或实际延迟超过目标值。

动态表最适合哪些真实世界的使用场景?

动态表在以下场景表现出色:

  • 具备严格新鲜度 SLA 的实时仪表盘。
  • 用以替代 Streams 与 Tasks 的简化 CDC 管道。
  • 零售、金融、物联网等场景下的多阶段 ELT 管道。
  • Data Vault 2.0 建模与中间转换层。
Tim Lu

作者

Tim Lu

我是一名数据科学家,擅长空间分析、机器学习和数据管道。曾使用过 GCP、Hadoop、Hive、Snowflake、Airflow 等数据科学/工程相关流程与工具。

主题