性能剖析是一个低强度分析工具,可以用在生产应用程序中识别瓶颈。
它是在指定时间范围(持续时间)内定时(采样周期)的调用系统中断,然后收集当前的调用栈(call stack trace)信息,记录调用栈中出现的函数及这些函数的调用结构,基于这些信息得到函数的调用关系图及每个函数的 CPU 使用信息。通过这些信息,我们可以清楚的看到时间是花费在哪一个方法的哪一行上,从而有针对性的进行代码的优化。
详细数据介绍:性能剖析相关知识
我们的Ai产品中有两种方法可以进行性能剖析的设置,分别是 应用>tier>性能剖析 以及 关键事务>性能剖析。
2. 应用>tier>性能剖析
3. 关键事务>性能剖析
If you want to… | Do this |
---|---|
查看性能剖析对应关键事务信息 | 选择关键事务下对应名称 |
查看性能剖析对应的tier应用情况 | 选择应用程序下对应名称 |
从不同的维度查看trace | 点击耗时/开始时间 |
查看单个trace的详细信息 | 点击选中的trace |
线程分析页面
调用栈信息可以根据需要进行展开和收缩。
此处的百分比是根据在采样周期中,该行代码总计被采样到的次数与总采样次数的百分比。代码后括号中的内容是该代码在事务中的行数。
停到某个类的某个方法比如 get 的方法,一般都是由于在进行密集计算,或者调用数据库但是数据库长时间没有返回结果,或者数据库中有锁。如果是 cpu 慢,就会出现在这里;如果由于锁等原因,就会出现在线程和锁的标签页中。
时间分布图的百分比计算: 该行代码总计被采样到的次数与总采样次数的百分比
CPU时间图的百分比计算: 该行代码总计在runable状态被采样到的次数与总采样次数的百分比。
可以理解是该方法在这类请求中的对于CPU开销占比。
线程和锁图的百分比计算:该行代码总计在norunable状态被采样到的次数与总采样次数的百分比。 可以理解是该方法在这类请求中的对于处于blocked状态时间的占比。
注:如果想要进行 关键事务>性能剖析 则需要预先将要进行性能剖析的Web 事务设为关键事务,且性能剖析进行时必须确保剖析的探针具有持续的访问。
设置方法如下,
1.问题类型:过度加载动态类导致性能下降
问题调查和分析:
这个问题的后续:
2.问题类型:不正确的thread sleep使用导致性能下降
同时结合客户终端请求有大量502报错。
初步分析是因为线程池用尽,导致请求堵塞在请求队列中,最后导致大量请求访问超时,报502错误。
给出建议操作: 增大线程池最大线程数量,继续观察。
* 第二阶段:
增大线程池最大线程数量以后,高峰期访问性能并没有得到提高,我们需要进一步分析。
由a1进一步分析:应用表现出性能的下降,却没有观察到CPU占用的提高,那就表示线程可能在等待I/O或是其他一些操作的结果。
同时通过 JVM性能剖析功能,发现确实用户在 发起对于后台系统调用 以后会进入都会进入thread.sleep。(时间太久找不到图,就不提供截图了。)
与客户开发确认后发现,在调用 交易平台 后端的 client.jar包中每次调用发起以后都会调用thread.sleep进行线程休眠(休眠时间与thread数量成正比)。
此时给出的相关建议:线程是一种十分宝贵的资源,创建,销毁,切换 都是相当耗性能的,当Sleep的时候,就等于说:现在我不用,但是你也别想用。你要用,自己去Create一个。当creat的线程到底最大值以后,请求就只能阻塞在请求队列中了。因此sleep的时候虽然不占用CPU,但是占着线程资源,会严重阻碍系统的线程调度。
经过现场与客户后台系统开发确认,为了保证前台系统的正常运行,临时取消了thread.sleep的调用。同时在客户后台系统加装探针,调整线程池大小,确认后台系统可能的瓶颈。
3.问题类型:应用性能异常缓慢