Skip to content

title: 性能监控 author: 书虫 tags:

  • 工作记录 categories:
  • 工作 date: 2021-01-13 15:18:00

DoKit性能监控实现原理

一、方法耗时检测

二、Activity页面启动耗时

三、CPU使用率检测

四、内存检测

五、帧率检测

六、内存泄露

七、卡顿检测

获取App启动耗时

使用ASM库插桩的方式,监听Application的声明周期回调

  1. 在如下两个方法调用中分别记录一个时间戳,根据两个时间戳就可以计算出启动耗时。

onMethodEnter  -> recodeObjectMethodCostStart

onMethodExit -> recodeObjectMethodCostEnd

获取内存Memory大小

https://blog.csdn.net/logan676/article/details/107107068

获取FPS帧率

帧率监控从API 16+开始支持

监听Choreographer.FrameCallback#doFrame方法。系统每次绘制的时候都会回调doFrame方法,通过主线程handler每隔一秒种发一个runnable消息,消息中运行#doFrame,使用计时器累加刷新次数就可以计算出帧率。

卡顿检测

检测卡顿的原理是:

监控主线程消息队列,消息队列处理消息时会打印日志,通过前后两次打印日志的间隔和阈值比较即可检测出是否出现卡顿。

检测卡顿的原理官方解释是这样的:a log message will be written to printer at the beginning and ending of each message dispatch, identifying the target Handler and message contents.

给主线程的消息队列设置日志打印类 Looper.getMainLooper().setMessageLogging(mMonitorCore) 消息队列处理消息时,每隔300ms采集一次堆栈信息,子线程中采集 采集堆栈信息方法,见下方代码块 卡顿阈值:200ms,该值可以修改成符合实际情况的值(字段:BLOCK_THRESHOLD_MILLIS) 信息卡顿通知,略 卡顿列表最多收集50条数据,超过之后把index=0的挤掉

小结:其实消息的开始、结束日志一直在收集,只不过当检测出卡顿之后才把这条信息的日志当成卡顿日志记录下来。

检测UI层级

根据activity获取DecorView,递归遍历子view,直到子view是View类型返回

递归的层级就是该子View的层级号layerNumber

计操作数View在屏幕上的位置

计操作数view的id,但是我这里使用时发现view.getId一直是-1,这个问题待查。

子View绘制耗时,未实现。所以暂时无法计算出子View的绘制时间。

不过层级结构应该是准的,我数了一下ActivityBookShelf有20层,和收集的数据匹配。

ActivityBookShelf层级结构20层

函数耗时原理

https://juejin.im/post/6844904154624688136

Activity启动耗时统计方案 https://juejin.im/post/6844903935912722439

字节码插桩

字节码插桩采坑笔记      https://juejin.im/post/6844903573331902472

【Android】函数插桩(Gradle + ASM)   https://www.jianshu.com/p/16ed4d233fd1

后续规划

修复内存泄露

ANR检测

性能监控平台可以全面覆盖iReader的各项性能表现了,除了ANR检测。 目前开发阶段的ANR检测还停留在测试同学主动报告的层次,在线的ANR也只是在BETA阶段检测,覆盖的范围有限。

其实优化完其他性能指针之后,ANR的问题就会成为iReader的性能瓶颈,需要一套检测上报机制。

而性能监控平台的服务端很适合保存、展示上报的这些ANR数据。 使用ASM库具备了插桩能力之后,就可以进行全局无痕埋点开发了。

性能监控平台支持的功能

客户端DoKit功能介绍 客户端项目地址 git@192.168.6.99:android_ireader/dokit.git

支持的客户端类型

安卓端 ios端(未集成) 微信小程序(未集成)

一、常用工具

  • App信息查看: 快速查看手机信息,App 基础信息、签名相关、权限信息的渠道,避免去手机设置查找或者查看项目原代码的麻烦;
  • 开发者选项: 一键跳转开发者选项,避免安卓由于平台差异导致的入口不一致(Android独有)
  • 仿真弱网: 限制网速,仿真弱网环境下App的运行情况。(android独有)
  • 本地语言: 一键跳转本地语言,避免安卓由于平台差异导致的入口不一致
  • 沙盒浏览: App 内部文件浏览的功能,支持删除和预览, 并且能通过 AirDrop 或者其他分享方式上传到 PC 中,进行更加细致的操作;
  • MockGPS: App 能定位到全国各地,支持地图地位和手动输入经纬度;
  • Crash查看: 方便本地打印出出现 Crash 的堆栈;
  • 清除本地数据: 一键删除沙盒中所有数据;
  • DBView: 通过网页方便快捷的操作应用内数据库,让数据库的调试变得非常优雅;
  • Lumberjack: 每一条 CocoaLumberjack 的日志信息,都在在 App 的接口中显示出来,再也不需要导出日志这么麻烦;(iOS独有)
  • 子线程UI: 快速定位哪一些 UI 操作在非主线程中进行渲染,避免不必要的问题;(iOS独有)
  • NSLog: 把所有 NSLog 信息打印到UI接口,避免没有开发证书无法调试的尴尬;

二、业务功能区

开发者:张宝全

业务专区目前有8个功能:

  1. 页面路径:以浮窗的形式显示当前接口所在的位置,是主工程还是插件,若是插件,则显示当前插件名称,同时表明当前接口所在的路基信息。

  2. APP信息:显示当前APP的基本信息,手机硬件、系统信息

  3. 插件信息:显示当前已经安装的所有插件信息

  4. 任务查看:根据任务号,可查看当前任务信息,例如输入:9,可以查看9号任务信息。

  5. DG设置:跳转DG设置接口

  6. 日夜切换:日夜间切换的入口,方便调试(后续支持暗色切换)

  7. 广告辅助:可以查看当前广告总排期,设置当前开屏广告的冷、热启动间隔时间

  8. 任意门:

  • 支持APP 内任意跳转 ,可配置跳转任意插件。

  • 支持H5跳转,支持手动输入任意H5链接、二维码扫描链接,任意跳转应用内、外。

  • 支持DeepLink 跳转。

后续支持:

1、支持自定义ADB 命令运行。

2、支持掌阅基本弹窗样式示例。

3、接口数据记录(例如记录最近二十次网络数据的请求参数、结果等)方便追查测试阶段由接口数据异常导致的问题。

三、性能检测

帧率: App 帧率信息提供波形图查看功能,让帧率监控的趋势更加明显; CPU: App CPU 使用率信息提供波形图查看功能,让 CPU 监控的趋势更加形象; 内存: App 内存使用量信息提供波形图查看功能,让内存监控的趋势更加鲜明; 流量监控: 拦截 App 内部流量信息,提供波形图展示、流量概要展示、流量列表展示、流量筛选、流量详情,对流量信息统一拦截,成为我们 App 中自带 "Charle:"; 卡顿: 锁定 App 出现卡顿的时刻,打印出对应的代码调用堆栈; 大图检测: 通过流量监测,找出所有的大小超标的图片,避免下载大图造成的流量浪费和渲染大图带来的CPU消耗。 启动耗时: 无侵入的统计出App启动过程的总共耗时; UI层级检查: 检查出每一个页面中层级最深的元素; 函数耗时: 从函数级别分析app性能瓶颈; 内存泄漏: 找出App中所有的内存泄漏的问题。(支持iReader的Fragment内存泄露检测) 数据Mock: App接口Mock解决方案,提供一套基于App网络拦截的接口Mock方案,无需修改代码即可完成对于接口数据的Mock。 健康体检: 一键式操作,集成DoKit多项工具,数据可视化,快速准确定位问题,让你对app的性能了如指掌: Load: 找出所有的Load方法,并给出耗时分析;(iOS独有)

四、视觉工具

颜色吸管: 方便设计师 UI 捉虫的时候,查看每一个组件的颜色值是否设置正确; 组件检查: 可以抓取任意一个UI控件,查看它们的详细信息,包括控件名称、控件位置、背景色、字体颜色、字体大小; 对齐标尺: 参考 Android 系统自带测试工具,能够实时捕获屏幕座标,并且可以查看组件是否对齐; 元素边框线: 绘制出每一个 UI 组件的边框,对于组件布局有一定的参考意义。

五、Weex专项工具(CML专项工具)(暂未集成)

console日志查看: 方便在端上查看每一个Weex文件中的console日志,提供分级和搜索功能; storage缓存查看: 将Weex中的storage模块的本地缓存数据可视化展示; 容器信息: 查看每一个打开的Weex页面的基本信息和性能数据; DevTool: 快速打开Weex DevTool的扫码入口。

六、微信小程序专项工具(暂未集成)

支持微信小程序性能检测

七、性能优化平台的后续规划

修复内存泄露 升级Glide版本到4.9.0 支持Fragment生命周期检测,关闭Fragment时及时回收内存 ANR检测 性能监控平台可以全面覆盖iReader的各项性能表现了,除了ANR检测。 目前开发阶段的ANR检测还停留在测试同学主动报告的层次,在线的ANR也只是在BETA阶段检测,覆盖的范围有限。 其实优化完其他性能指针之后,ANR的问题就会成为iReader的性能瓶颈,需要一套检测上报机制。 而性能监控平台的服务端很适合保存、展示上报的这些ANR数据。 使用ASM库具备了插桩能力之后,就可以进行全局无痕埋点开发了。

服务端DoKit功能介绍

开发者:张政

web端项目地址:git@192.168.6.99:android_ireader/DokitWeb.git

服务端项目地址:git@192.168.6.99:android_ireader/DokitServer.git

管理后台地址:http://www.maam.work/#/detail

服务端支持以下客户端类型上报的数据

安卓端 ios端(未集成) 微信小程序(未集成) 服务端可以查看的功能介绍

v1.0.0版本只支持健康体检功能。打开管理后台之后,效果如下图所示。

列表中每一条数据展示了特定的一台测试机上传的性能参数数据。点击右边的操作按钮可以查看详情。详情里包含了健康体检的功能,详细介绍见下文条目一。

目前健康体检数据只支持安卓客户端上报,客户端代码分支:feature/7.35.0_apm。

目前该功能还在分支上,供感兴趣的同学体验,后续会合并入develop分支。

客户端性能数据上报的频率目前是1小时一次。时间间隔不能太短,否则造成手机的性能数据不全面。上传成功之后会自动删除缓存,避免重复上传。

目前部分功能是关闭的,比如内存泄露检测、启动耗时等,关闭的原因是为了避免对测试同学的正常测试产生干扰。

内存泄露检测、启动耗时等性能可以自行打开使用。

一、健康体检功能

1)启动时长查看 :查看app启动方法耗时

2)帧率 : 查看app启动过程中帧率变化情况

3)cpu运行状况:查看手机cpu占用情况

4)网络请求流量情况:查看接口消耗流量

5)内存运行状况:查看app运行时内存变化

6)页面运行时长:查看使用期间页面停留时长

7)大文件列表:查看app存在的大文件

二、后续规划

展示接入性能监控的设备信息列表 数据Mock模块 账号权限管理 基于上传的数据生成性能指针月报,查看性能优化的走势