Why are build types distinct from product flavors?

Preface: this is not a question about how to use build types and product flavors in an Android app. I understand the basic concepts involved. This question is more about trying to understand which configuration should be specified in a build type, which configuration should be specified in a product flavor, and whether any distinction is actually necessary.

This week, I’ve been learning more about gradle configuration for Android apps. I initially thought I had a good handle on build types vs product flavors, but the deeper I got into the documentation the more I realized the distinction between the two was not clear to me at all.

Since there is a well-defined hierarchy (in the sense that properties specified in build types take precedence over those specified in product flavors), I don’t understand why there is a need to distinguish between build types and product flavors at all. Would it not be better to merge all properties and methods into the product flavor DSL object, and then just treat build type as a (default) flavor dimension?

Some concrete examples that led to my confusion:

  • The signingConfig property can be set in both build types and product flavors… but minifyEnabled (and, I assume, shrinkResources?) can only be configured in build types.

  • applicationId can only be specified in product flavors… and applicationIdSuffix can only be specified in build types!?

The actual question(s):

Given the above examples: is there a clear distinction between the roles of build types vs product flavors?

If so, what is the best way to understand it?

If not, is the plan to eventually merge build types and product flavors into a single configurable DSL object?

6 Answers
6

Leave a Comment