本节摘要:调度回答「什么时候跑、按什么顺序跑」,监控回答「跑得怎么样、出事谁先知道」。本节比较三种调度宿主的取舍,讲清数据调度与上游到货的衔接(先验货再开工),最后建立一套四维监控:任务成败、时长趋势、数据新鲜度、行数波动。监控的目标不是多,是把「该叫人的时刻」定义清楚。
新手段常见的心智误区是把调度理解成「每天定时执行命令」。定时只是表象,生产环境的真实问题是:定时到了,上游数据到了吗? 3.2 节的源新鲜度检查在这里兑现它的岗位价值——调度批次的第一步是验货,验货不过就不开工,比开工后跑出一堆错数再补救便宜得多。
一个考虑了前置条件的调度批次长这样:
# 生产调度批次(示意) 1. 源新鲜度检查 # 验货:上游到货齐了吗 |- 未通过 -> 告警并中止,本轮不开工 2. dbt build # 施工:全项目按依赖图构建 |- 失败 -> 定位失败模型,决定重跑或告警 3. 行数对账测试 # 验收:关键表数字对吗 4. 构建文档并发布 # 竣工:文档站点随构建更新
注意第二行的全量构建不带选择参数——生产调度跑的是整个依赖图,让工具算顺序;只有 CI 场景(5.2 节)才做选择性执行。两种场景的分工别弄反。
仓库自带的定时任务。 最轻的方案:一条 cron 或云仓库自带的任务计划,到点执行构建命令。适合单人或小团队的起步阶段,成本为零。短板也直白:没有执行历史的界面(翻日志)、失败通知要自建、重跑靠手敲。
通用调度平台(Airflow、Dagster 等)。 把 dbt 构建作为一个任务节点编进平台,获得的是执行历史、重跑策略、依赖编排(比如「先跑同步管道再跑 dbt」的跨系统依赖)、告警路由。适合已经用调度平台管着数据管道的团队——dbt 不该在调度平台之外另立一套定时,所有数据任务的节奏应该在同一张编排图上。
托管平台(dbt Cloud 或数仓厂商的托管调度)。 用订阅换运维:执行环境免维护、执行历史开箱有、CI 与调度一体化。适合团队规模到了「自建的人力成本超过订阅费」的临界点(1.2 节的账又算了一遍)。
三条不成凑一桌的经验:起步用仓库定时任务不丢人,它跑两个月你会精确知道自己需要调度平台提供什么;一旦出现「多个数据任务要排相对顺序」的需求,就到了上通用调度平台的时刻;托管与否是成本问题不是技术问题,别让它变成信仰之争。
监控最怕两个极端:什么都在告警(狼来了),什么都告警不到(事后再救)。四维各管一类异常,阈值设计的原则是「正常波动不响,模式异常就响」。
第一维:任务成败。 最粗的一道关——构建退出码非零就告警。要补充的是部分失败的处理策略:构建命令默认「一个模型失败,下游全部跳过」,日志里失败模型与跳过模型一目了然。告警信息里必须带上「失败的是谁、跳过了多少下游」,值班的人才能判断影响面。
第二维:时长趋势。 构建时长连续数日单调上升,几乎总意味着上游数据量在涨、或某个模型在劣化——这时的告警是「预警」而非「故障」,给了你在业务方感知之前处理的时间窗。阈值用相对值(比近两周均值高出百分之五十)比绝对值耐用。
第三维:数据新鲜度。 3.2 节的源新鲜度在生产调度里是「开工闸门」,在这里是「持续哨兵」——同一天里上游补数、断流,新鲜度检查都会知道。它回答的是「我现在看到的数据有多旧」这个业务方最常问的问题。
第四维:行数波动。 每张核心表的当日行数与前七日同日比较,波动超过阈值告警。这一维抓的是「构建成功但数据不对」的静默异常——上游断流半天(少了一批数据但构建照常成功)、上游重复推送(行数翻倍)都逃不过它。这是 3.3 与 4.4 节反复强调的对账思想的运维形态。
⚠️ 常见坑:告警只发到「群」,不发到「人」。群里几十条消息混着业务通知,故障告警半小时没人认领是常态。处置约定要明确到人:告警触发后谁应答、多久内应答、应答不了的升级给谁。监控体系的价值在闭环,不在消息条数。
故障响应的慌乱程度,取决于预案的有无。给一份可以直接改编的最低版本:
预案每执行一次就修订一次——真实的故障处置永远是预案最好的迭代来源,这也是 4.4 节事故档案方法论的运维版。
四维之外还有一条非技术的经验:把监控看板的入口写进值机手册与团队公告,让「现在构建到哪一步、每张表多新」成为全团队随手可查的公开信息。监控数据只留在运维手里时,业务方的询问永远是「好了吗」,运维只能人肉回答;公开之后,多数询问在看到看板的那一刻自答,值班的人只需要处理真正异常的部分。可观测性不只是给机器与值机员的,也是给数据消费者的——公开本身就是一种信任建设。
由业务对时效的需求倒推,而不是由「多多益善」正推。天级报表配天级构建(凌晨一次);小时级看板配小时级构建;构建时长逼近构建间隔时(比如构建要五十分钟、间隔一小时),说明这个频率已到极限——要么优化时长(4.3 节),要么与业务方重谈时效。一个常被忽略的约束是频率与成本的关系:全量物化的模型每次构建都是全量成本,高频调度下成本线性放大;高频场景天然偏爱增量与视图——调度频率反过来影响 2.2 节的物化选型,这是「四要素」里延迟要求的另一面。
这是「无人值守时段」的经典问题,两个手段组合应对。一是失败即暂停下游:构建命令默认失败时下游跳过,配合调度把「数据不完整」的状态显式留给下游消费者(报表上标注「数据截至昨日」),好过让不完整的数据冒充完整。二是告警分级:彻底失败立即呼叫值班(电话或强提醒),部分失败(某张次要表失败、主链完整)次日晨会处理即可。无人值守时段的目标不是「有人通宵守着」,而是「该叫醒人的叫醒,不该的留到早上」——分级错误比不告警更消耗团队。
生产日常中高频出现的场景:上游管道发现昨天的数据有误,修复后要补灌。dbt 侧的标准动作是「指定范围重跑」:用选择参数挑出受影响的模型子集及其下游,配合增量模型的回拨水位(把判定条件回退到补数起点之前),一次定向重跑完成下游同步。这个动作值得写进值机手册并演练过——真补数时是按手册执行,不是现场发明。前提条件只有一个:受影响范围要靠血缘图圈定(6.2 节),圈漏了就会留下「部分表补了、部分没补」的口径分裂。
到这一章为止,项目已经是一个每天在生产上运转、有人看护的系统。最后一章换个视角:当团队和消费者都变多之后,文档、血缘、权限与生态如何让这个系统被更多人信任地使用。