在终端执行pod search Flutter
,会发现Flutter在CocoaPods里其实有多个版本,但是,默认情况下,只会选择1.0.0
所以我就在想,是否能由我们自己决定用哪个Flutter pod库的版本呢?
经过一番尝试,终于成功指定了Flutter pod库的版本,但是这个方案并未在正式的项目里使用,只是我个人的一次尝试
分析Podfile
pod库的版本是在Podfile
里配置的,所以这个时候,先分析一下Podfile
# 省略大部分Podfile代码,只看target的
target 'Runner' do
use_frameworks!
use_modular_headers!
flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__))
end
根据将Flutter module集成到iOS项目里关于使用 CocoaPods 和 Flutter SDK集成
猜测关键代码是flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__))
然后通过ruby的print语句(由于CocoaPods是由ruby实现的)找到了File.dirname
所返回的路径就是项目目录下的ios
之后根据Podfile
里target上面的一段代码,方法flutter_root
def flutter_root
generated_xcode_build_settings_path = File.expand_path(File.join('..', 'Flutter', 'Generated.xcconfig'), __FILE__)
unless File.exist?(generated_xcode_build_settings_path)
raise "#{generated_xcode_build_settings_path} must exist. If you're running pod install manually, make sure flutter pub get is executed first"
end
File.foreach(generated_xcode_build_settings_path) do |line|
matches = line.match(/FLUTTER_ROOT\=(.*)/)
return matches[1].strip if matches
end
raise "FLUTTER_ROOT not found in #{generated_xcode_build_settings_path}. Try deleting Generated.xcconfig, then run flutter pub get"
end
require File.expand_path(File.join('packages', 'flutter_tools', 'bin', 'podhelper'), flutter_root)
分析到一个文件路径flutter/packages/flutter_tools/bin/podhelper
(这个flutter就是Flutter SDK存放路径,即环境变量FLUTTER_HOME指定的路径),打开这个文件可以看到很多代码。通过搜索Flutter
找到以下代码
# Generate a fake podspec to represent the Flutter framework.
# This is only necessary because plugin podspecs contain `s.dependency 'Flutter'`, and if this Podfile
# does not add a `pod 'Flutter'` CocoaPods will try to download it from the CocoaPods trunk.
File.open(copied_podspec_path, 'w') { |podspec|
podspec.write <<~EOF
#
# NOTE: This podspec is NOT to be published. It is only used as a local source!
# This is a generated file; do not edit or check into version control.
#
Pod::Spec.new do |s|
s.name = 'Flutter'
s.version = '1.0.0'
s.summary = 'High-performance, high-fidelity mobile apps.'
s.homepage = 'https://flutter.io'
s.license = { :type => 'MIT' }
s.author = { 'Flutter Dev Team' => 'flutter-dev@googlegroups.com' }
s.source = { :git => 'https://github.com/flutter/engine', :tag => s.version.to_s }
s.ios.deployment_target = '9.0'
# Framework linking is handled by Flutter tooling, not CocoaPods.
# Add a placeholder to satisfy `s.dependency 'Flutter'` plugin podspecs.
s.vendored_frameworks = 'path/to/nothing'
end
EOF
}
# Keep pod path relative so it can be checked into Podfile.lock.
pod 'Flutter', :path => 'Flutter'
尝试修改s.version = '1.0.0'
为s.version = '2.0.2'
再执行pod install
成功了
这里只修改了iOS
部分,其实文件里还有macOS
部分,也是直接修改s.version
就可以了
指定podhelper
的路径
经过一番折腾,终于找到了关键的podhelper.rb
文件,但这个文件在Flutter SDK里,修改了,以后所有项目都有生效,那是否能只对当前项目有效呢?通过之前的分析,发现其实可以通过修改Podfile
文件里的路径,就可以指定podhelper
的路径
首先,我将flutter/packages/flutter_tools/bin/podhelper.rb
拷贝到当前项目目录下的ios
目录,和Podfile
是同级的
然后修改Podfile
的内容,内容如下
# Uncomment this line to define a global platform for your project
# platform :ios, '9.0'
# CocoaPods analytics sends network stats synchronously affecting flutter build latency.
ENV['COCOAPODS_DISABLE_STATS'] = 'true'
project 'Runner', {
'Debug' => :debug,
'Profile' => :release,
'Release' => :release,
}
# 将flutter_root方法的代码移除,这个只是用来返回Flutter SDK路径的
# 这句是核心,这个是加载podhelper的路径
require File.expand_path(File.join('podhelper'))
flutter_ios_podfile_setup
target 'Runner' do
use_frameworks!
use_modular_headers!
flutter_install_all_ios_pods File.dirname(File.realpath(__FILE__))
end
post_install do |installer|
installer.pods_project.targets.each do |target|
flutter_additional_ios_build_settings(target)
end
end
然后执行pod install
,发现报错了,原来光修改Podfile
是不行的,这样会导致podhelper.rb
里的路径不对,所以还要对当前项目目录下ios
里的podhelper.rb
进行修改
在podhelper.rb
里搜索artifacts_dir =
artifacts_dir = File.join('..', '..', '..', '..', 'bin', 'cache', 'artifacts', 'engine')
# 将上面这句代码修改为下面这样
artifacts_dir = File.expand_path(File.join('bin', 'cache', 'artifacts', 'engine'),flutter_root)
# 同时加入flutter_root方法加入到podhelper.rb里flutter_additional_ios_build_settings方法之前
搜索artifacts_dir =
其实有两个结果,一个是iOS
的,一个是macOS
的,大家按需修改或者两个都改好也可以
放上我修改好的Podfile
和podhelper.rb
供大家参考,传送门
版本环境
Flutter已经迭代到2.5.3了,我的这次尝试未必适合所有版本
以下是我的环境
macOS Big Sur (11.6.1)
Xcode Version 12.5.1 (12E507)
Flutter 2.5.3 • channel stable • https://github.com/flutter/flutter.git
Framework • revision 18116933e7 (2 weeks ago) • 2021-10-15 10:46:35 -0700
Engine • revision d3ea636dc5
Tools • Dart 2.14.4
pod --version
1.11.2
ruby --version
ruby 2.6.3p62 (2019-04-16 revision 67580) [universal.x86_64-darwin20]
gem --version
3.0.3