Как собрать разные версии моего приложения Flutter для qa/dev/prod?
Я создаю приложение Flutter, и у меня есть переменные с разными значениями для разных сред (QA, dev, prod и т. Д.). Какой хороший способ организовать мое приложение, чтобы я мог легко сделать сборку для QA, dev, prod и других сред?
5 ответов
Один из способов сделать это: создать разные main_<environment>.dart
файлы в lib/
каталог вашего проекта.
каждый main_<environment>.dart
содержит специфичные для среды конфигурации / значения (например, имена разных баз данных и т. д.). каждый main_<environment>.dart
затем импортирует реальную библиотеку приложения и запускает приложение, передавая значения / конфигурации среды.
Затем выберите какой .dart
файл для сборки: flutter run -t lib/main_debug.dart
Основываясь на идее Сета, вот пример, который устанавливает глобальное представление BuildEnvironment
названный env
,
env.dart
import 'package:meta/meta.dart';
enum BuildFlavor { production, development, staging }
BuildEnvironment get env => _env;
BuildEnvironment _env;
class BuildEnvironment {
/// The backend server.
final String baseUrl;
final BuildFlavor flavor;
BuildEnvironment._init({this.flavor, this.baseUrl});
/// Sets up the top-level [env] getter on the first call only.
static void init({@required flavor, @required baseUrl}) =>
_env ??= BuildEnvironment._init(flavor: flavor, baseUrl: baseUrl);
}
main_dev.dart
import 'package:flutter/material.dart';
import 'env.dart';
import 'app.dart';
void main() {
BuildEnvironment.init(
flavor: BuildFlavor.development, baseUrl: 'http://dev.example.com');
assert(env != null);
runApp(App());
}
main_prod.dart
import 'package:flutter/material.dart';
import 'env.dart';
import 'app.dart';
void main() {
BuildEnvironment.init(
flavor: BuildFlavor.production, baseUrl: 'http://example.com');
assert(env != null);
runApp(App());
}
- Импортировать
env.dart
разоблачитьenv
переменная. запустить и собрать приложение, используя
target
вариант.flutter run -t lib/main_dev.dart flutter build -t lib/main_dev.dart
Для интеграции с VS Code определите конфигурации запуска:
.vscode / launch.json
{
"version": "0.2.0",
"configurations": [
{
"name": "development",
"program": "lib/main_dev.dart",
"request": "launch",
"type": "dart"
},
{
"name": "production",
"program": "lib/main_prod.dart",
"request": "launch",
"type": "dart"
}
]
}
Я изначально намеревался использовать аргументы командной строки, переданные Дартс main
функция, но я не думаю, что аргументы в настоящее время могут быть переданы в командной строке с flutter run
или же flutter build
, хотя VS Code и Android Studio поддерживают передачу аргументов в main
, Также кажется, что сборка в виде командной строки main
не подходит, так как аргументы могут быть переданы после процесса сборки.
Режим выпуска и отладки теперь можно получить с помощью
const bool isProduction = bool.fromEnvironment('dart.vm.product');
Поскольку это константа, она работает с тряской деревьев.
Так что код вроде
if(isProduction) {
// branch 1
} else {
// branch 2
}
будет включать только одну из этих двух ветвей в производственный код в зависимости от isProduction
Начиная с Flutter 1.17 вы можете использовать --dart-define
для создания приложения с разными переменными времени компиляции. Он работает как для Dart, так и для собственных слоев. В дротике эти значения можно получить с помощьюString.fromEnvironment
например. Таким образом, вам не нужно будет иметь тонны или точки входа и предоставлять учетные данные вашей среды.
Вот статья, которая объясняет больше https://link.medium.com/ibuTsWHrk6
import 'package:flutter/foundation.dart';
И используйте следующие значения const:
if (kReleaseMode) {
// App is running in release mode.
} else if (kProfileMode) {
// App is running in profile mode.
} else if (kDebugMode) {
// App is running in debug mode.
} else if (kIsWeb) {
// App is running on the web.
}
Более чистый способ сделать это - использовать Build Flavors.
В качестве быстрого примера, если вы хотите иметь другой идентификатор приложения для своего приложения для сборки "dev", вы можете указать это в файле gradle:
flavorDimensions "version"
productFlavors {
dev {
applicationIdSuffix ".dev"
versionNameSuffix "-dev"
}
}
Подробнее о конфигурации варианта сборки gradle здесь.
Теперь вы можете запустить этот вариант сборки с помощью командной строки:
flutter run --flavor dev
Если вы используете Android Studio, вы также можете указать вариант сборки в конфигурации запуска:
Подробнее о настройке iOS читайте в этом блоге. И официальная документация по флаттерам о вариантах сборки.
Просто вы можете реализовать варианты сборки.
В андроиде:
buildTypes {
release {
// TODO: Add your own signing config for the release build.
// Signing with the debug keys for now, so `flutter run --release` works.
signingConfig signingConfigs.release
}
debug{
applicationIdSuffix ".dev"
signingConfig signingConfigs.debug
}
qa{
applicationIdSuffix ".qa"
signingConfig signingConfigs.qa
}
}
В iOS:
добавить конфигурацию, выбрав проект-> бегун-> конфигурация добавить еще один
Дополнительная информация:
У меня была та же проблема, и я использовал решение, предложенное Сетом Лэддом. Поэтому я также нуждался в различной конфигурации для каждой версии приложения (dev / prod), и я не хочу записывать конфигурацию в файл main_dev.dart или main_prod.dart.
Я написал простой пакет флаттера, который имеет дело с разделением файлов конфигурации и загрузкой их при запуске приложения. Конфигурация будет доступна в каждой строке кода в вашем приложении.
https://github.com/Ephenodrom/Flutter-Global-Config
Как это использовать:
Создайте файл json в assets/cfg/$file.json
Добавьте assets / cfg в ваш pubspec.yaml
Загрузка различных файлов конфигурации при запуске приложения:
import 'package:flutter/material.dart';
import 'package:global_configuration/global_configuration.dart';
void main() async{
await GlobalConfiguration().loadFromAsset("app_settings");
await GlobalConfiguration().loadFromAsset("env_dev_settings");
runApp(MyApp());
}
class MyApp extends StatelessWidget {
...
}
Используя конфигурацию в вашем приложении:
import 'package:flutter/material.dart';
import 'package:global_configuration/global_configuration.dart';
class CustomWidget extends StatelessWidget {
CustomWiget(){
// Access the config in the constructor
print(GlobalConfiguration().getString("key1"); // prints value1
}
@override
Widget build(BuildContext context) {
// Access the config in the build method
return new Text(GlobalConfiguration().getString("key2"));
}
}
Создайте файл в корне проекта app_environment.dart
. ИспользоватьkReleaseMode
переменная от foundation.dart
пакет для проверки рабочего режима.
import 'package:flutter/foundation.dart';
class AppEnvironment {
String getApiURL() {
if (kReleaseMode) {
return 'PROD_API_URL';
} else {
return 'STAGING_API_URL';
}
}
}