Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

File google-services.json is missing when combining multiple product flavors with flavor dimensions

I am trying to configure an Android project combining multiple product flavors with flavor dimensions.

Here is a snippet of build.gradle

android {
    ...
    flavorDimensions "vendor", "type"
    productFlavors {

        development {
            dimension "vendor"
        }

        production {
            dimension "vendor"
        }

        free {
            dimension "type"
        }

        paid {
            dimension "type"
        }
    }
    ...
}

I am using a google service where I need to have the google-services.json file and I would like to have a different file for each vendor, one for development and another for production.

So I have one google-services.json in app/src/development and another in app/src/production.

When building the I get this error:

File google-services.json is missing. The Google Services Plugin cannot function without it. 
  Searched Location: 
  <path>/app/src/developmentPaid/debug/google-services.json
  <path>/app/src/debug/developmentPaid/google-services.json
  <path>/app/src/developmentPaid/google-services.json
  <path>/app/src/debug/google-services.json
  <path>/app/google-services.json

From the error I need to have the same google-services.json in app/src/developmentFree and app/src/developmentPaid and another in app/src/productionFree and app/src/productionPaid.

Do I need to have the same file in both places when using flavor dimensions?

Edit:

I end up by solving this issue with a couple of extra tasks for each merged productFlavor. I added this code after android :

afterEvaluate {

android.productFlavors.all { flavor ->
    if (flavor.dimension == "vendor") {
        task("copy${flavor.name.capitalize()}GoogleServicesFile", type: Copy) {
            description = 'Switches to google-services.json depending on flavor'
            from "src/${flavor.name}"
            include "google-services.json"
            into "."
        }
        task("delete${flavor.name.capitalize()}GoogleServicesFile", type: Delete) {
            description = 'Delete google-services.json from base folder'
            delete "./google-services.json"
        }
    }
}

android.applicationVariants.all { variant ->
    def buildType = variant.buildType.name.capitalize()
    def typeFlavorName = variant.productFlavors.get(0).name.capitalize()
    def vendorFlavorName = variant.productFlavors.get(1).name.capitalize()
    def copyFileTaskName = "copy${vendorFlavorName}GoogleServicesFile"
    def deleteFileTaskName = "delete${vendorFlavorName}GoogleServicesFile"
    def processGoogleServicesTaskName = "process${typeFlavorName}${vendorFlavorName}${buildType}GoogleServices"
    tasks."${processGoogleServicesTaskName}".dependsOn "${copyFileTaskName}"
    tasks."${processGoogleServicesTaskName}".finalizedBy "${deleteFileTaskName}"
}

}

This way, for each typeFlavorName, vendorFlavorName and buildType variation, the google-services.json file is copied to app/ before process{typeFlavorName}{vendorFlavorName}{buildType}GoogleServices and deleted afterwards.

like image 489
Rui Rodrigues Avatar asked Apr 04 '18 08:04

Rui Rodrigues


People also ask

How do I use a different Google services JSON file with multiple product flavors Android?

How to use this file for different product flavors. There are only 3 steps first step is so simple just remove the google-service. json file from the root of the app/ module and save it your local system directory for the save side, & then make your product flavors like Production & Staging environment.

How can I add two Google services json in the same project?

There is no way to use two google-services. json files in a single Android app. The file name is the same between them and they need to be in the same location. So one will overwrite the other in that case.


1 Answers

I end up by solving this issue with a couple of extra tasks for each merged productFlavor. I added this code after android :

afterEvaluate {

    android.productFlavors.all { flavor ->
        if (flavor.dimension == "vendor") {
            task("copy${flavor.name.capitalize()}GoogleServicesFile", type: Copy) {
                description = 'Switches to google-services.json depending on flavor' from "src/${flavor.name}"
                include "google-services.json" into "."
            }
            task("delete${flavor.name.capitalize()}GoogleServicesFile", type: Delete) {
                description = 'Delete google-services.json from base folder'
                delete "./google-services.json"
            }
        }
    }

    android.applicationVariants.all { variant ->
        def buildType = variant.buildType.name.capitalize()
        def typeFlavorName = variant.productFlavors.get(0).name.capitalize()
        def vendorFlavorName = variant.productFlavors.get(1).name.capitalize()
        def copyFileTaskName = "copy${vendorFlavorName}GoogleServicesFile"
        def deleteFileTaskName = "delete${vendorFlavorName}GoogleServicesFile"
        def processGoogleServicesTaskName = "process${typeFlavorName}${vendorFlavorName}${buildType}GoogleServices"
        tasks."${processGoogleServicesTaskName}".dependsOn "${copyFileTaskName}"
        tasks."${processGoogleServicesTaskName}".finalizedBy "${deleteFileTaskName}"
    }
}

This way, for each typeFlavorName, vendorFlavorName and buildType variation, the google-services.json file is copied to app/ before process{typeFlavorName}{vendorFlavorName}{buildType}GoogleServices and deleted afterwards.

like image 53
Rui Rodrigues Avatar answered Oct 01 '22 21:10

Rui Rodrigues