flavor_cli 0.0.10
flavor_cli: ^0.0.10 copied to clipboard
A production-grade CLI tool for automating Flutter flavor configuration, Firebase environment management, and boilerplate generation for scalable apps.
🍹 Flavor CLI #
Transform any Flutter project into a multi-environment powerhouse in seconds.
flavor_cli is a production-grade automation tool that handles the heavy lifting of build flavor configuration. Stop manually editing build.gradle or Xcode schemes; focus on shipping features instead.
✨ Key Features #
🛡️ Resilient & Type-Safe #
- Zero-Guess Configuration: Auto-generates a type-safe
AppConfigclass with typed variables (String,bool,int,double). - ENV-Driven Runtime: Securely stores per-flavor values in
.env.<flavor>files, loaded at runtime viaflutter_dotenv. - Project Safety: Interactive
deleteandreplacecommands ensure your project remains buildable.replaceuses a pre-flight snapshot for atomic, rollback-capable renames. Revert instantly with aresetcommand. - Automatic Formatting: Integrated
dart formatensures all generated and modified files match your project's styling.
📦 Flexible Architecture #
- YAML Configuration: Uses
flavor_cli.yamlfor clear, readable project metadata. - Automatic Isolation: Automatically configures unique internal suffixes (e.g.,
.dev,.beta) to allow parallel app installations on the same device. - Smart Patterns: Seamlessly supports both the professional "Separate Mains" pattern and the classic "Single Main" approach.
- IDE Integration: Automatically generates and maintains VS Code
launch.jsonconfigurations for each flavor, allowing you to run any environment directly from your IDE.
🚀 Getting Started #
1. Installation #
Add flavor_cli to your dev_dependencies:
flutter pub add dev:flavor_cli
2. Initialization #
Option A — Interactive wizard
Launch the interactive wizard to bootstrap your project:
dart run flavor_cli init
Option B — Non-interactive
Commit a flavor_cli.yaml to your repo and bootstrap with:
dart run flavor_cli init --from flavor_cli.yaml
All required fields are validated before any files are touched. See Config Reference for the full schema.
3. Usage Overview #
Usage: flavor_cli <command> [arguments]
Commands:
init Initialize flavor setup in your project
add Add a new flavor to an existing setup
delete Remove an existing flavor
replace Rename an existing flavor
reset Cleanup project from any flavors and revert to standard state
run Run the project with a specific flavor
build Build the project with a specific flavor
firebase Setup Firebase for all flavors automatically
migrate Migrate legacy JSON config to the latest YAML/ENV format
Examples:
dart run flavor_cli init
dart run flavor_cli init --from flavor_cli.yaml
dart run flavor_cli add staging
dart run flavor_cli replace
dart run flavor_cli reset
dart run flavor_cli run dev
dart run flavor_cli build apk prod
dart run flavor_cli firebase
dart run flavor_cli migrate
Tip
See it in action: Check out the example project for a pre-configured implementation.
🛠️ Command Deep Dive #
1. init #
Option A — Interactive wizard
The wizard guides you through 10 steps:
- Flavor Selection: Choose standard sets (
dev, prodordev, stage, prod) or enter manually. - Schema Definition: Define your
AppConfigvariables (e.g.,String baseUrl, bool debug). - Config Location: Specify where your generated
AppConfigfile should live. - Main Strategy: Choose between Separate Mains (one file per flavor) or Single Main.
- App Branding: Set the display name for your application (auto-detected from
Info.plist/pubspec.yaml). - Package ID: Set your base application identifier (auto-detected from
build.gradle). - Package ID Strategy: Choose whether your flavors use Unique IDs or a Shared ID.
- Firebase Project ID: Set your Firebase project ID if you enable Firebase.
- Per-Flavor Values: Set the runtime value for each
AppConfigvariable across every flavor (e.g.,baseUrlfordev,stage,prod). - Gitignore Env Toggling: Choose whether
.envfiles should be added to.gitignore.
On completion, flavor_cli.yaml is written to your project root (silently overwrites if it exists) and .env.<flavor> files are generated.
Option B — --from <path>
dart run flavor_cli init --from flavor_cli.yaml
Reads and strictly validates the config file, then runs the full setup non-interactively. Any missing required field fails immediately with a clear error:
❌ flavor_cli: invalid config at "flavor_cli.yaml"
→ "production_flavor" must be one of the declared flavors: [dev, stage, prod]
Note
Package ID Strategy: flavor_cli supports Unique IDs (appending .flavorName to non-production flavors, e.g. com.example.app.dev) or a Shared ID (same identifier across all environments). Unique IDs are recommended — they allow multiple flavors to be installed side-by-side on the same device. The production flavor always uses the base ID as-is, regardless of strategy.
2. add #
Add a new environment to an existing setup without re-initializing.
- Prompts for the flavor name if not provided as an argument.
- Initializes empty per-flavor values in new
.env.<flavor>files. - Regenerates
.xcconfigfiles, updates Android flavors, and adds the flavor to yourAppConfig.
dart run flavor_cli add staging
3. delete #
Safely remove a flavor and its associated artifacts.
- Prompts for the flavor to remove if not provided.
- Safety First: If deleting would leave fewer than 2 flavors, warns and offers a full Project Reset instead.
- Identity Migration: If you delete your production flavor, you are prompted to nominate a replacement.
4. replace #
Rename an existing flavor across the entire project.
- Guides you through selecting the old flavor and entering the new name.
- Atomic rename: A pre-flight snapshot of all affected files (xcconfig, schemes, gradle, dart mains,
.flavor_cli.json) is taken before any changes. If any step fails, all files are restored verbatim from the snapshot — no partial renames.
5. reset #
Reverts your project to its original, non-flavored state.
- Removes all flavor mains, xcconfig files, and VS Code launch configs.
- Reverts
build.gradle/build.gradle.ktsand Xcode project settings. - Deletes
flavor_cli.yamland all.env.*files.
6. run #
Standardized wrapper for flutter run.
- Prompts for flavor and build mode (
debug/release/profile) if not provided. - Resolves the correct entry point based on your main strategy (
lib/main/main_<flavor>.dartorlib/main.dart). - Automatically loads the correct
.env.<flavor>file at startup. - Fails with a clear error if the resolved entry point file does not exist.
dart run flavor_cli run dev
7. build #
High-level wrapper for flutter build.
- Prompts for build target (
apk/ipa/appbundleetc.) and flavor if not provided. - Same entry point resolution and
--dart-defineinjection asrun.
dart run flavor_cli build apk prod
8. firebase #
The "One-Pass" Firebase orchestrator.
Reads the firebase block from flavor_cli.yaml and configures Firebase non-interactively across all flavors. Requires flutterfire CLI to be available on PATH.
Supports 3 strategies:
| Strategy | use_suffix |
When to use |
|---|---|---|
shared_id_single_project |
false |
All flavors share one Firebase project and one package ID |
unique_id_single_project |
true |
All flavors in one Firebase project but with unique package IDs |
unique_id_multi_project |
true |
Each flavor has its own Firebase project |
- Runs
flutterfire configurethe minimum number of times needed for your strategy. - Injects
Firebase.initializeAppand the correct options import into your main files automatically. - Idempotent: Skips injection if
Firebase.initializeAppis already present in a file. - Suffix rules: Production flavor always uses the base bundle ID. Non-production flavors append
.<flavorName>whenuse_suffixistrue.
dart run flavor_cli firebase
9. migrate #
Migrate your configuration to the latest ENV format.
If you are upgrading from an older version of flavor_cli (v0.0.7 or below), you should migrate your legacy .flavor_cli.json to the new flavor_cli.yaml + .env architecture.
- Reads your existing
.flavor_cli.json. - Extracts
valuesand migrates them to per-flavor.envfiles. - Generates a clean
flavor_cli.yaml. - Updates your
AppConfigandmainentry points to useflutter_dotenv. - Deletes the legacy
.flavor_cli.jsonon success.
dart run flavor_cli migrate
📐 Config Reference #
flavor_cli.yaml is the source of truth for project metadata. Per-flavor runtime values are stored in .env.<flavor> files.
flavor_cli.yaml
flavors:
- dev
- stage
- prod
app_name: MyApp
fields:
baseUrl: String
debug: bool
app_config_path: lib/core/config/app_config.dart
use_separate_mains: true
use_suffix: true
android:
application_id: com.example.app
ios:
bundle_id: com.example.app
production_flavor: prod
platforms:
- android
- ios
gitignore_env: false
flavor_app_names:
dev: MyApp-Dev
stage: MyApp-Stage
prod: MyApp
firebase:
strategy: unique_id_multi_project
projects:
dev: my-app-dev
stage: my-app-stage
prod: my-app-prod
.env.dev
BASE_URL=https://dev.api.com
DEBUG=true
Required fields #
flavors, app_name, production_flavor, android.application_id, ios.bundle_id, app_config_path, use_separate_mains, use_suffix
Optional fields #
| Field | Default | Notes |
|---|---|---|
fields |
{} |
AppConfig variable definitions |
values |
{} |
Per-flavor values for each field in fields |
firebase |
(absent) | Skips firebase setup if not present |
📚 Guides #
- Firebase Integration — Step-by-step guide to using the Firebase CLI with flavors.
- Manual Setup Guide — Beginner-friendly reference for manual flavor configuration on Android and iOS.
🤝 Contributing #
Contributions are what make the open source community such an amazing place to learn, inspire, and create. Any contributions you make are greatly appreciated.