Framework: lazy symbol bind failed 解决记录

Framework: lazy symbol bind failed 解决记录

XCode Swift 兼容问题

XCode 支持Swift版本
9.2 3.2 / 4.0
9.3 3.3 / 4.1
10.0 3.0 / 4.0 / 4.2

Frameworks

  • MFNetworkingKit (link Alamofire)
  • Alamofire

设备Number说明

设备名称 XCode版本 OS版本
Service_A 10.1 (external) 10.14.2
Service_B 10.0 (external) 10.13.6
Client_A 10.0 (internal) 10.13.6
Client_B 10.0 (external) 10.13.6

: external 指的是从appstore下载的XCode, internal 指的是公司渠道获得Xcode

问题描述

客户基于CocoaPod 集成 Alamofire ~> 4.72 ,直接集成 MFNetworkingKit ~> 1.0.3

  • XCode9.2: 正常
  • XCode10.0: crash
    (注:Alamofire ~> 4.72 不支持Swift4.2, 4.7.3 支持)

detail errorinfo

dyld: lazy symbol bind failed: symbol not found: Alamofire_URLEncoding_destination

问题分析

  • Alamofire version 问题.

    解决方案: 在Service_A 更新 Alamofire ~> 4.7.3, 并且重新发布, Client_A 更新Alamofire 和 MFNetworking

    结果: lazy symbol bind failed

  • CocoaPod 集成问题
    解决方案: 放弃CocoaPod集成, 直接集成Alamofire
    结果: lazy symbol bind failed

事后分析:

  1. 不应该怀疑CocoaPod 的问题,这个有点浪费时间

    • 用户在没有更改CocoaPod配置的情况下,出现的问题
    • 如果没有集成成功的话,错误提示应是: load image failed
    • 这个更多的是基于主观揣测做的,非理性的,主要是CocoaPod用的少, 和对客户的 不信任以及对于自身产品的过于自信,出了问题首先想到的是客户使用姿势不对
  2. 和Swift版本没有太大关系, Swift版本引起更多的是编译错误

    一下代码可以在XCode10.0, 改变Swift version情况下看到编译错误

    
    //#if swift(>=4.2)
    //public typealias MFUIViewContentMode = UIView.ContentMode
    //#else
    public typealias MFUIViewContentMode = UIViewContentMode
    //#endif    
    
    

然后经过自己一段瞎折腾,成功了 fix bug 了,之所以说瞎折腾是因为并没有明确的计划做这件事情,对自己做了什么不是很清晰。然后传给了客户,告诉他已经成功了。

结果第二天客户过来说还是不行,没办法继续整,悲剧再次发生了,我居然无法重现上一天的成果,(注:我是拿的客户机子Client_A测试的, 没有使用git保护现场), 这个真的很伤,以后要记得保护现场。

  • align XCode: 紧急在Service_A 上加装了XCode10.0,并发布版本。结果还是不行

思来想去,只能从symbol入手了

  • compare symbol: 从Service_A和 Client_A 导出Alamofire 的dSYM文件,发现function symbol string存在细微的差异。

    • 验证: Client_A 使用 Service_A build 的 MFNetworking 和 Alamofire
    • 结果: ok ,一切正常
    • 结论:不同设备build Alamofire 产生的symbol 不一样。

解决方案

MFNetworking 和 Alamofire 统一由 Service_A build

客户反馈

解决方案不满意

  1. 增加使用成本: 需要改变Framwork集成方式 要从CocoaPod 迁移至其他方式集成
  2. 不稳定性担忧: 害怕其他产品也会出现类似的问题

结论不满意

不同设备build Alamofire 产生的symbol 不一样 这个结论太诡异有点不科学

重整旗鼓

  1. symbol 不一样是由于 external XCode 和 internal XCode差异造成的

    * 客户使用Client_B build Alamofire
    * 结果: crash
    

问题回到了原点: device 不一样导致symbol不一样, 现在已经出现了三台机 Service_A, Client_A,Client_B.
可以确定的是 Service_A 与 Client_A,Client_B 的 symbol 不一样,
不能确认 Client_A 和 Client_B 的 symbol是否一样。

原因

function symble 最后一位:

  • Service_A: u
  • Client_A:
  • Client_B:

这里主要不能确认这个符号是不是与编码一一对应。

于是想到多用几台机器验证一下,(如果每台 device 导致symbol不一样,那一定存在多种多样的symbol, 如果不是则必然存在某种不知的差异造成了确定性结果)

启用Service_B, build framework, 给Client_A 使用 这次居然成功了, Client_B 也正常, 最后想来想去可能是因为Service_B的OS 版本造成的。 要验证这个需要对Service_B 系统进行降级,就没有做了

结论

需要满足一下条件,方能保证发布方和客户方行为一致。

  • XCode Version
  • Dependence Frameworks Version
  • OS Version

你可能感兴趣的:(Framework: lazy symbol bind failed 解决记录)