性能故障的处理方法

Posted on Sat 22 May 2010 in 我思

公司的一个主营业务,从5月1日开始就不正常工作了,表面的现象就是DBCP的连接池耗尽,代码提示Cannot get a connection, pool exhausted,开始最严重的时候得靠人工启动,才能恢复服务。

后来问题逐渐往下定位,在代码级:修改了竞争性的SQL更新操作,降低了特定请求处理中的IO消耗;在配置级:禁止了Apache错误恢复的重试机制,调整了A和T之间的超时设置,优化了DBCP中的设置。好像都没解决问题,忽然有一天,系统部的人说问题解决了,原因是他们换了一台Apache分发服务器。

觉得有些不知所谓,正好这时候搞清故障原因的事情又落到我头上了,那就分析分析吧。

对于线上的性能故障,从观察现象,分析定位出关键问题,然后提出解决方案;再观察改进后的系统,定位新的问题,提出新的解决方案,可以形成一个闭环。

在每个问题处理的周期内,要尽量全面的思考问题,尽量不要遗漏重要的环节;在看到现象时,首先要做的是想办法拿到相关数据(系统参数、线上的配置、当时时间段的用户请求数),而不是轻易下结论;条件允许的情况下,逐步进行改进,比对改进前后的监控数据,用数据说明改进的效果。

上面罗嗦的两段话是我憋了半天才写出来的,舍不得删了。我想表达的意思就是: 每次改动前都得想清楚了为什么要改,没改的时候就得监控一些关键指标,好和改完了的对对比效果。

都憋出什么指标了呢?

1  请求失败率

请求失败率=返回给用户502失败响应的数量/此时段的所有用户请求数

用某个时段的请求失败率来衡量服务质量,大家都可以接受,减少就某个个别现象的扯皮。

从改参数到切换服务器,可以清楚的看到,失败请求率的降低。

2  平均处理时间

把一个时段的请求按照处理完成速度排序,分别统计前50%、90%、99%、100%请求的平均处理时间。

这个是和ab学的,也的确很有用。可以指导我们调整分发服务器和应用服务器的超时时间配置,保证我们为绝大多数用户提供高质量的服务。

3  请求并发报表

之前的并发监控报表,是按照300秒一个时段来统计并发情况的,粒度太大,反映不出实际的应用并发情况。

现在改为按秒为单位,新的监控报表能辅助我们快速定位故障时段。

 

我面临的最大问题就是如何模拟线上的压力

由于数据安全性和实现开销问题的考虑,在开发环境很难模拟线上实际的负载情况。

于是,我们只能主动提高系统压力,积极去验证我们的性能上限,来暴露存在问题。

进行这种操作一定要提前做好预案,相关开发人员和系统部工程师都要在场,做好相关监控和应急准备。

 

针对目前发现的问题的改进意见

下一步工作,还是应该在系统和开发方面双管齐下。
1   系统角度

在系统层面,我认为最有效的改进是拆分。
1.1   分发拆分

目前的分发口太窄了,并且一个分发服务给20多个应用做分发,单点太厉害了。
1.2   配置参数优化

  • Apache配置:

      超时按照应用处理平均时间进行设置
      设置keepalive为Off

  • Tomcat配置优化

       DBCP优化
1.3   冗余

线上需要配备一定的冗余服务器,当出现故障时,可以通过切换比对的方法,排除硬件和操作系统级别的问题。

2   开发角度


我认为最有效的改进方案是数据拆分

2.1   数据拆分

把各个应用私有的数据迁出现有的数据库,对公共数据的操作通过公共服务进行。

  • 好处:

      避免多个应用对用户级的数据进行竞争性操作

      提高数据库性能的扩充性

      方便数据库性能问题的定位

对数据拆分的认识需要达成,保证系统资源和开发资源。

2.2   系统监控

目前对应用的系统级监控做得还不够,还需要继续发现有用的监控指标,然后把监控工作系统化,开发工具或系统来实现。