介紹
多渠道打包常規方式有兩種,Flavor
和 --dart-define
,後者是 Flutter1.17
新增的命令行可選參數,比Flavor
配置更簡單,非常適合用於環境配置
運行命令:
flutter run --dart-define=DARTDEFINE_APP_ENV=debug
通常爲了區分不同的環境,會在測試和開發的apk名字後添加後綴,而且不同開發環境對應不同接口環境。所以以標題、域名和後綴作爲要更改的環境變量,開始 --dart-define
配置之旅。
Flutter 配置
環境配置
新建一個環境配置文件,用來獲取不同的環境變量。
// 環境配置
class EnvConfig {
final String appTitle;
final String appDomain;
EnvConfig({
required this.appTitle,
required this.appDomain,
});
}
// 獲取的配置信息
class Env {
// 獲取到當前環境
static const appEnv = String.fromEnvironment(EnvName.envKey);
// 開發環境
static final EnvConfig _debugConfig = EnvConfig(
appTitle: "debugTitle",
appDomain: "http://www.debugxxx.com",
);
// 發佈環境
static final EnvConfig _releaseConfig = EnvConfig(
appTitle: "releaseTitle",
appDomain: "http://www.releasexxx.com",
);
// 測試環境
static final EnvConfig _testConfig = EnvConfig(
appTitle: "testTitle",
appDomain: "http://www.testxxx.com",
);
static EnvConfig get envConfig => _getEnvConfig();
// 根據不同環境返回對應的環境配置
static EnvConfig _getEnvConfig() {
switch (appEnv) {
case EnvName.debug:
return _debugConfig;
case EnvName.release:
return _releaseConfig;
case EnvName.test:
return _testConfig;
default:
return _debugConfig;
}
}
}
// 聲明的環境
abstract class EnvName {
// 環境key
static const String envKey = "DART_DEFINE_APP_ENV";
// 環境value
static const String debug = "debug";
static const String release = "release";
static const String test = "test";
}
在EnvName
裏聲明瞭三個環境,這是運行命令和打包命令裏要填寫的值。envKey
是對應的key
。
使用配置
在main
文件裏使用前面配置的值,標題使用配置的標題,在頁面中顯示配置的域名:
return Scaffold(
appBar: AppBar(
title: Text(Env.envConfig.appTitle),
),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: <Widget>[
Text(
'配置的域名是:',
),
Text(
Env.envConfig.appDomain,
style: Theme.of(context).textTheme.headline4,
),
],
),
),
);
運行
在終端輸入命令,先運行debug
環境:
flutter run --dart-define=DART_DEFINE_APP_ENV=debug
注意,這裏的DART_DEFINE_APP_ENV
和debug
是和env_config
裏的對應的。
標題和域名是Env
裏配置的對應debug
的參數。
然後運行test
環境:
flutter run --dart-define=DART_DEFINE_APP_ENV=test
IDE配置
命令行容易輸錯怎麼辦?那就配置 IDE 。
- 點擊菜單上的編輯配置
- 輸入命令:
- 添加
test
的配置:
複製了一份,命名爲test
,把參數改爲test
- 繼續複製一份
release
。
然後要運行哪個環境,選擇對應的配置即可。
Android 配置
不僅僅在 dart 文件裏使用到配置信息,原生代碼也使用到,比如配置推送和bugly,另外測試人員爲了區分環境也會要求在配置不同的應用名稱後綴,那麼就需要在原生代碼裏修改。
在build.gradle
裏設置默認配置參數
// android/app/build.gradle
/// 設置默認配置參數
def dartDefine = [
DARTDEFINE_APP_ENV: 'debug',
]
然後從dart-defines
裏獲取定義的鍵值對,添加到dartEnv
裏。
// android/app/build.gradle
/// 設置默認配置參數
def dartDefine = [
DART_DEFINE_APP_ENV: 'debug',
]
if (project.hasProperty('dart-defines')) {
dartDefine = dartDefine + project.property('dart-defines')
.split(',')
.collectEntries { entry ->
def pair = URLDecoder.decode(entry).split('=')
[(pair.first()): pair.last()]
}
}
定義 resValue
,或者BuildConfig
,這裏因爲要改應用名,需要引用string
資源,所以用 resValue
:
defaultConfig {
applicationId "com.example.flutter_flavors"
minSdkVersion 16
targetSdkVersion 30
versionCode flutterVersionCode.toInteger()
versionName flutterVersionName
resValue "string","app_name","flutter_flavor${dartEnv.DART_DEFINE_APP_ENV}"
}
在清單文件引用:
<application
android:label="@string/app_name"
android:icon="@mipmap/ic_launcher">
每次運行不同的環境,就可以看到不同的應用名字。在代碼裏也可以通過getString("app_name")
獲取到定義的值。
Ios 配置
右鍵項目,選擇在 xcode 裏打開:
右鍵 Flutter 目錄選擇 new flie,選擇如下所示的類型。填入名稱 Dart
:
添加默認值:
DART_DEFINE_APP_ENV=flutter_flavor
在 Debug.xcconfig 和 Release.xcconfig 裏分別添加引用:
#include "DartDefine.xcconfig"
#include "DartDefineConfig.xcconfig"
第一行是引用我們創建的配置文件,第二行是在編譯時生成的(下一步配置生成代碼)。
在 Info 裏修改Bundle name
爲我們配置的值:
編輯Schema:
這裏有兩個地方需要注意,上面要選中 Runner ,下面的輸出文件名稱要和上一步引用的一致。
到此 Ios 也配置完成。選擇 test 配置運行:
應用名變成了選擇的配置。
打包
打包命令和運行命令的後綴一樣:
flutter build apk --dart-define=DARTDEFINE_APP_ENV=release
源碼
Flutter 環境:
Doctor summary (to see all details, run flutter doctor -v):
[✓] Flutter (Channel stable, 2.0.5, on Mac OS X 10.15.6 19G2021 darwin-x64,
locale zh-Hans-CN)
[✓] Android toolchain - develop for Android devices (Android SDK version 30.0.3)
[✓] Xcode - develop for iOS and macOS
[✓] Chrome - develop for the web
[✓] Android Studio (version 4.2)
[✓] VS Code (version 1.56.0)
[✓] Connected device (2 available)