MaxCompute 用户一个常见的问题是:同一个周期任务,为何最近几天比以前慢了不少?或者为何以前都能按时产出的做业最近常常破线?html
一般来讲,引发做业执行变慢的缘由有:quota 组资源不足、输入数据量变更、数据分布状况变更、平台硬件故障引起重跑等。本文主要针对数据变更引发的做业慢问题,介绍用户如何经过 MaxCompute Studio 的做业执行图及做业详情功能来自助定位问题。sql
咱们举个例子来讲。 下面是同一个任务分别在5月7日,5月9日的执行状况,下面分别称为做业1、做业二:安全
一般来讲,进行两次执行对比前,要先对比一下两次执行的 SQL 脚本是否相同,若是在这之间用户改动过做业脚本,就须要先分析改动的部分形成的影响。若是脚本内容一致,随后还须要比较执行计划是否一致,能够经过 MaxCompute Studio 的做业执行计划图功能来分析(参看文档),可视化地看看两次执行的计划图长得同样不同。 (做业对比的功能正在开发中,下个版本的 Studio 中就能够一键对比两个做业,标注出 SQL 脚本及其它部分的不一样之处啦,敬请期待)app
在上面这个例子中两个做业的 SQL 脚本及执行计划彻底一致,出于数据安全考虑,此处不粘贴具体 SQL 的内容。工具
第二步要看一下做业输入数据量有没有明显变化,有多是某一天输入表或分区的数据量暴涨致使了做业执行变慢。做业输入数据在 Detail 页面左侧,那里列出了这个做业全部输入的数据表和最终输出的数据表。 展开 输入->Table Name 能够查看详细信息,包括是哪一个 Fuxi 任务读取了这个表,读取了多少条记录以及读取的数据量大小。这些信息,也标注在做业执行计划图 graph 上,方便查看。以下图所示,优化
也能够从graph上直接读取输入行数或者字节数(默认展现行数,可在边上右键切换为字节数):spa
在这个例子中,从输入数据量来看,两次执行的输入数据量差异不大。3d
第三步,那到底做业运行状况是怎样的呢?运行那么长时间,或花费在哪儿了呢?不急,快快使用做业回放!
在 Studio 中做业执行计划图底部提供的做业回放工具条,容许用户在 30 秒内快速回放做业执行进度的全过程!这样咱们就能够迅速地了解究竟是哪一个 Task 耗时最多,或者处理得数据最多,或者输出的数据最多等等。日志
经过回放重现做业执行过程,Studio 提供进度图以及热度图方便从不一样维度进行做业分析。htm
从回放中能够看出
(1)J6_2_4_5 task是整个做业瓶颈,时间消耗最多,从task热度图中也能发现该节点明显热于其它节点。(时间热度图上越红表明运行时间越长,数据热度图上越红表明处理数据越多)
(2)同时对比两个做业的回放过程,可以比较明显地发现做业一在J6_2_4_5运行时长要大于做业二,说明做业一在J6_2_4_5阶段变慢了,初步怀疑有长尾节点产生。
接下来切换到时序图tab,比较两个做业的执行timeline:
虽然两个做业timeline的时间尺度不一样,可是能够明显看出,做业一中J6_2_4_5 占了更长的比例,由此能够判定是J6_2_4_5 在05-07执行(也就是做业一)发生可能长尾,致使整个做业执行变慢。
第四步,经过graph或detail tab 对比J6_2_4_5 的输入数据量
关注上图中J6_2_4_5 输入数据量和统计信息,经过比较可看出,两次执行的J6_2_4_5 输入数据量基本相同,1.58万亿字节 vs 1.7万亿字节,从统计信息来看,累计执行时间及平均时间也基本相同:292398 vs 307628, 72s vs 76s 但做业一 fuxi instances中的最长执行时间为710s, 由此能够认定是某几个fuxi instance长尾致使了J6_2_4_5 这个fuxi task的长尾。
第五步,对两个 J6_2_4_5 fuxi instance 列表按照latency 排序:
或者转到分析tab下的长尾页面查找长尾节点:注意这个图中的比例尺是以等比而不是等差方式标定的,所以,上面突出的比较长的毛刺就极可能是长尾的实例了。能够经过浮动窗口中的具体信息来判断。 另外 Studio 也提供了诊断的页面,来自动找出超过平均实例执行时间两倍的长尾实例。
从上面fuxi instance 输入数据对比能够肯定,由于J6_2_4_5#1912_0 这个instance 数据倾斜致使整个做业一长尾。即J6_2_4_5#1912_0 是latency排第二的输入数据量的7倍!
第六步,查看单个instance的执行日志,并经过job graph分析J6_2_4_5的具体执行计划,找到致使长尾的数据来源。
打开J6_2_4_5的operator graph, 能够看到有两个join:Merge Join2和Merge Join3,这里以Merge Join2为例展现如何查找数据来源。
从Merge Join2中可看到join key:_col13, user_id。 其中_col13 来自于J5, 点开J5后发现_col13来自IF(ISNULL(HOT_SELLER_MAP(sellerid)),sellerid,CONCAT(seller,TOSTRING(RAND()))) 说明_col13由seller决定,该seller来自于M4和M3。
分别打开M4和M3的Operator详细信息,能够看到seller 分别来自tmp_s_dw_log_app_user_track_pre_1_20180508 和dim_feed_shop。
同理能够分析出Merge Join2 的user_id 来自于dim_tb_shop。
最后,经过写sql模拟产生对应的userid及_col13,比较这两个字段的数据量大小,在针对sql脚本进行优化便可。sql脚本优化不在本文介绍范围,所以不在此赘述。
有了 MaxCompute Studio 做业分析这样趁手的工具,遇到各类 MaxCompute 做业的问题就再也不一筹莫展了,甚至,我们都没有打开那 “让人悲喜交加”的 Logview 不是?
本文做者:皓平