想定,取消了之前的发布单,联系运维同学,帮忙重新开了个紧急发布的绿灯, 重新开始发布。幸运的是,这次没有再报错误日志。于是,我按照写好的发布文档,一个人在这静静的天亮时分,按部就班地开始发布, 一直发了两个小时,到七点半多才发完,一如 08 年踏雪归来的感觉。
反思: 如果在 QA 有验证那个退款消息的任务, 就不会出现这个尴尬的局面了。因为这个任务的消息处理,需要加载一个自定义的 消息接收器,而这个没有被覆盖到。 这是一条漏网之鱼。
正要鸣金收兵,忽现新军情:电子发票索引同步的一队小骑兵,趁我困倦之时,偷袭过来,想来个以逸待劳。任务里的一段 groovy 脚本无法执行。有几条消息就出错几条。得赶紧解决,不然线上又要报问题了。
排查这个错误,有点尴尬。 错误日志只打印了: failed to execute 。。。 啥信息也没有。 我总不可能添加一行日志, 再发布一次吧。近乎崩溃。怎么办怎么办 ? 扫了一眼脚本,有个奇怪的格式化日期的变量似乎没定义。想用另一种先替换看看。没效果。试来试去,没效果。
此刻,有点难以承载思考了,有点扛不住了。 怎么办 ? 思来想去,只好打扰一下团队同学了。 叫醒了三位懂些 groovy 的同学,帮忙一起排查下。
KP 同学提醒说,在本地运行下这个脚本。 我马上想到了,可以把消息和脚本放到本地工程里运行下,看看哪里报错。那个被怀疑的变量也找到了定义的地方。在本地运行是通过的。 这可让人有点摸不着头脑了。 天已经亮了,八点多了。
有同学建议说,回滚吧。可是,回滚的代价太大了。 花了一整晚,终于将老的工程迁移到新的工程, 难道要因为一个小的问题,再滚回到原来的 ? 且新的工程回滚到老的,也是有比较大的风险的,发布也要经过一系列比较繁琐的操作,容易出错。 我宁可背一个 P4 故障,也要把这个问题解决掉。已经没有退路了。
突然灵光一闪,可以在预发起相同的任务,然后加调试日志,在预发看看是什么缘故 。 燃起了新的希望。
用最后的精力折腾了一下, 发现报 unable to solve groovy.json.JsonSlurper 。 我以为是没有 import ,因此加了一行 import 。可是还是报错。 KP 同学说 JsonSlurper 这个类没有找到啊,且最好把 groovy-all 也引用进去吧。关键的一击啊 ! 我马上去工程里看了下,groovy 2.0.8 才支持 JsonSlurper ,而我之前为了单测通过,只用了 groovy 2.0.1 。
立即修改,部署到预发, 解决了。 耶 !
线上消费出错怎么办呢 ? 先用预发的任务消费线上的消息吧,确保后续的数据都写入 OK , 待明天做个优化后,再切回到线上的任务消费。原来预发可以作为线上的 “备胎” 啊!
反思: 不用说,这个任务也没回归到,因为很边缘。 然而,这个任务引用了一个类,依赖更高版本的 groovy ,是个局部细节问题,没有覆盖到。 看来, 凡有疏忽,必受惩罚。 老天爷的惩罚还是比较轻的: 照这样算下来,胜算大抵只有 80% 左右。
终于可以碎觉了。 emm.... 别打扰我。
下午来到公司, 王爷 跟我说, S 的监控统计不对劲, 曲线值很低,跟业务量完全不匹配。我想,可能是日志平台又出问题了 ? 之前间歇性也会这样。但王爷坚持要查一下。于是,我开完一个会之后,就找日志平台的同学苏苏一起去查了。
苏苏显然更相信自己抓包看到的数据,说,这个业务量可能就是这样。但我深知,业务量肯定不是这样,更可能是改造工程的过程中,某个配置有问题,但暂时不知道是哪里有问题。
不过苏苏查底层问题,明显很有章法。在经过我认可后,在机器上安装工具,抓包,看监控图表,发现 在 S 发布点之后,写监控统计就一直报错了。查来查去,发现 S 引用了一个自研轻量级 R 的包,来写入监控数据, R 则会读取 S 的一个配置文件,而这个文件的 NSQ 配置是错误的。至此,真相大白。
想到之前还没仔细看过监控统计的代码,领悟: 每一个不清楚的想要暂时跳过的地方, 老天爷都会恩赐一个问题, 逼着你最终弄清楚。
像是走过了一段较长的路。 面对大流量下的大改动的发布,曾经感觉到比较大的压力。发布完成之后,感觉似乎没那么可怕了。 一切都过去了。
流量汹似海,心内亦平川。 平常心就好。