Snowpipe 故障排除

本主题介绍一种有条不紊的方法,用于解决在使用 Snowpipe 加载数据时出现的问题。

本主题内容:

Snowpipe 问题的解决步骤会有所不同,具体取决于在加载数据文件时使用的工作流。

使用云存储事件通知来自动加载数据

错误通知

为 Snowpipe 配置错误通知。当 Snowpipe 在加载过程中遇到错误时,该功能会将通知推送到配置的云消息传递服务,从而启用数据文件分析。有关更多信息,请参阅 Snowpipe 错误通知

常规故障排除步骤

完成以下步骤,确定阻止文件自动加载的大多数问题的原因。

第 1 步:检查管道状态

检索管道的当前状态。结果以 JSON 格式显示。有关信息,请参阅 SYSTEM$PIPE_STATUS

查看以下值:

lastReceivedMessageTimestamp

指定从消息队列接收的最后一条事件消息的时间戳。请注意,此消息可能不适用于特定管道,例如,如果与消息关联的路径与管道定义中的路径不匹配。此外,自动引入管道仅使用由创建的数据对象触发的消息。

如果时间戳早于预期,则可能表示服务配置(即 Amazon SQS 或 Amazon SNS 或 Azure 事件网格)或服务本身存在问题。如果该字段为空,请验证服务配置设置。如果字段包含时间戳,但早于预期,请验证服务配置中是否更改了设置。

lastForwardedMessageTimestamp

指定最后一条“创建对象”事件消息的时间戳,其中包含转发到管道的匹配路径。

如果事件消息从消息队列接收到,但未转发到管道,则用于创建新数据文件的 Blob 存储路径与 Snowflake 暂存区和管道定义中指定的组合路径可能不匹配。验证暂存区和管道定义中指定的路径。请注意,管道定义中指定的路径会追加到暂存区定义中的路径。

第 2 步:查看表的 COPY 历史记录

如果接收并转发事件消息,则查询目标表的加载活动历史记录。有关信息,请参阅 COPY_HISTORY

STATUS 列指明一组特定文件是已加载、部分加载还是加载失败。FIRST_ERROR_MESSAGE 列提供尝试部分加载或加载失败的原因。

请注意,如果一组文件存在多个问题,则 FIRST_ERROR_MESSAGE 列仅指明遇到的第一个错误。要查看文件中的所有错误,请执行 COPY INTO <table> 语句,将 VALIDATION_MODE 复制选项设置为 RETURN_ALL_ERRORS。VALIDATION_MODE 复制选项指示 COPY 语句验证要加载的数据并根据指定的验证选项返回结果。指定此复制选项时,不会加载任何数据。在语句中,引用您尝试使用 Snowpipe 加载的一组文件。有关复制选项的更多信息,请参阅 COPY INTO <table>

如果 COPY_HISTORY 输出不包含一组预期文件,请查询更早的时间段。如果文件是早期文件的副本,则在尝试加载原始文件时,加载历史记录可能已记录该活动。

第 3 步:验证数据文件

如果加载操作在数据文件中遇到错误,COPY_HISTORY 表函数会描述每个文件中遇到的第一个错误。要验证数据文件,请查询 VALIDATE_PIPE_LOAD 函数。

未加载 Microsoft Azure Data Lake Storage Gen2 存储中生成的文件

目前,有些第三方客户端不会调用 ADLS Gen 2 REST API 中的 FlushWithClose。要触发用于通知 Snowpipe 加载文件的事件,此步骤不不可少。尝试手动调用 REST API 以触发 Snowpipe 加载这些文件。

有关采用 close 实参的 Flush 方法的更多信息,请参阅 https://docs.microsoft.com/en-us/dotnet/api/azure.storage.files.datalake.datalakefileclient.flush (https://docs.microsoft.com/en-us/dotnet/api/azure.storage.files.datalake.datalakefileclient.flush)。有关 close 参数加载的其他 REST API 引用信息,请参阅 https://docs.microsoft.com/en-us/rest/api/storageservices/datalakestoragegen2/path/update (https://docs.microsoft.com/en-us/rest/api/storageservices/datalakestoragegen2/path/update)。

在删除 Amazon SNS 主题订阅后 Snowpipe 停止加载

用户首次创建会引用特定 Amazon Simple Notification Service (SNS) 主题的管道对象时,Snowflake 会为主题订阅 Snowflake 拥有的 Amazon Simple Queue Service (SQS) 队列。如果 AWS 管理员删除 SNS 主题的 SQS 订阅,则引用该主题的所有管道都不再接收来自 Amazon S3 的事件消息。

要解决此问题,请执行以下步骤:

  1. 从删除 SNS 主题订阅开始等待 72 小时。

    72 小时后,Amazon SNS 会清除已删除的订阅。有关更多信息,请参阅 Amazon SNS 文档 (https://aws.amazon.com/premiumsupport/knowledge-center/sns-cross-account-subscription/)。

  2. 重新创建引用该主题的管道(使用 CREATE REPLACE OR PIPE)。在管道定义中引用相同的 SNS 主题。有关信息,请参阅 第 3 步:创建已启用自动引入的管道

在删除 SNS 主题订阅之前工作的所有管道现在都应再次开始接收来自 S3 的事件消息。

要规避 72 小时延迟,您可以创建具有不同名称的 SNS 主题。使用 CREATE OR REPLACE PIPE 命令重新创建引用该主题的管道,并指定新的主题名称。

源自 Google Cloud Storage 的加载延迟或文件丢失

当配置为使用 Pub/Sub 消息从 Google Cloud Storage (GCS) 自动加载数据时,仅读取单个暂存文件的事件消息。或者,源自 GCS 的数据加载可能会延迟几分钟到一天或更长时间。通常,当 GCS 管理员未向 Snowflake 服务账户授予 Monitoring Viewer 角色时,会导致任一问题。

有关信息,请参阅 配置对 Cloud Storage 的安全访问 中的“第 2 步:授予 Snowflake 对 Pub/Sub 订阅的访问权限”。

调用 Snowpipe REST 端点以加载数据

错误通知

针对 Snowpipe 错误通知的支持适用于 Amazon Web Services (AWS) 上托管的 Snowflake 账户。数据加载期间遇到的错误会触发通知,从而启用数据文件分析。有关更多信息,请参阅 Snowpipe 错误通知

常规故障排除步骤

完成以下步骤,确定阻止文件加载的大多数问题的原因。

第 1 步:检查身份验证问题

Snowpipe REST 端点使用带 JSON Web 令牌 (JWT) 的密钥对身份验证。

Python/Java 引入 SDKs 会为您生成 JWT。直接调用 REST API 时,您需要生成它们。如果请求中未提供 JWT 令牌,则 REST 端点会返回错误 400。如果提供的令牌无效,则返回类似于以下内容的错误:

snowflake.ingest.error.IngestResponseError: Http Error: 401, Vender Code: 390144, Message: JWT token is invalid.
Copy

第 2 步:查看表的 COPY 历史记录

查询表的加载活动历史记录,包括使用 Snowpipe 尝试加载的数据。有关信息,请参阅 COPY_HISTORYSTATUS 列指明一组特定文件是已加载、部分加载还是加载失败。FIRST_ERROR_MESSAGE 列提供尝试部分加载或加载失败的原因。

请注意,如果一组文件存在多个问题,则 FIRST_ERROR_MESSAGE 列仅指明遇到的第一个错误。要查看文件中的所有错误,请执行 COPY INTO <table> 语句,将 VALIDATION_MODE 复制选项设置为 RETURN_ALL_ERRORS。VALIDATION_MODE 复制选项指示 COPY 语句验证要加载的数据并根据指定的验证选项返回结果。指定此复制选项时,不会加载任何数据。在语句中,引用您尝试使用 Snowpipe 加载的一组文件。有关复制选项的更多信息,请参阅 COPY INTO <table>

第 3 步:检查管道状态

如果 COPY_HISTORY 表函数为正在调查的数据加载返回 0 个结果,则检索管道的当前状态。结果以 JSON 格式显示。有关信息,请参阅 SYSTEM$PIPE_STATUS

executionState 键标识管道的执行状态。例如,PAUSED 指明管道当前已暂停。管道所有者可以使用 ALTER PIPE 恢复管道运行。

如果 executionState 值指明启动管道时出现问题,请检查 error 键以获取更多信息。

第 4 步:验证数据文件

如果加载操作在数据文件中遇到错误,COPY_HISTORY 表函数会描述每个文件中遇到的第一个错误。要验证数据文件,请查询 VALIDATE_PIPE_LOAD 函数。

其他问题

未加载的文件集

缺少加载的 COPY_HISTORY 记录

检查管道中的 COPY INTO <table> 语句是否包含 PATTERN 子句。如果包含,请验证指定为 PATTERN 值的正则表达式是否正在筛选所有要加载的暂存文件。

要修改 PATTERN 值,必须使用 CREATE OR REPLACE PIPE 语法重新创建管道。

有关更多信息,请参阅 CREATE PIPE

COPY_HISTORY 记录指明已卸载的文件子集

如果 COPY_HISTORY 函数输出指明未加载文件子集,则可以尝试“刷新”管道。

在以下任何一种情况下,都可能出现这种情况:

  • 外部暂存区以前用于使用 COPY INTO table 命令批量加载数据。

  • REST API:

    • 外部事件驱动功能用于调用 REST APIs,并且在配置事件之前,外部暂存区中已存在数据文件的积压任务。

  • 自动引入:

    • 在配置事件通知之前,外部暂存区中已存在数据文件的积压任务。

    • 事件通知失败导致一组文件无法排队。

要使用配置的管道在外部暂存区加载数据文件,请执行 ALTER PIPE ...REFRESH 语句。

目标表中的重复数据

通过执行 SHOW PIPES 或查询账户使用情况中的 PIPES 视图或 Information Schema 中的 PIPES 视图,比较账户中所有管道定义中的 COPY INTO <table> 语句。如果多个管道在 COPY INTO <table> statements, verify that the directory paths do not overlap. Otherwise, multiple pipes could load the same set of data files into the target tables. For example, this situation can occur when multiple pipe definitions reference the same storage location with different levels of granularity, such as <storage_location>/path1/ and <storage_location>/path1/path2/. In this example, if files are staged in <storage_location>/path1/path2/ 中引用相同的云存储位置,则两个管道都会加载文件的副本。

无法重新加载已修改的数据,无意加载已修改的数据

Snowflake 使用文件加载元数据来阻止重新加载表中的相同文件(和复制数据)。Snowpipe 阻止加载具有相同名称的文件,即使这些文件后来已修改(即具有不同的 eTag)。

文件加载元数据与 管道对象 (而不是表)相关。因此:

  • 忽略与已加载的文件同名的暂存文件,即使这些文件已修改,例如,如果添加了新行或更正了文件中的错误。

  • 使用 TRUNCATE TABLE 命令截断表 不会 删除加载元数据的 Snowpipe 文件。

但是,请注意,管道仅将加载历史记录元数据保留 14 天。因此:

文件在 14 天内修改并再次暂存:

Snowpipe 会忽略再次暂存的已修改文件。要重新加载已修改的数据文件,当前需要使用 CREATE OR REPLACE PIPE 语法重新创建管道对象。

以下示例基于 使用 Snowpipe REST API 做好加载数据的准备 中第 1 步的示例重新创建 mypipe 管道:

create or replace pipe mypipe as copy into mytable from @mystage;
Copy
文件在 14 天后修改并再次暂存:

Snowpipe 会再次加载数据,这可能会导致目标表中出现重复的记录。

此外,如果执行 COPY INTO <table> 语句,引用与活动 Snowpipe 加载相同的桶/容器、路径和目标表,则可能会将重复记录加载到目标表。COPY 命令和 Snowpipe 的加载历史记录在 Snowflake 中分开存储。在加载任何历史暂存数据后,如果您需要使用管道配置来手动加载数据,请执行ALTER PIPE ...REFRESH 语句。有关更多信息,请参阅本主题中的 未加载的文件集

使用 CURRENT_TIMESTAMP 插入的加载时间早于 COPY_HISTORY 视图中的 LOAD_TIME 值

表设计者可以添加一个时间戳列,该列在记录加载到表中时插入当前时间戳作为默认值。目的是获取将每条记录加载到表中的时间;但是,时间戳早于 COPY_HISTORY 函数 (Information Schema) 或 COPY_HISTORY 视图 (Account Usage) 返回的 LOAD_TIME 列值。原因是,CURRENT_TIMESTAMP 在云服务中编译加载操作时,而不是在将记录插入表中时(即提交加载操作的事务时)进行评估。

备注

我们目前不建议在 Snowpipe 的 copy_statement 中使用以下函数:

  • CURRENT_DATE

  • CURRENT_TIME

  • CURRENT_TIMESTAMP

  • GETDATE

  • LOCALTIME

  • LOCALTIMESTAMP

  • SYSDATE

  • SYSTIMESTAMP

一个已知的问题是,使用这些函数插入的时间值可能比 COPY_HISTORY 函数COPY_HISTORY 视图 返回的 LOAD_TIME 值早几个小时。

使用复制选项 INCLUDE_METADATAMETADATA$START_SCAN_TIME 相反,它提供了更准确的记录加载表示。有关更多信息,请参阅 CREATE PIPE 例子

错误:找不到与暂存区 {1} 关联的集成 {0}

003139=SQL compilation error:\nIntegration ''{0}'' associated with the stage ''{1}'' cannot be found.
Copy

当外部暂存区与链接到该暂存区的存储集成之间的关联中断时,可能会发生此错误。当(使用 CREATE OR REPLACE STORAGE INTEGRATION)重新创建存储集成对象时,会发生这种情况。暂存区使用隐藏 ID(而不是存储集成的名称)链接到存储集成。在后台,CREATE OR REPLACE 语法会删除对象,并使用其他隐藏 ID 重新创建对象。

如果将存储集成链接到一个或多个暂存区后,必须重新创建该存储集成,则必须通过执行 ALTER STAGE stage_name SET STORAGE_INTEGRATION = storage_integration_name 来重新建立每个暂存区与存储集成之间的关联,其中:

  • stage_name 是暂存区的名称。

  • storage_integration_name 是存储集成的名称。

Snowpipe 引用政府区域的错误

如果 Snowpipe 引用政府区域中的桶,同时账户位于商业区域,您可能会收到错误。 请注意,云提供商的政府区域不允许向其他商业区域发送事件通知或从其他商业区域发送事件通知。有关更多信息,请参阅 AWS GovCloud (US) (https://docs.aws.amazon.com/govcloud-us/latest/UserGuide/govcloud-s3.html) 和 Azure Government (https://learn.microsoft.com/en-us/azure/azure-government/)。

语言: 中文