Jak zmienić nazwę aplikacji na typ kompilacji Gradle


135

Próbuję znaleźć sposób, aby zmienić nazwę mojej aplikacji na typ kompilacji w gradle.

Na przykład chciałbym mieć wersję debugowania <APP_NAME>-debugi wersję QA <APP-NAME>-QA.

Jestem zaznajomiony z:

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

Jednak nie mogę znaleźć polecenia gradle, aby zastosować zmianę aplikacji w programie uruchamiającym.

Odpowiedzi:


167

Jeśli przez „nazwę aplikacji” masz android:labelna myśli włączone <application>, najprostszym rozwiązaniem jest umieszczenie tego punktu w zasobie ciągu (np. android:label="@string/app_name"), A następnie posiadanie innej wersji tego zasobu ciągu wsrc/debug/ zestawie źródeł.

Widać to w tym przykładowym projekcie , w którym mam zamiennik dla app_namew src/debug/res/values/strings.xml, który zostanie zastosowany do debugkompilacji. releasekompilacje będą używać wersji app_namein src/main/.


czy to rozwiązanie nie oznaczałoby, że musielibyśmy dodać dodatkowy ciąg string.xml do każdego tłumaczenia? to może być trudne do utrzymania ...
— sfera

7
@sfera: Po pierwsze, możesz odizolować ten ciąg w swoim własnym pliku zasobów, jeśli chcesz. Po drugie, dotyczy to tylko jednego ciągu. Po trzecie, dotyczy to tylko typów kompilacji, w których chcesz zamienić ten ciąg. Po czwarte, gdybyś nie miał zespołu programistów bez wspólnego języka, nie musiałbyś tłumaczyć releaseznaków niebędących ciągami znaków.
— CommonsWare,

Izolowanie struny wydaje się dobrym pomysłem. Dziękuję za to! Jeśli chodzi o releaseczęść niezwiązaną , widzę to nieco inaczej, ponieważ można również chcieć przetestować pod kątem problemów z lokalizacją, jednocześnie zezwalając na współistnienie kompilacji „wydanie” i „test” na tym samym urządzeniu. W takim przypadku obie kompilacje mogą skończyć z tą samą etykietą programu uruchamiającego, prawdopodobnie powodując pewne zamieszanie. Właśnie tego starałem się uniknąć.
— sfera

1
@sfera: "Właśnie tego starałem się uniknąć" - więc nie tłumacz tego jednego ciągu. Test na tym łańcuchu i tak będzie nieprawidłowy, ponieważ z definicji nie jest to ciąg, którego chcesz używać w releasetrybie. I używaj tego zasobu ciągu tylko app_namedla żadnej innej roli, a nie.
— CommonsWare,

3
@sfera: Nigdy nie wyślesz aplikacji z „AppNom-DEBUG”. Możesz wysłać aplikację z „AppNom”. Dlatego testowanie „AppNom-DEBUG” nie jest konieczne. Z pewnością możesz przetłumaczyć wersję do debugowania app_name, nawet jeśli nie jest to konieczne (np. Masz francuskich lub niemieckich programistów, którzy nie mówią po angielsku i dlatego muszą ją przetłumaczyć). Do testowania, aby sprawdzić, czy niezmodyfikowana releasewersja app_namedziała wraz z tłumaczeniami, przetestuj releasekompilację lub utwórz near-releasetyp kompilacji, który po prostu dodaje sufiks identyfikatora aplikacji i pozostawia ciągi w spokoju.
— CommonsWare,

159

Możesz użyć czegoś takiego

 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"
    }
}

Możesz użyć @ string / app_name w plikach AndroidManifest.xml.

Upewnij się, że usunąłeś app_name z wartości / folderu (brak wpisu o tej nazwie).


Idealne, gdy nazwę aplikacji trzeba odczytać z zewnętrznego pliku
— Joe Maher

Podczas budowania w ten sposób wystąpił błąd. Wykonanie nie powiodło się dla zadania „: app: mergeDebugResources” .. Zduplikowane zasoby: res / values ​​/ strings.xml: string /
— nazwa_aplikacji

5
Jeśli otrzymasz: Podczas tworzenia w ten sposób wystąpił błąd. Wykonanie nie powiodło się dla zadania „: app: mergeDebugResources” .. Zduplikowane zasoby: res / values ​​/ strings.xml: string / nazwa_aplikacji, które należy zrobić, tak jak napisano: „Upewnij się, że usunąłeś app_name z wartości / folderu (brak wpisu o tej nazwie ). ”
— ivan.panasiuk,

Podoba mi się to, ponieważ rozwiązanie z folderem ciągów (zaakceptowane rozwiązanie powyżej) działa tylko wtedy, gdy nazwa aplikacji jest zdefiniowana dla określonego zestawu źródłowego / smaku produktu. W moim przypadku konfiguruję zadanie Jenkins Pipeline, aby automatycznie budować różne wersje naszej aplikacji z różnymi nazwami, a nie wszystkie te nazwy mają zdefiniowane dla nich productFlavors. Więc Jenkins po prostu dostarcza nazwę aplikacji za pośrednictwem środowiska, a gradle czyta ją:resValue "string", "app_name", System.getenv("APP_NAME") ?: "MyApp"
— Aphex

jeśli usunąłem app_name z folderu string, wtedy pojawia się błąd podczas kompilacji i pojawia się błąd -Error: wykonanie nie powiodło się dla zadania ': app: processDevDebugManifest'. > Manifest fuzja nie powiodło się z
— powodu

55

Możesz to zrobić za pomocą gradle:

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

Następnie w twoim AndroidManifest.xml miejscu:

<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>

Uwaga: działa również z plikami productFlavors.


uzyskiwanie błędu -Error: wykonanie nie powiodło się dla zadania „: app: processDevDebugManifest”. > Manifest fuzja nie powiodło się z
— powodu

NIE DZIAŁA --- buildTypes {release {minifyEnabled false proguardFiles getDefaultProguardFile ('proguard-android.txt'), 'proguard-rules.pro'} debug {manifestPlaceholder = [appName: "GridL Debug"] applicationIdSuffix ".dev1"}}
— JSONParser

44

Aby wspierać tłumaczenia, wykonaj następujące czynności:

1. usuń ciąg „nazwa_aplikacji”

2. dodać do 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. Ustaw nazwę aplikacji w manifeście jako „@ string / app_name”

4. Dodaj do wartości strings.xml

<string name="app_name_admin">App Admin</string>
<string name="app_name_release">App  release</string>
<string name="app_name_debug">App debug</string>

Jakie są rodzaje typów kompilacji? Inne niż admin, wydanie i debugowanie?
— Dinesh

@DineshVG możesz samodzielnie ustawić różnicę, na przykład inny applicationId
— NickUnuchek

Chcę użyć testu UIAutomator w innej konfiguracji kompilacji innej niż debugowanie z różnymi regułami ochrony. Czy to jest możliwe ?
— Dinesh

To powinna być akceptowana odpowiedź, działała świetnie
— Oleg Dater

Bardzo podoba mi się takie podejście, ponieważ pozwala nawet dodać zwyczaj app_namew productFlavors części build.gradlepliku. Niezwykle wygodne i elastyczne podejście, gdy tego potrzebujesz.
— Egel

15

Nazwa aplikacji jest widoczna dla użytkownika i dlatego Google zachęca do jej przechowywania w pliku strings.xml. Możesz zdefiniować oddzielny plik zasobów ciągu, który zawiera ciągi, które są specyficzne dla twojego buildTypes. Wygląda na to, że możesz mieć niestandardowy qabuildType. Jeśli to nieprawda, zignoruj ​​poniższą część qa.

└── src
    ├── debug
    │   └── res
    │       └── buildtype_strings.xml
    ├── release
    │   └── res
    │       └── buildtype_strings.xml
    └── qa
        └── res
            └── buildtype_strings.xml

1
czy to kiedykolwiek działało dla ciebie? Udokumentowałem mój przykład i nie działa ... stackoverflow.com/questions/26032950/
— volkersfreunde

to są smaki, a nie typy
— budowli

13

Potrzebujemy rozwiązania obsługującego nazwę aplikacji z lokalizacją (dla wielu języków). Testowałem z rozwiązaniem @Nick Unuchek, ale kompilacja się nie powiodła (nie znaleziono @ string /). mała zmiana, aby naprawić ten błąd: plik build.gradle:

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 ]
        }

    }

wartości \ 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>

Na przykład gra taka jak „Need for Speed” nigdy nie będzie nazywana w Niemczech „Bedürfnis nach Geschwindigkeit”. Chyba że jest to zdzierstwo od wątpliwego programisty ...
— Niesamowity styczeń

To działa. Dziękuję bardzo. Jednak w moim przypadku, muszę dodać 1 tools:replace="android:label"w applicationwAndroidManifest
— Phan Van Linh


2

Możesz używać strings.xmlw różnych folderach, zobacz wartości oddzielnych ciągów dla systemu Android dla kompilacji do wydania i debugowania .

Więc utwórz ten plik:

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

Następnie wklej go do folderów app\src\debug\res\values\i app\src\release\res\values\. Zastąp tekst „Nazwa Twojej aplikacji” w plikach debugowania i zwalniania. Usuń app_nameelement z strings.xmlwapp\src\main\res\values\ folderze.

W AndroidManifestbędziesz miał to samo

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

Żadnych zmian. Nawet jeśli dodałeś bibliotekę z jej AndroidManifestplikiem i strings.xml.


1

Ponieważ autor prosi o zrobienie tego w Gradle , możemy założyć, że chce to zrobić w skrypcie, a nie w plikach konfiguracyjnych. Ponieważ zarówno Android Studio, jak i Gradle zostały mocno zaktualizowane i zmodyfikowane w ciągu ostatniego roku (~ 2018), wszystkie inne powyższe odpowiedzi wydają się nadmiernie wykrzywione. Najłatwiejszym sposobem jest dodanie następujących elementów do 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"
        }
    }
}
Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.