Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

In Android/Gradle how to define a task that only runs when building specific buildType/buildVariant/productFlavor (v0.10+)

Android Plugin for Gradle generates for every BuilType/Flavor/BuildVariant a task. The problem is that this task will be generated dynamically and thus won't be available as a dependency when defining a task like this:

task myTaskOnlyForDebugBuildType(dependsOn:assembleDebug) {     //do smth } 

A proposed workaround from this answer would be this

task myTaskOnlyForDebugBuildType(dependsOn:"assembleDebug") {     //do smth } 

or this

afterEvaluate {     task myTaskOnlyForDebugBuildType(dependsOn:assembleDebug) {         //do smth     } } 

But both didn't work for me.

like image 814
Patrick Favre Avatar asked Mar 30 '14 11:03

Patrick Favre


People also ask

What does Gradle use to determine the order in which task can be run?

Gradle determines the subset of the tasks, created and configured during the configuration phase, to be executed. The subset is determined by the task name arguments passed to the gradle command and the current directory. Gradle then executes each of the selected tasks.


2 Answers

Here is a full example on how to do this inspired by this post: (android plugin v.0.9.2 and gradle 1.11 at the time of writing)

We are going to define a task that only runs when we build a "debugCustomBuildType"

android {     ...     buildTypes {         debugCustomBuildType {             //config         }    } } 

Define the task that should only be executed on a specific builtType/variant/flavor

task doSomethingOnWhenBuildDebugCustom {     doLast {        //task action     } } 

Dynamically set the dependency when the tasks are added by gradle

tasks.whenTaskAdded { task ->     if (task.name == 'generateDebugCustomBuildTypeBuildConfig') {         task.dependsOn doSomethingOnWhenBuildDebugCustom      } } 

Here we use the "generateBuildConfig" task, but you can use any task that works for you (also see official docs)

  • processManifest
  • aidlCompile
  • renderscriptCompile
  • mergeResourcess.
  • mergeAssets
  • processResources
  • generateBuildConfig
  • javaCompile
  • processJavaResources
  • assemble

Don't forget to use the buildTypeSpecific task (generateBuildConfig vs. generateDebugCustomBuildTypeBuildConfig)

And that's it. It's a shame this workaround isn't well documented because for me this seems like one of the simplest requirements for a build script.

like image 157
Patrick Favre Avatar answered Oct 02 '22 13:10

Patrick Favre


I achieved it like this:

android {     ext.addDependency = {         task, flavor, dependency ->             def taskName = task.name.toLowerCase(Locale.US)             if (taskName.indexOf(flavor.toLowerCase(Locale.US)) >= 0) {                 task.dependsOn dependency             }     }      productFlavors {         production {         }         other     }      task theProductionTask << {         println('only in production')     }      tasks.withType(JavaCompile) {         compileTask -> addDependency compileTask, "production", theProductionTask     } } 

To be frank, I don't which locale is used to generate names for compile taks so toLowerCase(Locale.US) may be counterproductive.

like image 24
Juozas Kontvainis Avatar answered Oct 02 '22 14:10

Juozas Kontvainis