大家好,我是蓝胖子,相信大家或多或少都有这样的经历,当你负责的功能出现线上问题时,领导第一时间便是找到你询问原因,然而有时问题的根因或许不在你这儿,只是这个功能或许依赖了第三方或者内部其他部门,这个时候快速排查问题根因就是关键,给领导留个快速解决问题的印象,绩效也找不到理由给你打低了。
而日志作为最简单最直接的排查问题手段,就起到了至关重要的作用, 关于如何打日志,我谈谈我的一些感悟。
日志应该由什么组成
首先,我们来思考下日志应该具有哪些维度的信息,日志无非就是要记录,什么时间,什么地点,发生了什么事情。
针对于应用程序来说,就是哪台主机,哪个应用服务,哪种业务,在某个时间点,出现了什么问题。
这里要特别注意的是🔊🔊🔊,日志应该包含业务的上下文信息
,例如,要记录某个用户做了支付行为,你应该要记录用户的id,订单号,甚至可以更详细点,把订单的价格,购买的商品信息都记录下来,以便后续排查问题时能直接通过日志找到用户的支付记录。
当然,业务的上下文信息需要根据业务情况决定,不同业务需要考虑下需要打印的业务信息。
打印的日志格式,我还是建议json
,毕竟json 更容易被分析,特别是如果是当用上ELK这类的日志收集框架后,能很容易对日志提取字段进行分析。比如将日志中的应用服务名称
字段提取出来,在ELK中做聚合分析,我们能分析出某段时间内,究竟是哪个应用在疯狂的打日志。
甚至也可以从日志中提取业务场景
字段,对其进行聚合分析,得出某段时间内,那种业务在疯狂打印日志,评估其日志打印是否合理,如下图所示,是在kibana上对过去15小时的日志按业务场景对日志量进行的分析。
我总结下,日志的基本组成如下
{"host"="主机名",log_time="打印日志格式",app="应用服务名称",action="业务场景",msg="描述信息", err="如果有错误打印错误信息", 业务上下文信息....}
日志的作用
日志除了按上面提到的进行聚合统计分析系统日志量情况外,还可以按业务维度的字段进行聚合分析,比如将业务场景字段设置为登录,利用它统计每天,每小时登录的人数。利用日志做一些业务维度的监控
。
当然,日志除了去进行分析统计外,更是为了解决问题,对出错进行恢复,让系统留下运行的痕迹而打印的。打印日志前,一定要想清楚,我们需要解决的问题。
举一个场景,蓝胖子之前在服务中做过邮寄服务,由于邮寄需要依靠第三方的接口,并且整个邮寄的逻辑比较复杂,会有许多邮寄过滤条件,并且后续的产品功能持续有对这部分过滤逻辑进行修改,如何在对第三方接口进行容错,如何后续的迭代过程中对 过滤代码进行容错,保证出错后能有办法恢复出错用户的邮寄就成了要思考的问题。
其实要解决这类问题,最简单的办法就是将程序的运行轨迹能用日志表示出来,有了日志,日志被ELK此类日志收集组件收集后,后续就能通过ELK对日志进行搜索下载,进而恢复数据。所以,蓝胖子在开始邮寄之前,把人员名单记录了下来,把后续邮寄过程中出错的人员,无论是第三方接口调用出错,还是程序内部对数据库或者缓存的访问出错,把它们的错误原因和出错时影响到的用户名单都记录了下来,并且将那些由于邮寄过滤条件过滤掉的用户和过滤原因也记录了下来,最后,把邮寄成功的用户记录下来。
可以看到,最终我只要通过日志,就能找出最终邮寄成功的用户,以及邮寄失败的用户,整个邮寄过程就变透明了
,如果有邮寄失败的用户,我也可以通过日志进行恢复。
那你可能会想,那我干脆将程序所有接口,每步操作都打上日志,不就好了吗,其实也是不对的🚫🚫🚫。
1,会让代码变得很臃肿😮💨。
2, 打印的日志量也是很大,影响磁盘容量以及日志分析组件收集,因为多了很多无效日志。
所以,下面我给出几条打印日志的建议,
打日志最佳实践
☝🏻第一条,在请求第三方接口或者内部部门接口的时候,你应该要对接口参数以及返回结果
进行打印。比较重要的场景甚至还需要对错误情况进行告警🚨。这样起码在接口出错时,在第三方部门需要你提供参数时能及时捞出日志。
第二条 ,在程序对数据进行修改时,记录下改动日志
,这也是为了让程序留下运行的痕迹,有助于我们知道对数据做了哪些改动,以便后续出错时,能通过日志对数据进行回滚修复。甚至为了让这个原则更加容易落地,我们可以修改数据库的客户端库,通常这类库会提供许多埋点钩子函数,我们可以实现它们让其在进行delete,update,insert操作时,对sql进行记录,记录下对数据的改动。
第三条,程序出现报错时记录日志,这条基本是准则,不过就像前面提到的那样,在记录时除了记录错误信息,还需要记录下错误的上下文,比如是哪个用户,涉及到了哪些业务数据。
第四条,可以利用日志做一些关键业务信息的监控,特别是一些复杂的业务逻辑,通过日志记录来让业务流程透明化。就像蓝胖子之前提到的对接邮件服务那样,让邮寄过程透明化,也有利于对我们程序的出错恢复。
最后,
自荐一波✅:
欢迎朋友们关注我的公众号📢📢:【蓝胖子的编程梦】!
学习容器知识🐳,性能监控🚀,Golang🐋 相关编程知识