Injectionlll 快速调试工具

使Xcode可以进行运行时调试功能的工具,可以理解为把项目变成了Playground。
本文主要针对戴铭专栏中“App 如何通过注入动态库的方式实现极速编译调试?”进行的总结。
注意:需要注意第4节中提到的问题,修改过多地方的话,尽量还是重启App来调试。

1 安装和使用

1-1 安装

最简单的方法是从App Store下载安装InjectionIII,想体验最新feature的也可以从github上下载源码injectionforxcode

1-2 配置

//appDelegate.m
- (BOOL)application:(UIApplication *)application didFinishLaunchingWithOptions:(NSDictionary *)launchOptions {
//...
[[NSBundle bundleWithPath:@"/Applications/InjectionIII.app/Contents/Resources/iOSInjection.bundle"] load];
return YES;
}

启动App后,会让我们选择项目路径,选择后就可以使用了。
修改后不会立刻生效,保存才能生效。
每次保存后,会自动调用当前controller的- (void)injected方法(如果重写了的话)。

1-3 查看修改

  1. 手动触发
    如点击效果:点一下。
    如布局变化,或网络请求:退出当前controller,再重新进入。
  2. 代码触发,在- (void)injected中手动调用
    如布局变了,或网络请求:- (void)injected中调用viewWillLayoutSubviews、发送网络请求。

2 原理

  1. 启动了一个Mac App监听项目目录下的文件变化,并与模拟器建立通信
  2. 项目目录下的文件发生变化后,就重新打包动态链接库(多个单文件对应多个dylib动态库)
  3. 项目中InjectionIII Client端,收到Server端(Mac App)打包完成的socket消息,加载dylib,并执行Xcode焦点所在.m文件的inject方法。

对于项目来说,只记录了动态链接库的名字和路径,而不需要重新编译和链接。
链接器都做了什么

3 注意事项

  1. 只对模拟器有效。
  2. 支持OC和Swift。
  3. 使用了cocoapods的项目,如果希望监听pod中源码的修改,需要设置Legacy Build System。

默认的New Build System(Default)模式,不编译pod 里面的改动
设置方法:File -> Workspace Setting -> Build System, 改为Legacy Build System模式。

  1. 监听另一个项目时,通过InjectionIII重新选择监听目录。
  2. 不要修改进行了swizzling的类,否则二次交换,会造成死循环。

4 值得注意的问题

  1. 不支持方法的删除:删除后,方法调用仍然有效,不抛异常。
  2. 不支持新增类:新增类引入后使用无效。但类的重命名是有效的。
  3. 属性新增、删除、修改:反射上体现不出来。

在我看来,

问题原因,可能与苹果动态库调用的实现有关,不是InjectionIII工具的问题。
因为这些问题在动态库打包时也会出现:修改动态库源码,不修改版本号,重新打包(清过缓存也一样)。
另外,问题原因应该与加载时机无关,虽然动态库的路径绑定是在main之前进行的,而Injection是在didLaunch中才加载的。但是重命名类有效,说明这个路径绑定是有效的。

你可能感兴趣的:(Injectionlll 快速调试工具)