176

I am trying to figure out a way to be able to change my application's app name per build type in gradle.

For instance, I would like the debug version to have <APP_NAME>-debug and the qa version to have <APP-NAME>-QA.

I am familiar with:

debug {
        applicationIdSuffix '.debug'
        versionNameSuffix '-DEBUG'
}

However, I can't seem to find a gradle command to apply the change of the app when in the launcher.

appersiano
  • 2,670
  • 22
  • 42
Andre Perkins
  • 7,640
  • 6
  • 25
  • 39

11 Answers11

203

If by "app name", you mean android:label on <application>, the simplest solution is to have that point at a string resource (e.g., android:label="@string/app_name"), then have a different version of that string resource in a src/debug/ sourceset.

You can see that in this sample project, where I have a replacement for app_name in src/debug/res/values/strings.xml, which will be applied for debug builds. release builds will use the version of app_name in src/main/.

CommonsWare
  • 986,068
  • 189
  • 2,389
  • 2,491
  • wouldn't this solution imply that we would have to add an extra strings.xml for each translation? that could become a pain to maintain... – sfera Jul 18 '14 at 10:26
  • 8
    @sfera: First, you are welcome to isolate this string in its own resource file if you want. Second, this is only for one string. Third, this is only for the build types where you want to replace that string. Fourth, unless you have a development team without a common language, you would not need to translate non-`release` strings. – CommonsWare Jul 18 '14 at 10:36
  • Isolating the string sounds like a good idea. Thanks for that! As for the non-``release`` part, I see that a bit differently as one might want to also test for localization issues while allowing the "release" and "test" builds to coexist on the same device. In such a case both builds might end up with the same launcher label, probably causing some confusion. That is what I was trying to avoid. – sfera Jul 18 '14 at 10:46
  • 1
    @sfera: "That is what I was trying to avoid" -- so, don't translate this one string. The test on that string will be invalid anyway, as by definition, it is not the string you want to use in `release` mode. And only use this string resource for `app_name`, not for any other role. – CommonsWare Jul 18 '14 at 10:49
  • We are probably talking about different things. I didn't intend to translate the "DEBUG" string. But the app launcher label is certainly localized for the release build. Now - assuming that my app label is "AppName" - I would like to have "AppName-DEBUG" for debug builds with the french label of something like "AppNom-DEBUG" and the german label "AppNamen-DEBUG". – sfera Jul 18 '14 at 11:04
  • 3
    @sfera: You will never ship an app with "AppNom-DEBUG". You might ship an app with "AppNom". Testing "AppNom-DEBUG", therefore, is unnecessary. You are certainly welcome to translate a debug version of `app_name`, even though it is not necessary (e.g., you have French or German developers who do not speak English and therefore need to have it translated). For testing to see if the unmodified `release` version of `app_name` works, with its translations, test the `release` build, or create a `near-release` build type that just adds the app ID suffix and leaves the strings alone. – CommonsWare Jul 18 '14 at 11:12
  • When having flavors in the project, putting `strings.xml` in `/src/debug/res/values/`doesn't work. Instead, you need to specify the flavor name in front of the build type, e.g.: if you have a flavor called Premium then the folder name should be: `premiumDebug`. @CommonsWare, perhaps you should update your answer accordingly. – Nimrod Dayan May 17 '16 at 13:59
  • @NimrodDayan: No, that's still supposed to work, assuming that you do not need different names per actual build variant. If you want the same name for all `debug` builds regardless of flavor, my answer is correct. If you are having problems getting this to work, file a fresh Stack Overflow question with a [mcve]. – CommonsWare May 17 '16 at 14:01
  • You're right, it does work. I didn't notice, but in Android Studio, the current build type was something else than debug at the time I tried it. After changing that back to the `flavorDebug`, it seemed to do the trick. – Nimrod Dayan May 17 '16 at 14:14
  • @CommonsWare Link is dead. 404 – tenprint Nov 11 '17 at 14:26
196

You can use something like this

 buildTypes {
    debug {
        applicationIdSuffix '.debug'
        versionNameSuffix '-DEBUG'
        resValue "string", "app_name", "AppName debug"
    }
    release {
        minifyEnabled true
        shrinkResources true
        proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
        signingConfig signingConfigs.release
        zipAlignEnabled true
        resValue "string", "app_name", "AppName"
    }
}

You can use @string/app_name in AndroidManifest.xml files.

Make sure you remove app_name from values/ folder (no entry by this name).

irscomp
  • 2,900
  • 1
  • 16
  • 12
  • Perfect when the app name has to be read form an external file – Joe Maher Jan 20 '16 at 00:13
  • Got an error when building this way. Execution failed for task ':app:mergeDebugResources'.. Duplicate resources: res/values/strings.xml:string/app_name – Lalle Mar 29 '16 at 16:34
  • 7
    If you get: Got an error when building this way. Execution failed for task ':app:mergeDebugResources'.. Duplicate resources: res/values/strings.xml:string/app_name you should do, like its written: "Make sure you remove app_name from values/ folder (no entry by this name)." – ivan.panasiuk Apr 05 '16 at 17:51
  • I like this because the strings folder solution (the accepted solution, above) only works if the app name is defined for a particular source set / product flavor. In my case, I'm setting up a Jenkins Pipeline job to build different versions of our app automatically with different names, and not all those names have productFlavors defined for them. So Jenkins simply supplies the app name via the environment, and gradle reads it: `resValue "string", "app_name", System.getenv("APP_NAME") ?: "MyApp"` – Aphex Feb 03 '17 at 23:01
  • if i removed app_name from string folder then getting error compile time getting error -Error:Execution failed for task ':app:processDevDebugManifest'. > Manifest merger failed with multiple errors, see logs – aj0822ArpitJoshi Dec 14 '17 at 06:37
  • It works, but if you have another library in your application with it's own `strings.xml` and `app_name`, an application will get a value from there. Probably in this case you should change a key `app_name` to other. – CoolMind Jan 31 '19 at 11:54
  • did not work for me with a multi-module setup. play console kept reporting wrong empty icon attribute when in reality it was my app's name! I used this https://stackoverflow.com/questions/24785270/how-to-change-app-name-per-gradle-build-type/41301021#41301021 – Andre Thiele Feb 17 '21 at 16:20
68

You can do this with gradle:

android {
    buildTypes {
        release {
            manifestPlaceholders = [appName: "My Standard App Name"]
        }
        debug {
            manifestPlaceholders = [appName: "Debug"]
        }
    }
}

Then in your AndroidManifest.xml put:

<application
    android:label="${appName}"/>
    <activity
        android:label="${appName}">
        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
</application>

Note: it also works with productFlavors.

Albert Vila Calvo
  • 15,298
  • 6
  • 62
  • 73
  • getting error -Error:Execution failed for task ':app:processDevDebugManifest'. > Manifest merger failed with multiple errors, see logs – aj0822ArpitJoshi Dec 14 '17 at 06:32
  • NOT WORKING---buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } debug { manifestPlaceholders = [appName: "GridL Debug"] applicationIdSuffix ".dev1" } } – JSONParser Jan 17 '18 at 07:30
  • this is the only method that worked for me, what's even worse is the error reporting on the play console. it said that my icon was wrong but in reality it was my app name! this helped! Thanks man!! – Andre Thiele Feb 17 '21 at 16:19
63

To support translations make this:

1. remove string "app_name"

2. add to gradle

 buildTypes {
    admin {
       resValue "string", "app_name", "@string/app_name_admin"
    }
    release {
        resValue "string", "app_name", "@string/app_name_release"
    }
    debug {
        resValue "string", "app_name", "@string/app_name_debug"
    }
}

3. Set app name in Manifest as "@string/app_name"

4. Add to strings.xml values

<string name="app_name_admin">App Admin</string>
<string name="app_name_release">App  release</string>
<string name="app_name_debug">App debug</string>
NickUnuchek
  • 11,794
  • 12
  • 98
  • 138
  • What are the different types of build types ? Other than, admin, release and debug ? – Dinesh Jul 28 '17 at 09:12
  • @DineshVG you can set difference by yourself, for example different applicationId – NickUnuchek Jul 28 '17 at 09:17
  • I want to use UIAutomator test in another build configuration other than debug with different pro-guard rules. Is that possible ? – Dinesh Jul 28 '17 at 09:22
  • This should be the accepted answer, worked great for me – Olegdater Feb 22 '20 at 06:42
  • I really like this approach because it allows you even to add a custom `app_name` in _productFlavors_ section of `build.gradle` file. An extremely convenient and flexible approach when you need it. – Egel Jul 08 '20 at 08:39
  • did not work for me in a multi-module setup. i used this https://stackoverflow.com/questions/24785270/how-to-change-app-name-per-gradle-build-type/41301021#41301021 which worked for me! – Andre Thiele Feb 17 '21 at 16:21
  • I like this answer because it still allows me to reference the generate String in other resources, eg. `@string/app_name` – TomaszRykala Jan 15 '22 at 15:38
16

The app name is user-visible, and that's why Google encourages you to keep it in your strings.xml file. You can define a separate string resource file that contains strings that are specific to your buildTypes. It sounds like you might have a custom qa buildType. If that's not true, ignore the qa part below.

└── src
    ├── debug
    │   └── res
    │       └── buildtype_strings.xml
    ├── release
    │   └── res
    │       └── buildtype_strings.xml
    └── qa
        └── res
            └── buildtype_strings.xml
Krylez
  • 17,414
  • 4
  • 32
  • 41
16

We need a solution to support app name with localization (for multi language). I have tested with @Nick Unuchek solution, but building is failed (not found @string/) . a little bit change to fix this bug: build.gradle file:

android {
    ext{
        APP_NAME = "@string/app_name_default"
        APP_NAME_DEV = "@string/app_name_dev"
    }

    productFlavors{

        prod{
            manifestPlaceholders = [ applicationLabel: APP_NAME]
        }

        dev{
            manifestPlaceholders = [ applicationLabel: APP_NAME_DEV ]
        }

    }

values\strings.xml:

<resources>
    <string name="app_name_default">AAA prod</string>
    <string name="app_name_dev">AAA dev</string>

</resources>

values-en\strings.xml:

<resources>
    <string name="app_name_default">AAA prod en</string>
    <string name="app_name_dev">AAA dev en</string>

</resources>

Manifest.xml:

<application
    android:label="${applicationLabel}" >
</application>
HungNM2
  • 3,101
  • 1
  • 30
  • 21
  • A game like "Need for Speed" for example will never be called "Bedürfnis nach Geschwindigkeit" in Germany. Unless it is any rip-off from a dubious developer... – The incredible Jan Feb 13 '18 at 14:17
  • It working. Thank you so much. However, in my case, I need to add 1 more `tools:replace="android:label"` in `application` in `AndroidManifest` – Linh Mar 15 '19 at 03:05
5

For a more dynamic gradle based solution (e.g. set a base Application name in main's strings.xml once, and avoid repeating yourself in each flavor / build type combination's strings.xml), see my answer here: https://stackoverflow.com/a/32220436/1128600

Community
  • 1
  • 1
Steffen Funke
  • 2,168
  • 1
  • 21
  • 18
5

There are multiple ways you can do.

you can create manifestPlaceholders OR resValue in app level build.gradle. e.g.

buildTypes {
     release {
          ...
          manifestPlaceholders = [appLabel: "My App"]
          //resValue "string", "appLabel", '"My App"'
     }
     debug {
          ...
          manifestPlaceholders = [appLabel: "My App - Debug"]
          //resValue "string", "appLabel", '"My App - Debug"'
     }
}

OR

If you have productFlavors, you can create there

flavorDimensions "env"
productFlavors {
    dev {
        dimension "env"
        ...
        manifestPlaceholders = [appLabel: "My App - Development"]
        //resValue "string", "appLabel", '"My App - Development"'
    }
    prod {
        dimension "env"
        ...
        manifestPlaceholders = [appLabel: "My Awesome App"]
        //resValue "string", "appLabel", '"My Awesome App"'
    }
}

Then in AndroidManifest.xml if you are using manifestPlaceholders, just change android:label="${appLabel}" as below OR if you are using resValue, just change android:label=@string/appLabel

<application
    ...
    android:label="${appLabel}"> //OR `android:label=@string/appLabel`
    
    <activity
        ...
        android:label="${appLabel}">

        <intent-filter>
            <action android:name="android.intent.action.MAIN" />

            <category android:name="android.intent.category.LAUNCHER" />
        </intent-filter>
    </activity>
</application>

NOTE: Make sure to change android:label as well in <activity> of LAUNCHER category. If it doesn't require to use android:label in <activity>, just remove this.


If you do not want to add in build.gradle directly, you can add in values/string.xml of selected ProductFlavors. e.g.

Add

<string name="appLabel">My App - Development</string> 

in app/src/dev/res/values/string.xml

and

<string name="appLabel">My Awesome App</string> 

in app/src/prod/res/values/string.xml

Narendra
  • 4,514
  • 2
  • 21
  • 38
Amir Raza
  • 2,320
  • 1
  • 23
  • 32
  • Best answer by a country mile, allows to set all app name variants you want directly from Gradle (as per the question), rather than hunting down all the separate res folders. *Especially useful* if you may have dynamic app names, coming from build config. – Vin Norman Feb 24 '23 at 06:37
4

You can use strings.xml in different folders, see Android separate string values for release and debug builds.

So, create this file:

<?xml version="1.0" encoding="utf-8"?>
<resources>
    <string name="app_name">Your app name</string>
</resources>

Then paste it to app\src\debug\res\values\ and app\src\release\res\values\ folders. Replace "Your app name" in debug and release files. Remove app_name item from strings.xml in app\src\main\res\values\ folder.

In AndroidManifest you will have the same

<application
    android:label="@string/app_name"
    ...

No changes at all. Even if you added a library with it's AndroidManifest file and strings.xml.

CoolMind
  • 26,736
  • 15
  • 188
  • 224
2

As author asks to do this in Gradle, we can assume he want to do it in the script and not in the configuration files. Since both Android Studio and Gradle has been heavily updated and modified in the last year (~2018) all other answers above, seem overly contorted. The easy-peasy way, is to add the following to your app/build.gradle:

android {
    ...
    buildTypes {
        ...
        // Rename/Set default APK name prefix (app*.apk --> AwesomeApp*.apk)
        android.applicationVariants.all { variant ->
            variant.outputs.all { output ->
                def appName = "AwesomeApp"
                outputFileName = appName+"-${output.baseName}-${variant.versionName}.apk"
        }
    }
}
not2qubit
  • 14,531
  • 8
  • 95
  • 135
0

Go to your build-specific folder e.g development, Staging and

1-Add res folder.

2-Add values folder inside res folder.

3-Add strings.xml.

4-Add app_name string and change the name here.

repeat the same for other build types if you want to change for others.

Now you will get your app name as per your specific build type.

Yazdan Ilyas
  • 374
  • 4
  • 8