1. 集成方式选择
官方提供了源码集成方式,详细见文章Add Flutter to existing apps。
该方式有一个问题,Native工程和Flutter工程耦合性强,Native开发人员必须安装Flutter运行环境,才能运行真个工程,CI构建机上也要求有Flutter环境。更好的办法是将Flutter工程生成的产物集成进Native工程里,这样Native工程可以脱离Flutter环境运行。
经过调研和参考,我们的项目用了源码集成和私有库相结合的方式:
Flutter开发阶段,以源码方式引入,方便代码调试和快速查看效果。
编写构建脚本,脚本根据环境生成Debug和Release两个不同版本的构建产物,分别放在FlutterFrameworkDebug和FlutterFrameworkRelease私有库中。
Native开发人员以Pod私有库方式,将Flutter产物引入原生工程,线上版本同样以Pod私有库方式引入。
该集成方式很好的弥补了代码集成方式的缺点。Podflie的编写如下:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 |
|
通过修改IsFlutterSourceCode开关配置集成方式。
接下来介绍私有库产物的收集方法。
2. Flutter产物收集
产物收集分为三个部分,App.framework、Flutter.framework、Plugin(包括Plugin.h和Plugin.a文件)。
framework的收集分为Debug版本和Release版本,收集Debug版本前需要以源码模式先运行工程一次,收集Release版本前需要先执行flutter build ios
,这样对应的产物才能生成。
2.1 App.framework
App.framework是逻辑代码。
文件位置:
Debug版本:$TIP_FLUTTER_HOME/.ios/Flutter/App.framework
Release版本:$TIP_FLUTTER_HOME/build/ios/iphoneos/Runner.app/Frameworks/App.framework
2.2 Flutter.framework
Flutter.framework是引擎代码。
文件位置:
Debug版本:$TIP_FLUTTER_HOME/.ios/Flutter/engine/Flutter.framework
Release版本:$FLUTTER_HOME/bin/cache/artifacts/engine/ios-release/Flutter.framework
2.3 Plugin
为了减少复杂度,Plugin产物没有区分Debug版本和Release版本。
根据.flutter-plugins
文件的内容分析用到了哪些plugin。
例如文件内容如下:
1 2 3 |
|
可以分析出来三个plugin,分别是flutter_mmkv_cache
,path_provider
,sqflite
。
还不止这些,plugin可能会依赖native库,还需要进一步分析。
以flutter_mmkv_cache
为例,查看podspec文件,位置在/Users/junshao/Documents/Code/Flutter/flutter/.pub-cache/hosted/pub.dartlang.org/flutter_mmkv_cache-0.0.2/ios
,文件中有依赖的native库:
1 2 |
|
除去Flutter
本身,MMKV
就是需要依赖的native库。
分析完所有plugin和依赖库后,开始构建plugin。需要针对模拟器和真机分别构建.a文件,然后将两个.a文件合并。相关命令如下:
1 2 3 |
|
这样就得到了plugin的产物.h和.a文件。
3. 遗留问题
分析Plugin的依赖时,如果native工程里已有,会造成冲突。例如flutter_mmkv_cache
需要依赖MMKV
,但是以前的native工程也依赖了MMKV
,会导致库重复编译不过。目前我们的做法是,去掉native工程的MMKV
。有更好的方法欢迎指正。