解决方案:iOS应用性能数据采集原理和优化实践 | 详细版

优采云 发布时间: 2022-11-15 22:51

  解决方案:iOS应用性能数据采集原理和优化实践 | 详细版

  关于作者

  Alvin Liu,Cloud Wisdom/开发经理。在高德、当当有多年大型App开发经验,在云知汇从事APM SDK研发5年多。对App开发和性能优化有深入研究和实践。

  iOS应用数据的基本Objective-C Runtime1和消息转发 采集

  Objective-C 语言扩展了 C 语言。扩展的核心在于Runtime库的引入,使得Objective-C语言具有面向对象和动态运行时的特点。动态运行时机制的核心和表现是消息转发机制。

  Objective-C语言具有动态的运行时机制,方法的执行是在运行时而不是在编译阶段决定的。方法执行的本质是向对象发送消息。官方API是

  objc_msgSend(void /* id self, SEL op, ... */ )

复制代码

  objc_msgSend有两个公共参数:id self和SEL op,用于标识对象和方法,即向一个对象发送消息。因此,Objective-C的[实例方法]调用会被编译器转换成C语言API objc_msgSend的调用。

  以下消息转发机制*敏*感*词*翻译自官方文档:

  消息转发机制示例图

  如上图所示,在Objective-C的消息转发过程中,当在当前对象方法列表中找不到该方法的实现时,运行环境会依次分三个阶段进行查找

  第一阶段

  当一个对象收到无法处理的消息时,它首先调用它所属类的以下类方法。

  +(BOOL)resolveInstanceMethod:(SEL)sel{

//默认返回NO

return NO;

}

+(BOOL)resolveClassMethod:(SEL)sel{

//默认返回NO

return NO;

}

复制代码

  

  如果在其中找到方法的实现,则进行消息处理;否则进入第二阶段。

  第二阶段

  当在当前类中找不到该方法的实现时,运行时系统会尝试替换调用的对象,会调用下面的方法

  -(id)forwardingTargetForSelector:(SEL)aSelector{}

复制代码

  如果在本方法中找不到该方法的实现,则进入第三阶段。

  第三阶段

  这是最后一个阶段。通过创建一个 NSInvocation 实例,封装了与未处理消息相关的细节。运行时系统调用的接口是

  -(void)forwardInvocation:(NSInvocation *)anInvocation{}

复制代码

  这个方法会沿着类的继承链一直向上调用,直到在 NSObject 的这个方法中抛出 doesNotRecognizeSelector: 异常。

  2.函数指针

  SEL是Objective-C语言的方法选择器,也就是选择器的指针。再往下看,每个方法SEL也对应一个IMP函数指针,指向方法实现的首地址。官方API是:

  typedef id (*IMP)(id, SEL, ...);

复制代码

  有了它,就可以直接执行IMP指向的函数(方法)了。

  上面介绍了理论基础,下面介绍基于Objective-C语言动态运行时的方法拦截(Hook)操作。

  挂钩原理

  Hook步骤使用Category特性为类添加拦截方法SEL使用系统运行时的接口(Swizzle)交换方法实现(IMP) Hook使用示例图

  如图所示,当开发者调用原方法时,会转发给被拦截的方法。因为交换了原方法和拦截方法的入口地址(IMP),所以当拦截方法执行时可以回调原方法。对业务没有影响。

  钩子回调函数

  难点:不是类的实例方法,无法使用Category特性。

  优化前:扫描整个项目,然后拦截。

  缺点:只能在主线程中操作,扫描文件数量和耗时与App大小成正比。

  回调函数拦截优化

  步:

  对于会使用协议的系统类,利用Category特性添加拦截方法,拦截委托的setter方法,获取委托的实例,然后拦截获取到的委托实例的回调方法

  

  优化

  1.延迟拦截:只在方法调用时才拦截,并且只拦截一次

  2、SDK的启动运行与App的业务和规模无关,对App的影响降到最低

  崩溃解码练习

  目的:了解iOS崩溃解码原理

  崩溃解码步骤 Virtual memory offset: 145624->0x238d8->0x238d8 使用dwarfdump命令将dSYM文件解析成可读文件

  dwarfdum-e–debug-info 收录所有类和方法的代码和地址映射信息 -> 信息文件

  dwarfdum-e--debug-line 收录所有类的代码行号和地址映射信息 -> 行号文件

  在信息文件中找到offset所在的类和方法,得到崩溃的类和对应的方法。在行号文件中找到offset所在的行号,得到crash行号的具体虚拟内存偏移量:

  0x238d8

  dSYM文件分析命令symbolicatecrash->全文分析atos(mac)/atosl(linux)->单行分析H5页面监控原理

  以上介绍了系统原生接口的数据采集原理,下面介绍H5页面数据采集的实现原理。

  H5页面数据采集是通过在H5页面自动注入JS代码实现的。流程如下图所示

  H5页面注入JS代码*敏*感*词*

  如上图所示,在UIWebView时代,通过NSURLProtocol协议簇的接口,拦截加载页面数据的接口,获取H5数据块,检测数据块中的标签,JS代码被注入其中。这样JS代码就会和H5页面代码一起加载协同工作,你可以采集获取H5页面的相关信息。JS代码采集收到信息后,通过iframe触发UIWebView的回调,将信息发送到原生SDK端进行存储和上报。

  在WKWebView时代,由于WKWebView是一个单独的进程,所以在App中无法从系统的网络协议集群中获取WKWebView的数据。可以通过拦截WKWebView的回调函数来执行JS代码,可以达到和UIWebView采集数据一样的效果。这里我就不细说了。

  PS:JS代码的工作原理是另一个技术领域的范畴,这里就不赘述了。

  写在最后

  近年来,在AIOps领域快速发展的背景下,各个行业对IT工具、平台能力、解决方案、AI场景和可用数据集的迫切需求呈爆发式增长。基于此,云智于2021年8月发布了AIOps社区,旨在竖起开源大旗,为各行业的客户、用户、研究人员和开发者打造一个活跃的用户和开发者社区,共同贡献和解决行业问题。问题,促进该领域的技术发展。

  社区先后开源了数据可视化编排平台——FlyFish、运维管理平台OMP、云服务管理平台——Moore平台、Hours算法等产品。

  项目介绍:…

  Github地址:/CloudWise-O...

  Gitee地址:/CloudWise/f...

  欢迎通过下方链接了解我们,添加小助手微信(xiaoyuerwie),备注:飞鱼。申请加入开发者交流群,与行业大咖1V1交流!

  您也可以联系我们了解云智AIOps信息,了解云智开源社区其他项目的开源情况!

  操作方法:优采云采集器功能介绍和使用技巧

  优采云采集器是一款非常好用的互联网爬虫工具,用VisualC#编写,专业用于互联网数据的抓取、分析、处理和挖掘。软件绿色安全,安装方便。主要用于网络数据处理,可以快速灵活地抓取网页中大量的非结构化文本。优采云采集器提供一站式高效的采集服务,通过一系列的分析处理支持多种类型的数据库,使用多线程采集方法精准挖掘需要的数据,其强大的识别系统积累了大量的用户和良好的口碑,能够准确识别各种编码字符,满足不同的数据处理需求。

  优采云采集器功能介绍及使用技巧图1

  优采云采集器菜单功能介绍:

  优采云采集器功能介绍及使用技巧图2

  1.创建一个新组

  

  选择它所属的组,创建一个新的任务组,并确定组名和注释。

  2.新任务

  新建任务,确定所属组,填写任务名称并保存。

  3. Web发布配置

  定义登录到 网站 并向该 网站 提交数据。涉及网站编码设置、登录信息的获取、栏目列表的获取。

  4. 网页发布模块

  获取栏目列表,可以定义网站登录,获取网页随机值,内容发布参数,构造发布数据等高级功能。

  5.数据库发布配置

  

  定义数据库链接信息的设置和数据库模块的选择。

  6.数据库发布模块

  用于编辑数据库的发布模块,优采云采集器可以选择四种数据库类型,方便我们将数据发布到配置好的数据库中。加载到采集器模块文件夹中,在文本输入框中填写sql语句。

  7.安排任务

  在列表中设置采集任务的启动计划。保存设置后,即可根据设置执行任务。

  8.插件管理

  插件是可以用来扩展优采云采集器功能的程序,支持三种插件,可以用来扩展http请求,可以单独测试。

0 个评论

要回复文章请先登录注册


官方客服QQ群

微信人工客服

QQ人工客服


线