3. 数据质量维度与Snowflake落地框架
数据质量不是一个单一指标,而是一组可以分别定义、分别度量、分别追责的维度。在 Snowflake 中,这五个维度——完整性、准确性、一致性、及时性、唯一性——并不是抽象口号,它们都能落到具体的表、列、时间戳、主键约束和查询语句上。理解每个维度在 Snowflake 语境下的定义与度量思路,是搭建数据质量监控体系的第一步。
完整性:记录与字段是否缺失
完整性关注的是“该有的数据有没有”。它分为两个层次:行级完整性和列级完整性。行级完整性指业务上应该到达的记录是否全部到达,例如订单表在某个时间窗口内是否覆盖了所有门店;列级完整性指关键字段是否为空,例如 customer_id、order_amount 是否出现 NULL。
在 Snowflake 中,行级完整性通常通过源端与目标端的计数比对来度量。假设源系统某日应产生 12000 条订单,落地到 RAW.ORDERS 后执行:
SELECT COUNT(*) AS row_cnt
FROM RAW.ORDERS
WHERE order_date = '2024-06-01';
-- 示例结果:11840
若预期为 12000,则完整性缺口为 160 条,缺口率约 1.33%。列级完整性则用空值率衡量:
SELECT
SUM(CASE WHEN customer_id IS NULL THEN 1 ELSE 0 END) / COUNT(*) AS null_rate
FROM RAW.ORDERS
WHERE order_date = '2024-06-01';
-- 示例结果:0.021
空值率 2.1% 是否可接受,取决于该字段的业务重要性。主键类字段通常要求 0%,而备注类字段可以放宽。Snowflake 的 INFORMATION_SCHEMA.COLUMNS 可以辅助识别哪些列允许 NULL,从而确定完整性检查的优先级。
准确性:值是否真实反映业务事实
准确性衡量数据值是否与真实世界一致。它比完整性更难度量,因为“真实值”往往不在数据仓库内部。Snowflake 中常见的准确性度量思路有三类:
- 值域校验:检查数值是否落在合理区间,例如
order_amount应大于 0 且小于 100000。 - 格式校验:用正则表达式检查邮箱、手机号、身份证号等字段格式。
- 交叉比对:将 Snowflake 中的聚合结果与源系统或财务系统的对账结果比较。
例如,用 REGEXP_LIKE 检查邮箱格式:
SELECT COUNT(*) AS bad_email_cnt
FROM RAW.CUSTOMERS
WHERE NOT REGEXP_LIKE(email, '^[A-Za-z0-9._%+-]+@[A-Za-z0-9.-]+\\.[A-Za-z]{2,}$');
-- 示例结果:37
准确性度量通常需要业务规则库配合。建议在 Snowflake 中建立一张 DQ.RULES 表,记录每条规则的字段、规则类型、阈值和责任人,使准确性检查可配置、可追溯。
一致性:跨表、跨系统是否对齐
一致性关注同一事实在不同位置是否表达一致。在 Snowflake 中,一致性至少有三个层面:
- 跨表一致性:订单明细汇总金额应等于订单主表金额。
- 跨系统一致性:Snowflake 中的客户数与 CRM 系统客户数一致。
- 编码一致性:同一状态码在不同表中含义相同,例如
status='A'在订单表和退款表中都表示“有效”。
跨表一致性可以用 JOIN 加聚合来度量:
SELECT
o.order_id,
o.total_amount,
SUM(d.amount) AS detail_sum
FROM RAW.ORDERS o
JOIN RAW.ORDER_DETAIL d ON o.order_id = d.order_id
GROUP BY o.order_id, o.total_amount
HAVING ABS(o.total_amount - SUM(d.amount)) > 0.01;
-- 示例结果:返回 12 条不一致记录
编码一致性则可以通过维度表或 DQ.CODE_MAPPING 表来校验,确保所有状态码都能在映射表中找到对应解释。
及时性:数据是否在需要时可用
及时性衡量数据从产生到可用的延迟。在 Snowflake 中,及时性通常用两个时间戳之差来度量:业务发生时间(event_time)和数据落地时间(load_time)。延迟 = load_time - event_time。
SELECT
MAX(DATEDIFF('minute', event_time, load_time)) AS max_lag_min,
AVG(DATEDIFF('minute', event_time, load_time)) AS avg_lag_min
FROM RAW.ORDERS
WHERE load_time >= DATEADD('hour', -1, CURRENT_TIMESTAMP());
-- 示例结果:max_lag_min = 18, avg_lag_min = 6
及时性阈值应根据业务场景设定。实时风控可能要求延迟小于 1 分钟,而日报类数据可以接受 2 小时。Snowflake 的 TASK 和 STREAM 可以用于构建近实时管道,但及时性监控本身应独立于管道,避免“管道成功即认为及时”的误区。
唯一性:是否存在重复记录
唯一性检查主键或业务键是否重复。在 Snowflake 中,虽然可以定义 PRIMARY KEY,但 Snowflake 默认不强制唯一约束,因此唯一性必须通过查询主动验证。
SELECT order_id, COUNT(*) AS cnt
FROM RAW.ORDERS
GROUP BY order_id
HAVING COUNT(*) > 1;
-- 示例结果:返回 5 个重复 order_id
对于复合业务键,可以将多个字段拼接后检查:
SELECT MD5(CONCAT_WS('|', store_id, order_date, order_seq)) AS biz_key,
COUNT(*) AS cnt
FROM RAW.ORDERS
GROUP BY biz_key
HAVING COUNT(*) > 1;
唯一性问题的常见来源包括重复抽取、幂等性缺失和上游重复提交。度量时应同时记录重复记录数和重复率,便于判断影响范围。
五维度在 Snowflake 中的统一落地框架
将五个维度落到 Snowflake 时,建议采用“规则表 + 检查任务 + 结果表”的三层结构。DQ.RULES 存储规则定义,DQ.CHECK_RESULTS 存储每次检查的结果,Snowflake TASK 按调度执行检查。下图展示了五个维度与 Snowflake 对象、度量方式和典型输出之间的对应关系。
这个框架的关键在于:每个维度都有明确的度量 SQL,每条规则都有阈值和责任人,每次检查都有结果记录。Snowflake 的 TASK 负责调度,CHECK_RESULTS 负责留痕,告警和看板负责消费结果。这样,数据质量就从“感觉有问题”变成了“可量化、可追踪、可改进”的工程实践。