381просмотров
4 марта 2026 г.
Score: 419
👣 Настройка окружений во Flutter приложении с помощью Flavors Когда приложение выходит за пределы пет-проекта, возникает необходимость держать окружения раздельно. Dev, Staging и Production должны жить своей жизнью: с разными API-ключами, бэкендом, а иногда даже иконками и названиями. В Flutter эта задача решается через Flavors. Рассказываю, как настроить и не запутаться. Что такое Flavors и зачем они нужны: Flavors (или схемы в iOS, продуктные варианты в Android) позволяют из одной кодовой базы собирать разные варианты приложения. У каждого варианта могут быть свои: 🔵URL бэкенда и ключи API. 🔵Имя приложения и bundle ID. 🔵Иконки и сплеш-скрины. 🔵Настройки сборки и зависимости. Это дает возможность установить на устройство одновременно dev-версию и продовую, не боясь, что они перезатрут друг друга. И главное - исключает случайную отправку тестового кода в релиз. Организация кода: Самый простой способ - сделать отдельные точки входа для каждого окружения. В папке lib создаем файлы: 🔵main_dev.dart 🔵main_staging.dart 🔵main_prod.dart В каждом передаем в приложение идентификатор среды, чтобы внутри можно было подставлять нужные конфиги. void main() { runApp(MyApp(environment: 'DEV'));
} Android - настройка productFlavors: В android/app/build.gradle добавляем секцию: flavorDimensions "default"
productFlavors { dev { dimension "default" applicationIdSuffix ".dev" versionNameSuffix "-dev" } staging { dimension "default" applicationIdSuffix ".staging" versionNameSuffix "-staging" } production { dimension "default" }
} Это даст разные имена пакетов: .dev, .staging и основное. Приложения не будут конфликтовать при установке. iOS - схемы и бандлы: В Xcode нужно продублировать схему Runner для каждого окружения и задать разные идентификаторы бандла в настройках таргета. Например: 🔵com.example.app.dev 🔵com.example.app.staging 🔵com.example.app В Info.plist можно выставить разные названия приложений, чтобы в меню было видно, какая версия запущена. Запуск и сборка: Для запуска нужного flavor используем флаги: flutter run --flavor dev -t lib/main_dev.dart
flutter build apk --flavor prod -t lib/main_prod.dart
flutter build ios --flavor staging -t lib/main_staging.dart Управление конфигурацией: Внутри кода удобно сделать класс с константами для каждого окружения: class AppConfig { static const Map<String, String> apiUrls = { 'DEV': 'https://dev.api.example.com', 'STAGING': 'https://staging.api.example.com', 'PROD': 'https://api.example.com', };
} А в приложении просто обращаться по ключу, который пришел из main-файла. Иконки для каждого flavor: Пакет flutter_launcher_icons умеет генерировать иконки под разные flavors. В pubspec.yaml прописываем: flutter_launcher_icons: flavors: dev: image_path: "assets/icons/dev_icon.png" staging: image_path: "assets/icons/staging_icon.png" production: image_path: "assets/icons/prod_icon.png" Запускаем и получаем разные иконки для каждого окружения. Лучшие практики: 🔵Не храните ключи и секреты прямо в коде. Используйте .env файлы или безопасное хранилище. 🔵Ведите имена flavors одинаково на Android и iOS - меньше путаницы. 🔵Настройте CI/CD так, чтобы пайплайны собирали каждый flavor отдельно. 🔵Для тестировщиков dev-сборка должна визуально отличаться (иконка, цвет темы), чтобы случайно не перепутали с продакшеном. 🔗 Ссылка на подробную статью 💡 Вывод: Flavors - это не про «сделать красиво», а про контроль и безопасность. Правильная настройка окружений убережет от случайных деплоев с тестовыми данными и позволит команде спокойно работать, не боясь что-то сломать в бою. Один раз настроив, вы сэкономите часы нервотрепки и багов на пустом месте. ➡️ Flutter & Dart | Мобильный трудоголик