Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

productFlavor variables in Android Studio / Gradle

Tags:

I have an android application that has the following product flavors:

productFlavors {
    local {

    }

    development {


    }

    production {

    }
}

then have the following at the bottom of my build.grade:

File crashlyticsProperties = new File("${project.projectDir.absolutePath}/fabric.properties")
android.applicationVariants.all { variant ->
    def variantSuffix = variant.name.capitalize()
    def generateResourcesTask = project.tasks.getByName("fabricGenerateResources${variantSuffix}")
    def generatePropertiesTask = task("fabricGenerateProperties${variantSuffix}") << {
        Properties properties = new Properties()
        properties.put("apiSecret", WHAT_GOES_HERE)
        properties.put("apiKey", WHAT_GOES_HERE)
        PropertiesUtils.injectPropertyInFile(crashlyticsProperties, properties, "")
    }
    generateResourcesTask.dependsOn generatePropertiesTask
}

I'm trying to set the api secret/key for crashlytics but I need to be able to set these depending on what product flavor I'm building.

properties.put("apiSecret", WHAT_GOES_HERE)
properties.put("apiKey", WHAT_GOES_HERE)

How can I set/get these variables?

Update #1

I've added the following to my build.gradle

productFlavors {
    local {
        buildConfigField "String", "CRASHLYTICS_API_SECRET", "1234"
        buildConfigField "String", "CRASHLYTICS_API_KEY", "1234"
    }

    development {
        buildConfigField "String", "CRASHLYTICS_API_SECRET", "1234"
        buildConfigField "String", "CRASHLYTICS_API_KEY", "1234"
    }

    production {
        buildConfigField "String", "CRASHLYTICS_API_SECRET", "1234"
        buildConfigField "String", "CRASHLYTICS_API_KEY", "1234"
    }
}

Then at the bottom of the build.gradle file I have:

File crashlyticsProperties = new File("${project.projectDir.absolutePath}/fabric.properties")
android.applicationVariants.all { variant ->
    def variantSuffix = variant.name.capitalize()
    def generateResourcesTask = project.tasks.getByName("fabricGenerateResources${variantSuffix}")
    def generatePropertiesTask = task("fabricGenerateProperties${variantSuffix}") << {
        Properties properties = new Properties()
        println "...copying apiSecret for ${variant.name}"
        properties.put("apiSecret", BuildConfig.CRASHLYTICS_API_SECRET)
        println "...copying apiKey for ${variant.name}"
        properties.put("apiKey", BuildConfig.CRASHLYTICS_API_KEY)
        PropertiesUtils.injectPropertyInFile(crashlyticsProperties, properties, "")
    }
    generateResourcesTask.dependsOn generatePropertiesTask
}

This however does not compile and gives me:

Error:(334, 1) Execution failed for task ':app:fabricGeneratePropertiesDevelopmentDebug'. Could not find property 'BuildConfig' on task ':app:fabricGeneratePropertiesDevelopmentDebug'.

like image 672
Kyle Decot Avatar asked Mar 06 '18 13:03

Kyle Decot


People also ask

What is a Buildtype in Gradle?

A build type determines how an app is packaged. By default, the Android plug-in for Gradle supports two different types of builds: debug and release . Both can be configured inside the buildTypes block inside of the module build file.

How can I get flavor on my Android?

You can add a config file, say 'Appconfig. java' to your productFlavor specific source folders i.e. src/<productflavor>/java/<packagename>/Appconfig. java ; you can then use Appconfig. PRODUCT_FLAVOR in your app.

What are build variants in Android?

Build variants are the result of Gradle using a specific set of rules to combine settings, code, and resources configured in your build types and product flavors. Although you do not configure build variants directly, you do configure the build types and product flavors that form them.

What is Gradle product flavors?

Product flavors are a powerful feature of the Gradle plugin from Android Studio to create customised versions of products. They form part of what we call Build Variants.


2 Answers

For this error:

Error:(334, 1) Execution failed for task ':app:fabricGeneratePropertiesDevelopmentDebug'. Could not find property 'BuildConfig' on task ':app:fabricGeneratePropertiesDevelopmentDebug'.

Use a different construction, eg:

variant.mergedFlavor.buildConfigFields["CRASHLYTICS_API_SECRET"].value

Of course this solution expects, that such BuildConfig field is defined. If you expect field would not exist, make sure to check if present first.

EDIT:

If you'd like a solution described in your question:

File crashlyticsProperties = new File("${project.projectDir.absolutePath}/fabric.properties")
android.applicationVariants.all { variant ->
    def variantSuffix = variant.name.capitalize()
    def generateResourcesTask = project.tasks.getByName("fabricGenerateResources${variantSuffix}")
    def generatePropertiesTask = task("fabricGenerateProperties${variantSuffix}") << {
        Properties properties = new Properties()
        println "...copying apiSecret for ${variant.name}"
        properties.put("apiSecret", variant.mergedFlavor.buildConfigFields.get("CRASHLYTICS_API_SECRET").value)
        println "...copying apiKey for ${variant.name}"
        properties.put("apiKey", variant.mergedFlavor.buildConfigFields.get("CRASHLYTICS_API_KEY").value)
        PropertiesUtils.injectPropertyInFile(crashlyticsProperties, properties, "")
    }
    generateResourcesTask.dependsOn generatePropertiesTask
}
like image 134
R. Zagórski Avatar answered Sep 19 '22 13:09

R. Zagórski


you can have different buildConfigFields for every flavour where you can declare mutiple strings variables and seperate keys for each flavour easily

Like :

local { buildConfigField "String", "KEY", '"abcKey' } 
development { buildConfigField "String", "KEY", '"xyzKey' } 

and use these variables in your java files as follows

properties.put("apiSecret", BuildConfig.KEY)
like image 44
Adeel Turk Avatar answered Sep 21 '22 13:09

Adeel Turk