Small knowledge, big challenge! This article is participating in the creation activity of “Essential Tips for Programmers”.

Gradle builds multiple versions

This ZhangMu

  • Build types Build types
    • Product flavors
    • Variants will Build its own varieties
  • Signing configurations

When developing an APP, there is a need to build different versions. Such as test builds and release builds. There are usually different Settings between versions.

Build types

Define how the APP or module should be built.

BuildTypes can be defined with buildTypes. Such as:

buildTypes {
    release {
        minifyEnabled false
        proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'}}Copy the code

The default build.gradle file contains a release build type

Creating a Build type

For example, create a staging build type

buildTypes {
    // staging is a custom name
    // This type can be selected when generating signed apps
    staging.initWith(buildTypes.debug)
    staging {
        applicationIdSuffix ".staging"
        versionNameSuffix "-staging"
        buildConfigField("String"."BASE_URL"."\"http://www.staging.com\"")}}Copy the code

ApplicationIdSuffix is defined so that the applicationId at the staging version is different from the release version.

InitWith () creates a new build type and copies the existing build type. Use this method to override existing build types.

The resource directory

After you create a new build type, you can create a new resource file. For example, we already have a staging build type

├─ SRC ├─ androidTest ├─ Debug ├─ greenRelease ├─ main ├─ redDebug ├─ staging// You can create a new resources directory ├─ testCopy the code

Files in different resource directories can have the same file name.

Strings.xml in the main directory

<resources>
    <string name="app_name">GDemo</string>
</resources>
Copy the code
<resources>
    <! -- staging strings.xml -->
    <string name="app_name">GStaging</string>
</resources>
Copy the code

When building different versions of the app, it will automatically find the corresponding resource file

Dependency package Management

Each build type can have its own dependencies. Gradle automatically creates a dependency configuration for each type. Here are the dependencies to add the logging module for the Debug version alone

dependencies {
    compile fileTree(dir: 'libs'.include: ['*.jar'])
    androidTestCompile('com. Android. Support. Test. Espresso: espresso - core: 2.2.2', {
        exclude group: 'com.android.support'.module: 'support-annotations'
    })
    compile 'com. Android. Support: appcompat - v7:25.1.1'
    testCompile 'junit: junit: 4.12'

    debugCompile 'DE. Mindpipe. Android: android logging - log4j: 1.0.3'
}
Copy the code

Product flavors

Product Flavors is about creating different versions of the same APP. The most direct example is free and paid apps.

When we want to release our APP, we can choose between a release or staging version (as in the above example). However, for the same build type, such as the Release version, we can package Product Flavors with different features of the APP. Such as:

// Multi-channel packaging can be used in this configuration
// Once productFlavors is configured, one of the options is selected by default when apK is generated
productFlavors {
    red {
        versionName "1.0 - red"
    }
    green {
        applicationId "com.rustfisher.gradletest.green" // Use another signature
        versionNameSuffix "-green"// Add a suffix to the version name}}Copy the code

Resource file

After creating the productFlavors type, we can create a new resource directory.

SRC ├─ androidTest └ ─ Debug ├─ Green Release └ ─ Main ├─ redDebug // DEBUG Red ├─ staging └ ─ ─ the testCopy the code

Variants of Multiflavor variants

“Product flavors” can be combined, for example

android {

    flavorDimensions("color"."price") // Create two new types

    // Multi-channel packaging can be used in this configuration
    // Once productFlavors is configured, debug selects one option by default
    productFlavors {
        red {
            versionName "1.0 - red"
            dimension "color"
        }
        green {
            applicationId "com.rustfisher.gradletest.green" // Use another signature
            versionNameSuffix "-green"
            dimension "color"
        }
        freeApp {
            dimension "price"
        }
        paidApp {
            dimension "price"}}}Copy the code

When you package APK, you can have the following four versions

green-freeApp 
green-paidApp 
red-freeApp 
red-paidApp
Copy the code

Once flavorDimensions are added, you must specify dimensions for each flavor. Color and Price must be included in the four productFlavors listed below. Otherwise, an error will be reported.

Build Variants

The Build Variants window will open in the lower left corner of Android Studio. Choose modules and Build Variants. All of the previously configured build types appear in this list.

The Tasks task

The Android plugin for Gradle automatically creates tasks for each configured build type. When you create a project, there are default assembleDebug and assembleRelease. After the above configuration, there is a task to generate the corresponding response

assemble
assembleAndroidTest
assembleDebug
assembleFreeApp
assembleGreen
assembleGreenFreeApp
assembleGreenPaidApp
assemblePaidApp
assembleRed
assembleRedFreeApp
assembleRedPaidApp
assembleRelease
assembleStaging
Copy the code

Resource and manifest merging

The Android Gradle plugin combines the main resources and build-type resources before packaging the app. In addition, the Lib project can provide additional resource files that can be merged. The manifest file can also be merged. For example, you can apply for permissions in the Debug version that are not required in the official version.

Defining build variables

Add resources to the types in productFlavors

ProductFlavors {red {versionName "1.0-red" Dimension "color" resValue("color", "flavor_color", "# ff0000")}, {applicationId com. Rustfisher. Gradletest. "green" / / use another signature versionNameSuffix "," resValue("color", "flavor_color", "#00ff00") dimension "color" } // ... }Copy the code

The flavor_color above can be found in the code in the R file r.color.flavor_color

Obtain flavor name

You can get the flavor name from variable.getflavorName ().

android {
    // ...
    applicationVariants.all { variant ->
        variant.outputs.all {
            if (variant.getFlavorName() == 'rust-fisher') {
                outputFileName = "RustFisher-app_v${defaultConfig.versionName}_${defaultConfig.versionCode}_${getTime()}.apk"}}}}Copy the code

Kevin Pelgrims Gradle for Android