Discriminate Flutter flavors that should build with signing
1 min read

Discriminate Flutter flavors that should build with signing

Keep you build.gradle clean by assigning signing configuration only to the flavors that need them.

I am working on a Flutter app with different flavors. There are currently three flavors configured in the app:

  • development connects to local Firebase emulators, it is not signed, it's used only to run on simulators or devices.
  • uat connects to a staging Firebase project, it is not signed for App Store or Play Store distribution, it is distributed via Firebase App Distribution.
  • release connects to a production Firebase project, it is signed for store distribution.

How we implemented flavors is very similar to the guides linked in Flutter documentation.

After having development and uat working, we added signing for release, following the official guide, and at that point, Android uat stopped working. On building time we experienced the following error.

...
* What went wrong:

Execution failed for task ':app:validateSigningUatRelease'.

> Keystore file not set for signing config release

The interesting part of android/app/build.gradle is:

signingConfigs {
    release {
        keyAlias keystoreProperties['keyAlias']
        keyPassword keystoreProperties['keyPassword']
        storeFile keystoreProperties['storeFile'] ? file(keystoreProperties['storeFile']) : null
        storePassword keystoreProperties['storePassword']
    }
}

buildTypes {
    release {
        signingConfig signingConfigs.release
    }
}

flavorDimensions "flavors"
productFlavors {
    dev {
        dimension "flavors"
        applicationIdSuffix ".dev"
        versionNameSuffix "-dev"
    }
    uat {
        dimension "flavors"
        applicationIdSuffix ".uat"
        versionNameSuffix "-uat"
    }
    release {
        dimension "flavors"
        // This is the play store release version.
        applicationId "com.ishouldgotosleep.android"
    }
}
}   

The problem is with the release inside buildTypes. It does not identify the releaseflavor, but the Flutter release.

To fix it we changed it to

signingConfigs {
    release {
        keyAlias keystoreProperties['keyAlias']
        keyPassword keystoreProperties['keyPassword']
        storeFile keystoreProperties['storeFile'] ? file(keystoreProperties['storeFile']) : null
        storePassword keystoreProperties['storePassword']
    }
}

flavorDimensions "flavors"
productFlavors {
    dev {
        dimension "flavors"
        applicationIdSuffix ".dev"
        versionNameSuffix "-dev"
    }
    uat {
        dimension "flavors"
        applicationIdSuffix ".uat"
        versionNameSuffix "-uat"

        // Set the signing configuration. 
        signingConfig signingConfigs.debug
    }
    release {
        dimension "flavors"
        // This is the play store release version.
        applicationId "com.ishouldgotosleep.android"

        // Set the signing configuration. 
        signingConfig signingConfigs.release
    }
}

We removed the buildTypes section and added the signing information directly in the productFlavors section.

Subscribe to a curated newsletter

Receive an email every week with curated content about Dart and Flutter.

See previous issues of the newsletter.