10水压表与水质检测:监控目录
监控要回答的不是"服务器还亮着绿灯吗",而是一句话:哪一段漏了、漏的是什么、谁来修。
一根管子铺出去,分成四段。每段头上挂一块表:压力表看这一段通不通,化验单看这段水干不干净。哪块表摆了红针,就在旁边挂一张小牌,写清楚是哪一段、错在哪、谁负责。装表不是为了挂墙上好看——是为了漏的时候不用把整根管子拆开找。

一、先说人话:别盯着服务器的绿灯

集群里最常见的那种"监控"是这样的:CPU 不高、磁盘没满、进程都活着,一屏全绿。这屏绿只说明一件事——管子没爆。它一个字都没说水对不对。

业务真正怕的不是管子爆,是水压低了一点点:报表还能打开、页面还能点、数就是错的。没人报错、没人喊,等到有人拿这个数去开会,才发现已经错了三天。

所以这一页的监控只干一件事:把"数不对"翻译成"哪一段漏了、漏的是什么"。原文那条链路的说法很干脆,就是四段:源到贴源、入湖任务、湖仓 ETL 调度、湖到仓到页面。一段一块表,谁也不替谁。

整页只用三个词,不换:

一条判据好的链路看板不是"四块表各看各的",是把四段的结果合成一个状态:入湖一致性检查、入湖 CDM 任务、湖仓开发任务、同步 CDM 任务——四项全部成功无异常,才叫这张表"正常",否则一律算异常,并且必须写明是哪一项出的问题。

二、拆开看:表、单、铃三个零件

先认脸。三个零件各管一段话,认完再看它们在一根管子上怎么排。

📈 压力表(任务状态)

像什么:水管上那个圆盘表,指针在绿区就是通,掉到红区就是没水。

其实是什么:调度系统里每个节点、每次同步的运行状态。它只回答"这段程序跑完了没有",不回答"数对不对"。

真名
status(任务状态);入湖节点 CDM / DataX,出湖节点 SeaTunnel
在哪看
海豚工作流实例、SeaTunnel 概览页、Doris 监控面板

搞错了会怎样:把"指针在绿区"当成"水是好的"——这就是本页第六节那个反常识。

🧪 化验单(数据质量差异)

像什么:水厂每天抽一瓶水去化验:浑不浑、有没有泥沙、几项指标超没超。

其实是什么:源端和贴源层之间的差异记录——行数差多少、指标差多少、维度差多少。原文说这块"前期完成",也就是最早做的那一层。

表这一层
data_quality_monitor_table_dim:源端条数 source_rows_nums 对 hudi 端条数 hudi_rows_nums,差在 rows_diff
字段这一层
data_quality_monitor_field_dim:字段类型差异,加前一天的均值 / 方差 / 最大最小 / 空值比例对比

搞错了会怎样:只比总行数、不比字段。字段类型从字符悄悄变成数字,行数一行不差,取数时整列变成空值——行数表全绿,页面全空。

🔔 铃(告警到人)

像什么:门口那个铃。管子一漏就响,而且响在值班室,不是响在机房角落。

其实是什么:把表和单的结果按"页面 → 指标 → 表 → 任务 → 责任人"串成一行,出问题时推给那个该动手的人。

真名
表级监控模型那 14 个字段(第四节逐条过),其中 job_owner 决定这声铃响给谁
在哪
全链路监控看板 + 明细页

搞错了会怎样:铃响在一个没人看的群里。第二天同一个地方照旧漏。

四段各自挂什么表

这张表是本页的骨架,四行就是四个段位。看的时候只记一件事:这一段挂的是表还是单,它替你回答什么问题。

段 · 挂什么表它替你回答什么
①源→贴源 化验单:数据差异(行数、指标、维度)进厂的水,跟河里的是不是同一批、同一个量
②入湖 压力表:任务状态(CDM / DataX)这一车水到底运进来没有
③湖仓调度 压力表:任务状态 + 下游影响(海豚)这一段停了,会拖垮哪几张下游表
④湖→仓→页面 同步状态 + 表级血缘到帆软仓里的水和龙头出的水,是不是同一批

这四段各自会冒出哪些异常,第三节一张一张拆开。先记一句话:①是化验单,②③是压力表,④是出口的同步状态加血缘。四块表不重叠,这也是排错快的原因——看到哪种异常,就知道该去哪个段。

第一段,源到贴源。这是进水口的表,也是最容易被跳过的一段。它不比"任务成功没成功",只比两边的东西对不对得上:源端删掉的行,湖里是不是还留着;源端新增的行,湖里有没有跟上来。这一段的监控前期就做完了,原因很简单——它最便宜,一次行数比对就能抓住大问题。

第二段,入湖任务。CDM 或 DataX 的任务状态。这段的意义原文写得很直白:入湖任务状态异常,会影响后续 ETL 的数据流转,最后导致前端数据异常。换句话说,②掉了,③④都白搭。

第三段,湖仓 ETL 调度。海豚里的加工任务。这段的表不只报自己坏了,还要报"坏了会拖垮哪些下游表、对应影响帆软的哪个场景模块"。这一段是四段里唯一需要血缘才说得清的一段——没有血缘,你只知道一个任务红了,不知道哪张报表今天别看了。

第四段,湖到仓到页面。SeaTunnel 把湖里的表同步进 Doris,页面再连 Doris。这一段断了,页面不会报错,只会一直显示昨天、前天的数。原文的结论一句话:同步任务状态异常,同样会影响帆软展示数据的准确性。

一根管子四段,每段挂一块表 表看通不通 · 单看干不干净 贴源 入湖 湖仓 入仓 ① 差异 源↔贴源 ② 任务 CDM/DataX ③ 调度 海豚 ETL ④ 同步 SeaTunnel 页面 帆软控件 ① 化验单:行数 / 指标 / 维度对不对 ②③ 压力表:跑没跑完、拖垮了谁 ④ 出口表:仓和页面对不上就是它 虚线 = 这块表响了,得有人去修 哪张表 · 哪个任务 ads_log_inv_kpi_wide 报错:心跳超时 责任人:job_owner 页面 → 指标 → 表 → 人

三、别只会说"失败了"

监控里最没用的一句话就是"任务失败"。它对齐不了动作:源端网络断了要去找源系统 IT,集群没资源要找运维,上游还没跑完只能等——三句话对应三类人,干的三件事完全不同。

所以原文把异常按组拆开,标签给机器看,含义给人看。三组,逐条来。

1)数据质量异常:化验单上说水不对

标签原文含义 · 人话
source_delete源端删除。源系统把这行删了,湖里还留着。行数差 rows_diff 是正数:hudi 比源端多。
source_add源端新增,增量时间字段未生效。源端加了新数据,但增量抽取靠时间字段过滤,那个字段没更新——新行压根抽不进来。行数差是负数。
table_columns入湖表与源端字段差异。两边字段对不上:少一列、多一列、或者类型不一样。行数可能一行不差,字段已经错位。

这三个标签的区别很关键:前两个是"行数对不上",第三个是"行数对得上、字段对不上"。只看行数的人,永远抓不到 table_columns。

2)入湖 / 同步任务:压力表掉针

标签原文含义 · 人话
failed任务失败,源端网络问题 / 集群资源问题。要么源库那边连不上,要么湖这边没资源给它跑。这是"真失败"。
stopped任务停止,任务超时问题。跑太久,被强制停下来了。不是它自己报错退出。
running任务持续运行中。还挂着没结束。跑十分钟正常,挂一整天就是问题。

这一组标签是两段共用的:cdm 入湖有这三个状态,cdm 同步到 dws 也是同样三项。所以看到 failed 第一件事不是去修,是看它属于入湖那段还是出湖那段——修反了白忙。

3)调度任务:海豚里的那段

标签原文含义 · 人话
Failed集群资源问题 / 上游依赖任务失败。两种可能:自己没资源跑,或者前面那段根本没跑完。先看上游,再看资源。
Waiting上游依赖任务 running / 上游依赖任务 waiting。在排队等上游。不是它坏了,是还没轮到它。
注意大写 Failed 是小写的 failed 之外的另一套:前者是海豚调度任务,后者是入湖/同步任务。看板里混着出现,靠 abnormal_label 那一列区分,别看错组。

Waiting 不是故障,是排队。但排队时长能看出真问题:单个项目 756 个任务分布在 10 台 worker 上,其中 10.160.10.26 一台承接 218 个、排队 3.8 分钟,其余 9 台基本空闲。这不是任务慢,是活儿没分匀。看到一片 Waiting,先看资源分配,再看代码。

四、表级监控模型:14 个字段把整条链缝成一行

前面四段是分段看的。真正能干活的是表级这张表:一行不是"一个任务",是"一张表某一天的健康记录",从页面一路缝到源头。

原文给的字段一共 14 个。下面逐条过,每个字段后面那句人话,就是它在一条告警里替你回答的问题。

字段原文含义 · 它替你回答什么
finereport_name场景到页面。哪个业务场景的哪个页面(帆软那边的叫法)
finereport_widget场景控件。页面上的哪一块:一张图、一列表、还是一个筛选器
report_level指标 / 控件。这行说的是整块控件,还是控件里那一个数字
finereport_text对应指标。页面上那行文字的原文——截图给业务看时,他一眼认得出
dws_table相关 dws 表。这个指标的数从哪张汇总表取的
job_id调度任务 id。具体是哪一次实例(机器认编号)
job_name调度任务名。这个任务叫什么(人认名字)——排查时先搜名字
status任务状态。这次跑到哪一步了:成功、失败、还是还在跑
abnormal_label异常问题类别。属于哪一类异常——就是上一节那些标签
error_message报错信息。具体报的什么错,比如心跳超时
hudi_schema源头 schema。源头落在哪个库 / schema
hudi_table源头表名。源头是哪张表——顺着它才能找到入湖那一段
execute_time任务执行时间。什么时候跑的,用来分清"没更新"和"更新了但错"
job_owner任务责任人。这行该喊谁。铃响给谁,就看这一列

从上往下读这张表,就是一条链:哪个页面 → 哪个控件 → 哪个指标 → 哪张汇总表 → 哪个任务 → 什么状态 → 报的什么错 → 源头哪张表 → 谁负责。这也是它敢叫"全链路"的原因——一行就把两头挂上了,中间不留空档。

值在哪一条告警出来,不用开会挨个问人,直接能说出:哪个页面、哪个指标、哪张表、哪个任务——外加第五件,谁负责。这就是"表级"两个字的意思:单位是表,不是服务器,也不是任务。

一条告警摊开长这样

拿原文里那条真实的同步配置举例:湖里 dm_gk_hudi.ads_log_inv_kpi_wide 同步到仓里 dm_gk_dws.ads_log_inv_kpi_wide(原文那份配置是 SIT 环境,源端写的是 dm_gk_hudi_sit)。假设今天这次同步失败了,这一行会填成:

字段这一行填什么
finereport_name用到这张表的那张帆软页面(页面名原文没给,实际值现场核)
finereport_widget页面上对应的那个图表 / 数字块
report_level指标
finereport_text页面上那行指标文字的原文
dws_tabledm_gk_dws.ads_log_inv_kpi_wide
job_id海豚里那条 SeaTunnel 同步节点的实例号(机器认它)
job_name同一个节点的名字(人认它,排查时先搜名字)
status失败
abnormal_labelfailed
error_messageOperationTimeoutException(Hazelcast operation-heartbeat-timeout)
hudi_schema源头库 dm_gk_hudi
hudi_table源头表 ads_log_inv_kpi_wide
execute_time当天那次调度的时间
job_owner这个同步任务的责任人(实际值现场核)

error_message 这一栏不是把"失败"复述一遍,是留真报错:原文里这一类失败根因就是 SeaTunnel 心跳超时。这类失败有个好处——重跑就好,所以兜底是两层的:DS 节点自己重试,下游再挂一个 retry_to_doris 补跑。

反过来看,如果 error_message 里只有"失败"两个字,这条告警基本等于没报——修的人还得从头查一遍。

五、三层仪表:集群、任务、数据,各看各的

看板不止一块。原文分三层,对应三种人操心的事:机器够不够、任务稳不稳、数对不对。混着看就会得出错误的结论。

层挂什么表 · 具体看什么
集群侧Prometheus + Grafana。Doris 生产集群面板 http://10.160.4.111:8182/d/1fFiWJ4mz/doris-prod-cluster,看 BE / tablet 状态、查询延迟、导入失败
任务侧海豚实例 + 失败率。近 8 天 45,571 成功 / 296 失败 / 529 被杀,失败率 0.65%;根因集中在 SeaTunnel 心跳超时,retry_to_doris 自动重跑后全部成功
数据侧表维度监控 data_quality_monitor_table_dim、表字段维度监控 data_quality_monitor_field_dim、一致性检查自动调度。看源端 ↔ 贴源的行数差 rows_diff、字段类型差、入湖前后数值稳定性;湖 ↔ 仓的差异由一致性检查自动巡检

三层是个漏斗:集群侧亮绿灯只说明"有电有水",任务侧成功率高只说明"泵都在转",只有数据侧对得上,才敢说"龙头里的水是对的"。

0.65% 这个数要会读。它好看,是因为分母大。但它不回答"页面那个数是今天的还是上周的"——296 次失败的根因集中在 SeaTunnel 心跳超时,retry_to_doris 自动重跑后恢复,说明链路是稳的;可如果某张表压根没进监控,失败率再漂亮也照不到它。

注意529 次"被杀"和 296 次"失败"不是一回事。被杀是外部强停,不是自己报错退出;它在失败率里同样不显眼,但那张表当天很可能没更新。原文没写被杀的原因,遇到就去翻那个实例的日志和资源队列。

数据侧还有一块容易被忘:表字段维度监控不只是比字段名。它把前一天和今天的均值、方差、最大最小值、空值比例都存下来,还检查日期字段的合法性(有没有未来日期、有没有公司成立以前的日期)。这类"数还在、但整体飘了"的问题,行数对比永远发现不了。

六、一个反常识:SUCCESS 只说明程序没报错

会出事海豚给你 SUCCESS,意思是这段程序跑完了、退出码是 0。它不回答数对不对。三种情况全都能是绿的:源端新增了数据但增量时间字段没生效(source_add)——任务成功,新数据一行没进来;同一张表的日增脚本被放在两个已调度的作业里、又没设空跑——一天跑两遍;依赖检查只认"上次成功",上游 10-03 已经下线,08:00:05 照样放行,天天搬旧数据。最后这条是原文里的真实事故。

所以要验数,不能只看状态,得三方对:

  1. 湖:dm_gk_hudi 里那张源表的行数、字段类型、数值分布——看两张监控表(表维度 + 字段维度)。
  2. 仓:dm_gk_dws 里同步过去的那张表,行数、总额、最大日期是不是跟湖里一致。
  3. 页面:帆软页面上那个控件的显示文字,跟仓里同一个口径算出来的数对一遍。

三方都对上,才叫"数对"。三方对不上时,这一页的用处才真正显出来:差在湖和仓之间 → 是 SeaTunnel 那段;差在仓和页面之间 → 是帆软取数或缓存那段;湖本身就比源端少 → 是入湖那段。不用拆整根管子,看差在哪个接口就够了。

做对了把 SUCCESS 降级成一个中间信号:表是绿的,也要有三方对账的结果,才敢把这个数拿去开会。

七、搞错了会怎样

四种坏法,按严重程度排。后两种不是假设,是原文记录里真发生过的事。

一、只盯绿灯Prometheus 全绿、任务看着也都成功,页面上的数错了三天没人知道。绿灯管的是机器,管不到"源端删了几行、湖里还留着"。
二、报警不带页面和责任人只报"任务失败",收件人在群里一圈一圈互相问"这是谁的表"。所以 finereport_name 和 job_owner 不是装饰,是让铃响在对的人头上。
三、有些表压根没进监控搭看板时的真实记录:DWS 里的 ADS 表找不到同步任务。这种表在看板里永远"没有异常"——不是它好,是没人盯它,页面不更新也查不出来。上线前先确认每张前台表都有对应的同步任务。
四、对账口径不一样调度任务里的离线表,更新保留历史;实时表更新不保留历史(防止数据量过大)。拿这两类表直接比行数,会得出"差异巨大"的假警报。

八、一句话记住

回头看这四段:源到贴源挂化验单,入湖挂压力表,湖仓调度挂压力表,湖到仓到页面挂同步状态加血缘。四块表合起来只服务一句话——哪一段漏了、漏的是什么、谁来修。

所以别把监控当成"再买一块大屏"。大屏只解决"能看见";那 14 个字段的表解决的是"看得懂、找得到人"。这两件事差着一整条链路的维修时间。

做对了好的监控不是"亮绿灯",是出问题时能一句话说清漏在哪、谁来修。
四段式14 个字段三层仪表失败率 0.65%表 / 单 / 铃