Auf dieser Seite erfahren Sie, wie Sie Build-Varianten für verschiedene Versionen Ihrer App aus einem einzigen Projekt erstellen um Ihre Abhängigkeiten und das Signieren von Konfigurationen richtig zu verwalten.
Jede Build-Variante steht für eine andere Version Ihrer App, die die Sie erstellen können. Vielleicht möchten Sie eine Version Ihrer App das für eine begrenzte Anzahl von Inhalten kostenlos ist, und eine kostenpflichtige Version, enthält mehr. Sie können auch verschiedene Versionen Ihrer App erstellen, die auf verschiedene Geräte, je nach API-Level oder anderen Gerätevarianten.
Build-Varianten sind das Ergebnis von Gradle. zum Kombinieren von Einstellungen, Code und Ressourcen, die in Ihrem und Produktgeschmack zu erstellen. Obwohl Sie keine Build-Varianten konfigurieren, konfigurieren Sie die Build-Typen und Produkt-Geschmacksrichtungen, aus denen sie bestehen.
Beispiel: Eine „Demo“ Produktgeschmack kann bestimmte Merkmale angeben.
und Geräteanforderungen wie benutzerdefinierter Quellcode, Ressourcen und Mindestanforderungen
API-Ebenen, während die "Debug"- Mit build type werden verschiedene Build- und
Einstellungen für die Paketerstellung, wie etwa
Debug-Optionen und Signaturschlüssel. Die
die diese beiden
Build-Varianten kombiniert, Version deiner App. Außerdem enthält sie ein
Kombination der in der Demo enthaltenen Konfigurationen und Ressourcen
Produktsortiment, „debug“ Build-Typ und main/
-Quellsatz.
Build-Typen konfigurieren
Sie können Build-Typen in android
erstellen und konfigurieren
der Datei build.gradle.kts
auf Modulebene. Wenn Sie
ein neues Modul installiert, erstellt Android Studio automatisch den Debug- und Release-Build
Typen. Obwohl der Debug-Build-Typ nicht in der Build-Konfiguration angezeigt wird
wird sie von Android Studio mit debuggable
true
konfiguriert. So kannst du Fehler in der App auf sicheren Android-Geräten
Konfiguriert die App-Signatur mit einem generischen Schlüsselspeicher für die Fehlerbehebung.
Sie können den Debug-Build-Typ in Ihre Konfiguration aufnehmen, wenn Sie
oder bestimmte Einstellungen ändern. Im folgenden Beispiel wird ein
applicationIdSuffix
für den Build-Typ der Fehlerbehebung und konfiguriert
ein „Staging“ Build-Typ, der mit Einstellungen aus dem Debug-Build-Typ initialisiert wird:
Kotlin
android { defaultConfig { manifestPlaceholders["hostName"] = "www.example.com" ... } buildTypes { getByName("release") { isMinifyEnabled = true proguardFiles(getDefaultProguardFile("proguard-android.txt"), "proguard-rules.pro") } getByName("debug") { applicationIdSuffix = ".debug" isDebuggable = true } /** * The `initWith` property lets you copy configurations from other build types, * then configure only the settings you want to change. This one copies the debug build * type, and then changes the manifest placeholder and application ID. */ create("staging") { initWith(getByName("debug")) manifestPlaceholders["hostName"] = "internal.example.com" applicationIdSuffix = ".debugStaging" } } }
Cool
android { defaultConfig { manifestPlaceholders = [hostName:"www.example.com"] ... } buildTypes { release { minifyEnabled true proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } debug { applicationIdSuffix ".debug" debuggable true } /** * The `initWith` property lets you copy configurations from other build types, * then configure only the settings you want to change. This one copies the debug build * type, and then changes the manifest placeholder and application ID. */ staging { initWith debug manifestPlaceholders = [hostName:"internal.example.com"] applicationIdSuffix ".debugStaging" } } }
Hinweis:Wenn Sie Änderungen an einer Build-Konfigurationsdatei vornehmen, Android Studio erfordert, dass Sie Ihr Projekt mit dem neuen Konfiguration. Klicken Sie zum Synchronisieren Ihres Projekts auf Jetzt synchronisieren. in der Benachrichtigungsleiste, die erscheint, wenn Sie eine Änderung vornehmen oder auf Projekt synchronisieren aus. Wenn Android Studio erkennt eventuelle Fehler in Ihrer Konfiguration, Im Fenster Nachrichten wird das Problem beschrieben.
Weitere Informationen zu allen Attributen, die Sie mit Build-Typen konfigurieren können,
Lesen Sie die
BuildType
-Referenz.
Produktgeschmacksrichtungen konfigurieren
Das Erstellen von Produkt-Geschmacksrichtungen ähnelt dem Erstellen von Build-Typen. Fügen Sie Produktgeschmack
productFlavors
-Block in Ihrer Build-Konfiguration fest und enthält die gewünschten Einstellungen.
Die Produktsorten unterstützen die gleichen Eigenschaften wie
defaultConfig
, weil: defaultConfig
gehört tatsächlich zum
<ph type="x-smartling-placeholder"></ph>
ProductFlavor
. Das bedeutet, dass Sie die Grundlage
Konfiguration für alle Geschmacksrichtungen im defaultConfig
-Block und
jeder Flavor kann einen dieser Standardwerte ändern, z. B. applicationId
. Bis
Weitere Informationen zur Anwendungs-ID finden Sie unter
Legen Sie die Anwendungs-ID fest.
Hinweis:Sie müssen trotzdem noch einen Paketnamen mithilfe des
package
in der Manifestdatei main/
. Sie müssen auch diese
Paketnamen in Ihrem Quellcode, um auf die R
-Klasse zu verweisen oder alle Fehler aufzulösen,
der relativen Aktivität
oder der Registrierung des Dienstes. So können Sie
applicationId
, um jedem Produktgeschmack eine eindeutige ID für
Paketerstellung und Verteilung, ohne den Quellcode ändern zu müssen.
Alle Geschmacksrichtungen müssen zu einer benannten Geschmacksdimension gehören. Dies ist eine Gruppe von Produktgeschmack. Sie müssen alle Geschmacksrichtungen einer Geschmacksdimension zuordnen. Andernfalls erhalten Sie den folgenden Build-Fehler.
Error: All flavors must now belong to a named flavor dimension. The flavor 'flavor_name' is not assigned to a flavor dimension.
Wenn ein bestimmtes Modul nur eine Flavor-Dimension angibt, wird das Android-Gradle-Plug-in weist dieser Dimension alle Varianten des Moduls zu.
<ph type="x-smartling-placeholder">
Im folgenden Codebeispiel wird eine Flavor-Dimension namens „version“ erstellt und fügt
„Demo“ und „vollständig“ Produktgeschmack. Diese Geschmacksrichtungen haben ihre eigene
<ph type="x-smartling-placeholder"></ph>
applicationIdSuffix
und
versionNameSuffix
:
Kotlin
android { ... defaultConfig {...} buildTypes { getByName("debug"){...} getByName("release"){...} } // Specifies one flavor dimension. flavorDimensions += "version" productFlavors { create("demo") { // Assigns this product flavor to the "version" flavor dimension. // If you are using only one dimension, this property is optional, // and the plugin automatically assigns all the module's flavors to // that dimension. dimension = "version" applicationIdSuffix = ".demo" versionNameSuffix = "-demo" } create("full") { dimension = "version" applicationIdSuffix = ".full" versionNameSuffix = "-full" } } }
Cool
android { ... defaultConfig {...} buildTypes { debug{...} release{...} } // Specifies one flavor dimension. flavorDimensions "version" productFlavors { demo { // Assigns this product flavor to the "version" flavor dimension. // If you are using only one dimension, this property is optional, // and the plugin automatically assigns all the module's flavors to // that dimension. dimension "version" applicationIdSuffix ".demo" versionNameSuffix "-demo" } full { dimension "version" applicationIdSuffix ".full" versionNameSuffix "-full" } } }
Hinweis:Wenn Sie eine alte App haben, die vor dem
August 2021), die Sie über APKs bei Google Play vertreiben, um Ihre App mit mehreren APKs zu vertreiben.
in Google Play, weise denselben Wert applicationId
zu.
auf alle Varianten angewendet und jeder Variante eine andere
versionCode
Zum Verteilen
als separate Apps in Google Play erstellt haben, müssen Sie eine
verschiedene applicationId
für jede Variante.
Nachdem Sie Ihre Produkt-Geschmacksrichtungen erstellt und konfiguriert haben, klicken Sie auf Synchronisieren
Now (Jetzt) in der Benachrichtigungsleiste. Nach Abschluss der Synchronisierung
erstellt automatisch Build-Varianten auf der Grundlage Ihrer Build-Typen und Ihres Produkts
Geschmacksrichtungen und benennt sie nach
<product-flavor><Build-Type>
Wenn Sie beispielsweise
hat „Demo“ erstellt und „vollständig“ Produktgeschmack und die Standardeinstellung beibehalten
„Debug“ und
"veröffentlichung" Build-Typen erstellt Gradle die folgenden Build-Varianten:
-
demoDebug
-
demoRelease
-
fullDebug
-
fullRelease
Um eine Build-Variante auszuwählen, gehen Sie zu Build > Wählen Sie Build-Variante und dann eine Build-Variante aus. Um jede Build-Variante mit ihren eigenen Funktionen und Ressourcen, müssen Sie Quelle erstellen und verwalten , wie auf dieser Seite beschrieben.
Anwendungs-ID für Build-Varianten ändern
Wenn Sie ein APK oder AAB für Ihre App erstellen, taggen die Build-Tools die App mit dem
Im defaultConfig
-Block der build.gradle.kts
definierte Anwendungs-ID
wie im folgenden Beispiel gezeigt. Wenn Sie jedoch verschiedene Versionen Ihrer
App als separate Einträge im Google Play Store angezeigt, z. B. als „kostenlos“ und „pro“
Version erstellen, müssen Sie separate
Build-Varianten mit unterschiedlichen
Anwendungs-ID
Definieren Sie in diesem Fall jede Build-Variante als
Produktgeschmack. Für jede Geschmacksrichtung
innerhalb des productFlavors
-Blocks können Sie applicationId
neu definieren
Eigenschaft oder Sie können stattdessen ein Segment an die Standardanwendungs-ID anhängen.
mit applicationIdSuffix
, wie hier gezeigt:
Kotlin
android { defaultConfig { applicationId = "com.example.myapp" } productFlavors { create("free") { applicationIdSuffix = ".free" } create("pro") { applicationIdSuffix = ".pro" } } }
Cool
android { defaultConfig { applicationId "com.example.myapp" } productFlavors { free { applicationIdSuffix ".free" } pro { applicationIdSuffix ".pro" } } }
Dann wird die Anwendungs-ID für die Produktgeschmack ist „com.beispiel.meineapp.kostenlos“.
Sie können auch applicationIdSuffix
verwenden, um ein Segment basierend auf
Ihren Build-Typ aus:
Kotlin
android { ... buildTypes { getByName("debug") { applicationIdSuffix = ".debug" } } }
Cool
android { ... buildTypes { debug { applicationIdSuffix ".debug" } } }
Da Gradle die Build-Typkonfiguration nach dem Produkt-Flavor anwendet, Anwendungs-ID für „free debug“ Build-Variante ist „com.example.myapp.free.debug“. Dies ist nützlich, wenn Sie sowohl die Debug und Release-Build auf demselben Gerät ausgeführt werden, da keine zwei Apps dieselbe Anwendungs-ID.
Wenn Sie eine alte App haben, die vor August erstellt wurde 2021), die Sie über APKs bei Google Play vertreiben und denselben App-Eintrag für folgende Zwecke verwenden möchten: mehrere APKs zu verteilen, die die jeweils auf eine andere Gerätekonfiguration ausgerichtet sind, z. B. das API-Level, müssen Sie für jede Build-Variante dieselbe App-ID verwenden, APK ein anderesversionCode
. Weitere Informationen finden Sie in den
Unterstützung mehrerer APK-Dateien. Wird veröffentlicht
AABs sind davon nicht betroffen, da ein einzelnes Artefakt mit
Versionscode und Anwendungs-ID.
Tipp:Wenn Sie auf die Anwendungs-ID in der
Manifestdatei verwenden, können Sie den Platzhalter ${applicationId}
in einer beliebigen
Manifest-Attribut. Während eines Builds ersetzt Gradle dieses Tag durch das eigentliche
Anwendungs-ID. Weitere Informationen finden Sie unter Build einfügen.
in das Manifest einfügen.
Kombinieren Sie mehrere Produktsorten mit Geschmacksdimensionen
In einigen Fällen möchten Sie vielleicht Konfigurationen aus mehreren Produkten kombinieren Geschmacksrichtungen. Beispielsweise können Sie verschiedene Konfigurationen für die "voll" und „Demo“ Geschmacksrichtungen, die auf dem API-Level basieren. Gehen Sie dazu wie folgt vor: Mit dem Android-Gradle-Plug-in können Sie mehrere Gruppen von Produkt-Geschmacksrichtungen für Geschmack erstellen. Dimensionen.
Beim Erstellen Ihrer App kombiniert Gradle ein Produkt Flavor-Konfiguration aus jeder von Ihnen definierten Geschmacksdimension sowie einer Build-Typkonfiguration, um die endgültige Build-Variante zu erstellen. Gradle erkennt Produktsorten kombinieren, die zur selben Geschmacksdimension gehören.
Im folgenden Codebeispiel wird die Methode
<ph type="x-smartling-placeholder"></ph>
flavorDimensions
, um einen Modus zu erstellen Geschmack
zum Gruppieren der vollständigen und „Demo“ Produktvarianten und eine "API" Geschmack
Dimension zum Gruppieren von Produktvarianten nach API-Ebene:
Kotlin
android { ... buildTypes { getByName("debug") {...} getByName("release") {...} } // Specifies the flavor dimensions you want to use. The order in which you // list the dimensions determines their priority, from highest to lowest, // when Gradle merges variant sources and configurations. You must assign // each product flavor you configure to one of the flavor dimensions. flavorDimensions += listOf("api", "mode") productFlavors { create("demo") { // Assigns this product flavor to the "mode" flavor dimension. dimension = "mode" ... } create("full") { dimension = "mode" ... } // Configurations in the "api" product flavors override those in "mode" // flavors and the defaultConfig block. Gradle determines the priority // between flavor dimensions based on the order in which they appear next // to the flavorDimensions property, with the first dimension having a higher // priority than the second, and so on. create("minApi24") { dimension = "api" minSdk = 24 // To ensure the target device receives the version of the app with // the highest compatible API level, assign version codes in increasing // value with API level. versionCode = 30000 + (android.defaultConfig.versionCode ?: 0) versionNameSuffix = "-minApi24" ... } create("minApi23") { dimension = "api" minSdk = 23 versionCode = 20000 + (android.defaultConfig.versionCode ?: 0) versionNameSuffix = "-minApi23" ... } create("minApi21") { dimension = "api" minSdk = 21 versionCode = 10000 + (android.defaultConfig.versionCode ?: 0) versionNameSuffix = "-minApi21" ... } } } ...
Cool
android { ... buildTypes { debug {...} release {...} } // Specifies the flavor dimensions you want to use. The order in which you // list the dimensions determines their priority, from highest to lowest, // when Gradle merges variant sources and configurations. You must assign // each product flavor you configure to one of the flavor dimensions. flavorDimensions "api", "mode" productFlavors { demo { // Assigns this product flavor to the "mode" flavor dimension. dimension "mode" ... } full { dimension "mode" ... } // Configurations in the "api" product flavors override those in "mode" // flavors and the defaultConfig block. Gradle determines the priority // between flavor dimensions based on the order in which they appear next // to the flavorDimensions property, with the first dimension having a higher // priority than the second, and so on. minApi24 { dimension "api" minSdkVersion 24 // To ensure the target device receives the version of the app with // the highest compatible API level, assign version codes in increasing // value with API level. versionCode 30000 + android.defaultConfig.versionCode versionNameSuffix "-minApi24" ... } minApi23 { dimension "api" minSdkVersion 23 versionCode 20000 + android.defaultConfig.versionCode versionNameSuffix "-minApi23" ... } minApi21 { dimension "api" minSdkVersion 21 versionCode 10000 + android.defaultConfig.versionCode versionNameSuffix "-minApi21" ... } } } ...
Die Anzahl der von Gradle erstellten Build-Varianten entspricht dem Produkt des Anzahl der Geschmacksrichtungen in jeder Geschmacksdimension und die Anzahl der Build-Typen, die Sie konfigurieren. Wenn Gradle jede Build-Variante oder die entsprechenden Artefakte benennt, kann das Produkt Flavor-Sorten, die zur Geschmacksdimension höherer Priorität gehören, erscheinen zuerst, durch Dimensionen mit niedrigerer Priorität, gefolgt vom Build-Typ.
Mit der vorherigen Build-Konfiguration als Beispiel erstellt haben, erstellt Gradle insgesamt Erstellen Sie Varianten mit folgendem Namensschema:
- Build-Variante:
[minApi24, minApi23, minApi21][Demo, Full][Debug, Release]
- Entsprechendes APK:
app-[minApi24, minApi23, minApi21]-[demo, full]-[debug, release].apk
- Beispiel:
- Build-Variante:
minApi24DemoDebug
- Entsprechendes APK:
app-minApi24-demo-debug.apk
Zusätzlich zu den Quellsatz-Verzeichnissen, die Sie für jedes einzelne
Produkt-Flavor und Build-Variante erstellt haben, können Sie auch Quellsatzverzeichnisse
für jede Kombination von Produktaromen zu berechnen. Sie können beispielsweise
und fügen Sie dem Verzeichnis src/demoMinApi24/java/
Java-Quellen hinzu.
und Gradle verwendet diese Quellen nur beim Erstellen einer Variante, die
beiden Produktsorten.
Quell-Sets, die Sie für Produkt-Flavor erstellen Kombinationen haben eine höhere Priorität als Quellsätze der jeweiligen Kombination. den Geschmack des jeweiligen Produkts. Weitere Informationen zu Quellsätzen und dazu, wie Gradle führt, lesen Sie den Abschnitt über das Erstellen Quellsätzen.
Varianten filtern
Gradle erstellt eine Build-Variante für jede mögliche Kombination des Produkts
und Build-Typen, die Sie konfigurieren. Möglicherweise gibt es jedoch
erstellen Sie Varianten, die Sie nicht benötigen oder im
in den Kontext Ihres Projekts ein. Um bestimmte Build-Variantenkonfigurationen zu entfernen,
Erstellen Sie einen Variantenfilter in der build.gradle.kts
auf Modulebene
-Datei.
Nehmen wir als Beispiel die Build-Konfiguration
aus dem vorherigen Abschnitt
Angenommen, Sie planen, für die Demo nur API-Levels 23 und höher zu unterstützen.
Version der App. Sie können die
<ph type="x-smartling-placeholder"></ph>
variantFilter
blockieren, um alle Build-Varianten herauszufiltern
Konfigurationen, die die „minApi21“ und „Demo“ Produktgeschmack:
Kotlin
android { ... buildTypes {...} flavorDimensions += listOf("api", "mode") productFlavors { create("demo") {...} create("full") {...} create("minApi24") {...} create("minApi23") {...} create("minApi21") {...} } } androidComponents { beforeVariants { variantBuilder -> // To check for a certain build type, use variantBuilder.buildType == "<buildType>" if (variantBuilder.productFlavors.containsAll(listOf("api" to "minApi21", "mode" to "demo"))) { // Gradle ignores any variants that satisfy the conditions above. variantBuilder.enable = false } } } ...
Cool
android { ... buildTypes {...} flavorDimensions "api", "mode" productFlavors { demo {...} full {...} minApi24 {...} minApi23 {...} minApi21 {...} } variantFilter { variant -> def names = variant.flavors*.name // To check for a certain build type, use variant.buildType.name == "<buildType>" if (names.contains("minApi21") && names.contains("demo")) { // Gradle ignores any variants that satisfy the conditions above. setIgnore(true) } } } ...
Fügen Sie der Build-Konfiguration einen Variantenfilter hinzu und klicken Sie auf Synchronisieren Jetzt ignoriert Gradle in der Benachrichtigungsleiste alle Build-Varianten, die den Bedingungen vor, die Sie angeben. Die Build-Varianten werden nicht mehr im Menü angezeigt wenn Sie auf Build > Wählen Sie in der Menüleiste „Build-Variante“ aus. oder Build-Varianten in in der Symbolleiste des Tool-Fensters.
Quellsätze erstellen
Standardmäßig erstellt Android Studio die main/
Quellsatz und Verzeichnisse für
alles, was Sie für alle Ihre Build-Varianten freigeben möchten. Sie haben jedoch
Sie können neue Quellsätze erstellen, um genau zu steuern, welche Dateien Gradle kompiliert und
für bestimmte Build-Typen, Produkt-Geschmacksrichtungen, Kombinationen
Produktgeschmack (bei Verwendung von Geschmacksrichtungen"
Dimensionen) und erstellen Varianten.
Sie können beispielsweise grundlegende
im main/
-Quellsatz enthalten und Produkt-Flavor verwendet werden.
Quellsätze, um das Branding deiner App für verschiedene Kunden zu ändern, oder
enthalten spezielle Berechtigungen und Logging-Funktionen nur für Build-Varianten
die den Build-Typ "Debug" verwenden.
Gradle geht davon aus, dass Quelldateien und -verzeichnisse in einem bestimmten
ähnlich dem main/
-Quellsatz. Beispiel: Gradle
erwartet Kotlin- oder Java-Klassendateien, die für Ihre „debug“- den entsprechenden Build-Typ
die sich im Verzeichnis src/debug/kotlin/
oder src/debug/java/
befinden.
Das Android-Gradle-Plug-in bietet eine nützliche Gradle-Aufgabe, wie Sie Ihre Dateien für jeden Ihrer Build-Typen, jedes Produkt Geschmacksrichtungen und Varianten entwickeln. Das folgende Beispiel aus der Aufgabenausgabe beschreibt, wo Gradle erwartet, dass er bestimmte Dateien für die Fehlerbehebung Build Typ:
------------------------------------------------------------ Project :app ------------------------------------------------------------ ... debug ---- Compile configuration: debugCompile build.gradle name: android.sourceSets.debug Java sources: [app/src/debug/java] Kotlin sources: [app/src/debug/kotlin, app/src/debug/java] Manifest file: app/src/debug/AndroidManifest.xml Android resources: [app/src/debug/res] Assets: [app/src/debug/assets] AIDL sources: [app/src/debug/aidl] RenderScript sources: [app/src/debug/rs] JNI sources: [app/src/debug/jni] JNI libraries: [app/src/debug/jniLibs] Java-style resources: [app/src/debug/resources]
So rufen Sie diese Ausgabe auf:
- Klicken Sie in der Leiste des Toolfensters auf Gradle.
Gehen Sie zu MyApplication > Tasks > Android und Doppelklicken Sie auf sourceSets.
Damit Sie den Ordner Tasks sehen können, müssen Sie Gradle die Funktion zum Erstellen des Aufgabenliste während der Synchronisierung. Führen Sie dazu die folgenden Schritte aus:
- Klicken Sie auf Datei > Einstellungen > Experimentell (Android Studio > Einstellungen > Experimentell) unter macOS).
- Deaktivieren Sie die Option Nicht zulassen Gradle-Aufgabenliste während der Gradle-Synchronisierung erstellen
- Nachdem Gradle die Aufgabe ausgeführt hat, wird das Fenster Run (Ausführen) geöffnet, in dem die .
Hinweis:Die Aufgabenausgabe zeigt Ihnen auch, wie Quellsätze organisiert werden.
für Dateien, die Sie zum Ausführen von Tests für Ihre App verwenden möchten, z. B.
test/
und androidTest/
Quellsätze testen.
Wenn Sie eine neue Build-Variante erstellen, wird die Quelle nicht in Android Studio erstellt.
Verzeichnisse für Sie einrichten, aber es gibt Ihnen einige Optionen, die Ihnen dabei helfen können. Für
Beispiel, um nur das Verzeichnis java/
für Ihr „debug“ zu erstellen
Build-Typ:
- Öffnen Sie den Bereich Projekt und wählen Sie das Projekt Projektansicht aus.
- Zu
MyProject/app/src/
navigieren - Klicken Sie mit der rechten Maustaste auf das Verzeichnis
src
und wählen Sie Neu > Verzeichnis. - Wählen Sie im Menü unter Gradle Source Sets die Option full/java.
- Drücken Sie die Eingabetaste.
Android Studio erstellt ein Quellsatzverzeichnis für Ihren Debug-Build-Typ und
erstellt dann darin das Verzeichnis java/
. Alternativ können Sie
Android Studio kann die Verzeichnisse für Sie erstellen, wenn Sie eine neue Datei zu
Ihr Projekt für eine bestimmte Build-Variante.
Um beispielsweise eine XML-Datei mit Werten für Ihr "debug" zu erstellen, Build-Typ:
- Klicken Sie im Bereich Projekt mit der rechten Maustaste auf
src
. und wählen Sie New > (Neu) > XML > Values XML File. - Geben Sie den Namen für die XML-Datei ein oder behalten Sie den Standardnamen bei.
- Wählen Sie im Menü neben Target Source Set (Zielquellensatz) die Option debug
- Klicken Sie auf Fertig.
Da die Funktion zur Fehlerbehebung als Zielquellensatz angegeben wurde, Android Studio erstellt automatisch die erforderlichen Verzeichnisse, erstellt die XML-Datei. Die resultierende Verzeichnisstruktur sieht so aus: Abbildung 1.
Das Symbol aktiver Quellensätze weist einen grünen Indikator darauf hin, dass sie aktiv sind. Die
Das debug
-Quellset hat das Suffix [main]
, um anzuzeigen, dass es zusammengeführt wird
in den main
-Quellensatz ein.
Mit demselben Verfahren können Sie auch Quellsatzverzeichnisse für
Produktvarianten wie src/demo/
und Build-Varianten wie
src/demoDebug/
. Außerdem können Sie Testquellsätze erstellen,
die auf bestimmte Build-Varianten ausgerichtet sind, z. B.
src/androidTestDemoDebug/
Weitere Informationen finden Sie im
Quellsätze testen.
Standardkonfigurationen des Quellsatzes ändern
Wenn Sie Quellen haben, die nicht in der Standardquellsatzdatei organisiert sind
Struktur zu erstellen, die Gradle erwartet, wie im vorherigen Abschnitt über
Erstellen von Quellsätzen haben, können Sie die Methode
<ph type="x-smartling-placeholder"></ph>
sourceSets
, um zu ändern, wo Gradle Daten sammelt
-Dateien für jede Komponente eines Quellsatzes.
Der sourceSets
-Block muss
im android
-Block. Sie müssen die
Quelldateien Sie müssen Gradle nur die Pfade relativ zum
Modulebene build.gradle.kts
, in der Gradle
Dateien für jede Quellsatzkomponente finden. Um zu erfahren, welche Komponenten
und ob sie mehreren Dateien oder Verzeichnissen
zugeordnet werden können,
Weitere Informationen finden Sie in der API-Referenz für das Android Gradle Plugin.
Im folgenden Codebeispiel werden Quellen aus dem Verzeichnis app/other/
zugeordnet
auf bestimmte Komponenten des main
-Quellsatzes an und ändert
Stammverzeichnis des androidTest
-Quellsatzes:
Kotlin
android { ... // Encapsulates configurations for the main source set. sourceSets.getByName("main") { // Changes the directory for Java sources. The default directory is // 'src/main/java'. java.setSrcDirs(listOf("other/java")) // If you list multiple directories, Gradle uses all of them to collect // sources. Because Gradle gives these directories equal priority, if // you define the same resource in more than one directory, you receive an // error when merging resources. The default directory is 'src/main/res'. res.setSrcDirs(listOf("other/res1", "other/res2")) // Note: Avoid specifying a directory that is a parent to one // or more other directories you specify. For example, avoid the following: // res.srcDirs = ['other/res1', 'other/res1/layouts', 'other/res1/strings'] // Specify either only the root 'other/res1' directory or only the // nested 'other/res1/layouts' and 'other/res1/strings' directories. // For each source set, you can specify only one Android manifest. // By default, Android Studio creates a manifest for your main source // set in the src/main/ directory. manifest.srcFile("other/AndroidManifest.xml") ... } // Create additional blocks to configure other source sets. sourceSets.getByName("androidTest") { // If all the files for a source set are located under a single root // directory, you can specify that directory using the setRoot property. // When gathering sources for the source set, Gradle looks only in locations // relative to the root directory you specify. For example, after applying the // configuration below for the androidTest source set, Gradle looks for Java // sources only in the src/tests/java/ directory. setRoot("src/tests") ... } } ...
Cool
android { ... sourceSets { // Encapsulates configurations for the main source set. main { // Changes the directory for Java sources. The default directory is // 'src/main/java'. java.srcDirs = ['other/java'] // If you list multiple directories, Gradle uses all of them to collect // sources. Because Gradle gives these directories equal priority, if // you define the same resource in more than one directory, you receive an // error when merging resources. The default directory is 'src/main/res'. res.srcDirs = ['other/res1', 'other/res2'] // Note: Avoid specifying a directory that is a parent to one // or more other directories you specify. For example, avoid the following: // res.srcDirs = ['other/res1', 'other/res1/layouts', 'other/res1/strings'] // Specify either only the root 'other/res1' directory or only the // nested 'other/res1/layouts' and 'other/res1/strings' directories. // For each source set, you can specify only one Android manifest. // By default, Android Studio creates a manifest for your main source // set in the src/main/ directory. manifest.srcFile 'other/AndroidManifest.xml' ... } // Create additional blocks to configure other source sets. androidTest { // If all the files for a source set are located under a single root // directory, you can specify that directory using the setRoot property. // When gathering sources for the source set, Gradle looks only in locations // relative to the root directory you specify. For example, after applying the // configuration below for the androidTest source set, Gradle looks for Java // sources only in the src/tests/java/ directory. setRoot 'src/tests' ... } } } ...
Beachten Sie, dass ein Quellverzeichnis nur zu einem Quellsatz gehören kann. Beispielsweise können Sie das
Dieselbe Testquellen mit den Quellsätzen test
und androidTest
. Dieses
liegt, weil Android Studio separate IntelliJ-Module für jeden Quellsatz erstellt und keine
duplizierten Inhaltsstammen in verschiedenen Quellsätzen.
Mit Quellsätzen erstellen
Sie können Quellsatzverzeichnisse verwenden, um den Code und die Ressourcen zu enthalten, die nur mit bestimmten Konfigurationen gepackt werden sollen. Wenn Sie zum Beispiel „demoDebug“ erstellen, Build-Variante, das das Kreuzprodukt einer „Demo“ Produktsortierung und „Fehlerbehebung“ den Build-Typ, den Gradle betrachtet, diese Verzeichnisse und gibt ihnen die folgende Priorität:
-
src/demoDebug/
(Variantenquellensatz erstellen) -
src/debug/
(Build-Typ-Quellsatz) -
src/demo/
(Menge der Geschmacksquelle des Produkts) -
src/main/
(Hauptquellen festgelegt)
Quellsätze, die für Kombinationen von Produkt-Geschmacksrichtungen erstellt werden, müssen alle Geschmacksdimensionen enthalten. Der Quellsatz der Build-Variante muss beispielsweise die Kombination aus dem Build-Typ und allen Flavors sein Dimensionen. Zusammenführen von Code und Ressourcen mit Ordnern, die mehrere, aber nicht alle abdecken Flavor-Dimensionen werden nicht unterstützt.
Wenn Sie mehrere Produkte
Geschmacksrichtungen bestimmt, wird die Priorität zwischen den Produktaromen durch den Geschmack bestimmt.
Dimension zuordnen, zu der sie gehören. Wenn Sie Flavor-Dimensionen mit dem Attribut
<ph type="x-smartling-placeholder"></ph>
android.flavorDimensions
-Property, Produktsorten, die
zur ersten Dimension der Geschmacksrichtung gehören, die Sie auflisten, eine höhere Priorität haben als
zur zweiten Geschmacksdimension usw. gehören. Außerdem
und Quellsätzen, die Sie für Kombinationen von Produktgeschmacks erstellen,
Priorität als Quellsätzen, die zu einem einzelnen Produkt-Geschmacks gehören.
Anhand der Prioritätsreihenfolge wird bestimmt, welche Quelle eine höhere
Priorität haben, wenn Gradle
Code und Ressourcen kombiniert. Da die demoDebug/
Das Quellsatzverzeichnis enthält wahrscheinlich Dateien, die für diesen Build spezifisch sind
Variante, wenn demoDebug/
eine Datei enthält, die auch in
debug/
verwendet Gradle die Datei im demoDebug/
Quellsatz. Ebenso stellt Gradle Dateien mit dem Build-Typ und dem Produkt-Flavor zur Verfügung.
Quelle legt eine höhere Priorität fest als dieselben Dateien in main/
.
Gradle berücksichtigt diese Prioritätsreihenfolge bei der Anwendung der folgenden Build-Regeln:
- Der gesamte Quellcode in den Verzeichnissen
kotlin/
oderjava/
ist kompiliert. zu einer einzigen Ausgabe kombinieren.Hinweis:Für eine bestimmte Build-Variante löst Gradle einen Build aus. wenn zwei oder mehr Quellsatz-Verzeichnisse gefunden werden, Kotlin- oder Java-Klasse, So können Sie z. B. beim Erstellen einer Debugging-App sowohl
src/debug/Utility.kt
als auchsrc/main/Utility.kt
, da Gradle sowohl während des Build-Prozesses in diese Verzeichnisse ein und löst eine "duplizierte Klasse" Fehler. Wenn Sie verschiedeneUtility.kt
-Versionen für verschiedene Build-Typen haben, muss jeder Build-Typ eine eigene Version von der Datei und nicht in denmain/
-Quellsatz. - Manifeste werden zu einem einzigen Manifest zusammengeführt. Priorität ist zugewiesen in derselben Reihenfolge wie in der Liste im vorherigen Beispiel. Manifest-Einstellungen für einen Build die Manifest-Einstellungen für eine Produktvariante überschreiben usw. Weitere Informationen Weitere Informationen zum Zusammenführen von Manifesten
- Dateien in den
values/
-Verzeichnissen werden zusammengeführt miteinander verbinden. Wenn zwei Dateien den gleichen Namen haben, zum Beispiel zweistrings.xml
Dateien haben, wird die Priorität in derselben Reihenfolge wie die Datei -Liste im vorherigen Beispiel. Das sind Werte, die in einer Datei im Quellsatz des Build-Typs definiert sind. die in derselben Datei definierten Werte für eine Produkt-Geschmacksrichtung überschreiben usw. - Ressourcen in den Verzeichnissen
res/
undasset/
verpackt sind. Wenn Ressourcen mit demselben Namen in zwei oder mehr Quellsätzen hat, wird die Priorität in der gleichen Reihenfolge wie die Liste angegeben. aus dem vorherigen Beispiel. - Gradle stellt Ressourcen und Manifeste in der Bibliothek bereit Modulabhängigkeiten beim Erstellen der App die niedrigste Priorität.
Abhängigkeiten deklarieren
Um eine Abhängigkeit für eine bestimmte Build-Variante oder
Testquellensatz,
den Namen der Build-Variante oder des Testquellensatzes vor dem Präfix
Implementation
, wie im folgenden Beispiel gezeigt:
Kotlin
dependencies { // Adds the local "mylibrary" module as a dependency to the "free" flavor. "freeImplementation"(project(":mylibrary")) // Adds a remote binary dependency only for local tests. testImplementation("junit:junit:4.12") // Adds a remote binary dependency only for the instrumented test APK. androidTestImplementation("com.android.support.test.espresso:espresso-core:3.5.1") }
Cool
dependencies { // Adds the local "mylibrary" module as a dependency to the "free" flavor. freeImplementation project(":mylibrary") // Adds a remote binary dependency only for local tests. testImplementation 'junit:junit:4.12' // Adds a remote binary dependency only for the instrumented test APK. androidTestImplementation 'com.android.support.test.espresso:espresso-core:3.5.1' }
Weitere Informationen zum Konfigurieren von Abhängigkeiten Siehe Build-Abhängigkeiten hinzufügen.
Variantensensitive Abhängigkeitsverwaltung verwenden
Das Android-Gradle-Plug-in 3.0.0 und höher enthält einen neuen Abhängigkeitsmechanismus, der automatisch
bei der Nutzung einer Bibliothek abgeglichen. Das bedeutet die debug
-Variante einer App
verwendet automatisch die debug
-Variante einer Bibliothek usw. Es funktioniert auch, wenn Sie
Flavors: Die freeDebug
-Variante einer App verbraucht die freeDebug
einer Bibliothek
Variante.
Damit das Plug-in Varianten genau abgleichen kann, müssen Sie Übereinstimmende Fallbacks bereitstellen, wie unter im folgenden Abschnitt für Fälle, in denen eine direkte Übereinstimmung nicht möglich ist.
Angenommen, Ihre App konfiguriert einen Build-Typ namens "Staging", aber einer der Bibliotheksabhängigkeiten nicht. Wenn das Plug-in versucht, das Staging-Objekt zu erstellen Version Ihrer App installiert, erkennt sie nicht, welche Version der Bibliothek verwendet werden soll, und Sie sehen eine Fehlermeldung zu:
Error:Failed to resolve: Could not resolve project :mylibrary. Required by: project :app
Build-Fehler im Zusammenhang mit dem Variantenabgleich beheben
Das Plug-in enthält DSL-Elemente, mit denen Sie steuern können, wie Gradle Probleme in bei denen eine direkte Variantenübereinstimmung zwischen einer App und einer Abhängigkeit nicht möglich ist.
Im Folgenden finden Sie eine Liste mit Problemen im Zusammenhang mit dem Abgleich von Abhängigkeiten, die bei verschiedenen Varianten berücksichtigt werden, und wie Sie mithilfe von DSL-Eigenschaften lösen:Deine App enthält einen Build-Typ, den es bei einer Bibliotheksabhängigkeit nicht gibt.
Ihre App enthält beispielsweise eine Staging- Build-Typ, aber eine Abhängigkeit umfasst nur „Debug“ und „Release“ Build-Typen.
Es gibt kein Problem, wenn eine Bibliotheksabhängigkeit einen Build enthält. die Ihre App nicht kann. Das liegt daran, dass das Plug-in -Anfragen, die einen Build-Typ aus der Abhängigkeit erstellen.
Verwenden Sie
matchingFallbacks
, um alternative Übereinstimmungen für einen bestimmten Build-Typ anzugeben. wie hier gezeigt:Kotlin
// In the app's build.gradle.kts file. android { buildTypes { getByName("debug") {} getByName("release") {} create("staging") { // Specifies a sorted list of fallback build types that the // plugin can try to use when a dependency does not include a // "staging" build type. You may specify as many fallbacks as you // like, and the plugin selects the first build type that's // available in the dependency. matchingFallbacks += listOf("debug", "qa", "release") } } }
Cool
// In the app's build.gradle file. android { buildTypes { debug {} release {} staging { // Specifies a sorted list of fallback build types that the // plugin can try to use when a dependency does not include a // "staging" build type. You may specify as many fallbacks as you // like, and the plugin selects the first build type that's // available in the dependency. matchingFallbacks = ['debug', 'qa', 'release'] } } }
Für eine bestimmte Geschmacksdimension, die sowohl in der App als auch in ihrer Bibliothek vorhanden ist enthält, enthält deine App Flavor-Varianten, die die Bibliothek nicht enthält.
Beispielsweise enthalten sowohl die Anwendung als auch die Bibliotheksabhängigkeiten eine „Stufe“. Flavor-Dimension. Die „Stufe“ in der App den Begriff „kostenlos“ enthält und „bezahlt“ Geschmacksrichtungen, aber Abhängigkeit enthält nur „demo“ und „bezahlt“ Geschmacksrichtungen für dieselbe Dimension.
Beachten Sie, dass für eine bestimmte Flavor-Dimension, die sowohl in der App als auch in ihrer Bibliothek vorhanden ist, Abhängigkeiten gibt es kein Problem, wenn eine Bibliothek einen Produkt-Flavor enthält, den Ihre App nicht. Das liegt daran, dass das Plug-in diese Flasche aus der Abhängigkeit nie anfordert.
Verwenden Sie
matchingFallbacks
, um alternative Übereinstimmungen für „free“ der App anzugeben. Produktgeschmack, wie hier gezeigt:Kotlin
// In the app's build.gradle.kts file. android { defaultConfig{ // Don't configure matchingFallbacks in the defaultConfig block. // Instead, specify fallbacks for a given product flavor in the // productFlavors block, as shown below. } flavorDimensions += "tier" productFlavors { create("paid") { dimension = "tier" // Because the dependency already includes a "paid" flavor in its // "tier" dimension, you don't need to provide a list of fallbacks // for the "paid" flavor. } create("free") { dimension = "tier" // Specifies a sorted list of fallback flavors that the plugin // can try to use when a dependency's matching dimension does // not include a "free" flavor. Specify as many // fallbacks as you like; the plugin selects the first flavor // that's available in the dependency's "tier" dimension. matchingFallbacks += listOf("demo", "trial") } } }
Cool
// In the app's build.gradle file. android { defaultConfig{ // Don't configure matchingFallbacks in the defaultConfig block. // Instead, specify fallbacks for a given product flavor in the // productFlavors block, as shown below. } flavorDimensions 'tier' productFlavors { paid { dimension 'tier' // Because the dependency already includes a "paid" flavor in its // "tier" dimension, you don't need to provide a list of fallbacks // for the "paid" flavor. } free { dimension 'tier' // Specifies a sorted list of fallback flavors that the plugin // can try to use when a dependency's matching dimension does // not include a "free" flavor. Specify as many // fallbacks as you like; the plugin selects the first flavor // that's available in the dependency's "tier" dimension. matchingFallbacks = ['demo', 'trial'] } } }
Eine Bibliotheksabhängigkeit umfasst eine Flavor-Dimension, die Ihre App nicht enthält.
Eine Bibliotheksabhängigkeit umfasst beispielsweise Flavors für eine „minApi“ Dimension, aber Ihre App enthält Geschmacksrichtungen nur für die "Stufe" Dimension. Wenn Sie die Methode "freeDebug" erstellen möchten, Version Ihrer Anwendung enthält, weiß das Plug-in nicht, ob das Plug-in "minApi23Debug" oder „minApi18Debug“ Version der Abhängigkeit.
Es gibt kein Problem, wenn Ihre App eine Flavor-Dimension enthält, die von einer Bibliothek die Abhängigkeit nicht. Das liegt daran, dass das Plug-in nur die Varianten der Dimensionen die in der Abhängigkeit vorhanden sind. Wenn eine Abhängigkeit beispielsweise keine Dimension für ABIs enthält, „freeX86Debug“ Ihrer App die Methode „freeDebug“ verwenden, Version der Abhängigkeit.
Verwenden Sie
missingDimensionStrategy
imdefaultConfig
-Block, um anzugeben, den Standard-Flavor für das Plug-in aus jeder fehlenden Dimension auszuwählen, wie in den folgenden Beispiel. Sie können Ihre Auswahl auch in denproductFlavors
überschreiben. -Block, sodass für jede Variante eine andere Abgleichsstrategie für eine fehlende Dimension angegeben werden kann.Kotlin
// In the app's build.gradle.kts file. android { defaultConfig{ // Specifies a sorted list of flavors that the plugin can try to use from // a given dimension. This tells the plugin to select the "minApi18" flavor // when encountering a dependency that includes a "minApi" dimension. // You can include additional flavor names to provide a // sorted list of fallbacks for the dimension. missingDimensionStrategy("minApi", "minApi18", "minApi23") // Specify a missingDimensionStrategy property for each // dimension that exists in a local dependency but not in your app. missingDimensionStrategy("abi", "x86", "arm64") } flavorDimensions += "tier" productFlavors { create("free") { dimension = "tier" // You can override the default selection at the product flavor // level by configuring another missingDimensionStrategy property // for the "minApi" dimension. missingDimensionStrategy("minApi", "minApi23", "minApi18") } create("paid") {} } }
Cool
// In the app's build.gradle file. android { defaultConfig{ // Specifies a sorted list of flavors that the plugin can try to use from // a given dimension. This tells the plugin to select the "minApi18" flavor // when encountering a dependency that includes a "minApi" dimension. // You can include additional flavor names to provide a // sorted list of fallbacks for the dimension. missingDimensionStrategy 'minApi', 'minApi18', 'minApi23' // Specify a missingDimensionStrategy property for each // dimension that exists in a local dependency but not in your app. missingDimensionStrategy 'abi', 'x86', 'arm64' } flavorDimensions 'tier' productFlavors { free { dimension 'tier' // You can override the default selection at the product flavor // level by configuring another missingDimensionStrategy property // for the 'minApi' dimension. missingDimensionStrategy 'minApi', 'minApi23', 'minApi18' } paid {} } }
Weitere Informationen findest du unter matchingFallbacks
.
und missingDimensionStrategy
in der DSL-Referenz für das Android-Gradle-Plug-in.
Signatureinstellungen konfigurieren
Gradle signiert nur das APK oder AAB Ihres Release-Builds, wenn Sie explizit ein Signaturkonfiguration für diesen Build. Falls Sie noch keinen Signaturschlüssel haben, Uploadschlüssel und Schlüsselspeicher generieren mit Android Studio.
So konfigurieren Sie die Signaturkonfigurationen für Ihren Release-Build-Typ manuell mithilfe von Gradle-Build-Konfigurationen:
- Erstellen Sie einen Schlüsselspeicher. Ein Schlüsselspeicher ist eine Binärdatei. die eine Reihe privater Schlüssel enthält. Bewahren Sie Ihren Schlüsselspeicher an einem sicheren Ort auf. an einem sicheren Ort auf.
- Erstellen Sie einen privaten Schlüssel. Ein privater Schlüssel wird zum Signieren Ihrer App verwendet und wird niemals in die App integriert oder an nicht autorisierte Dritte weitergegeben.
-
Signaturkonfiguration zum
build.gradle.kts
auf Modulebene hinzufügen Datei:Kotlin
... android { ... defaultConfig {...} signingConfigs { create("release") { storeFile = file("myreleasekey.keystore") storePassword = "password" keyAlias = "MyReleaseKey" keyPassword = "password" } } buildTypes { getByName("release") { ... signingConfig = signingConfigs.getByName("release") } } }
Cool
... android { ... defaultConfig {...} signingConfigs { release { storeFile file("myreleasekey.keystore") storePassword "password" keyAlias "MyReleaseKey" keyPassword "password" } } buildTypes { release { ... signingConfig signingConfigs.release } } }
Hinweis:Fügen Sie die Passwörter für Ihren Release-Schlüssel und Schlüsselspeicher innerhalb der Build-Datei ist keine gute Sicherheitsmaßnahme. Konfigurieren Sie stattdessen die Build-Datei so, dass diese Passwörter abgerufen werden. aus Umgebungsvariablen oder den Build-Prozess dazu auffordern, Passwörter.
So erhalten Sie diese Passwörter aus Umgebungsvariablen:
Kotlin
storePassword = System.getenv("KSTOREPWD") keyPassword = System.getenv("KEYPWD")
Cool
storePassword System.getenv("KSTOREPWD") keyPassword System.getenv("KEYPWD")
Alternativ können Sie den Schlüsselspeicher aus einer lokalen Attributdatei laden. Aus Sicherheitsgründen sollten Sie fügen Sie diese Datei zur Versionsverwaltung hinzu. Richten Sie es stattdessen lokal für jeden Entwickler. Weitere Informationen erhalten Sie unter . Signaturinformationen aus Build-Dateien entfernen
Nachdem Sie diesen Vorgang abgeschlossen haben, können Sie Ihre App vertreiben und veröffentlichen. bei Google Play.
Warnung: Bewahren Sie Ihren Schlüsselspeicher und Ihren privaten Schlüssel an einem sicheren an einem sicheren Ort aufzubewahren und gesicherte Back-ups zu haben. Wenn Sie die Play App-Signatur verwenden und du deinen Uploadschlüssel verlierst, kannst du anfordern Sie mithilfe der Play Console zurücksetzen. Wenn Sie eine App ohne Play App-Signatur veröffentlichen (für Apps, die vor August 2021 erstellt wurden) und können Sie keine Updates mehr in Ihrer App veröffentlichen, da Sie Ihren App-Signaturschlüssel verlieren. müssen immer alle Versionen Ihrer App mit demselben Schlüssel signieren.
Wear OS-Apps signieren
Bei der Veröffentlichung von Wear OS-Apps müssen sowohl das Smartwatch-APK als auch das optionale Smartphone-APK mit dem und denselben Schlüssel hat. Weitere Informationen zum Verpacken und Signieren von Wear OS-Apps findest du unter Wear-Apps im Paket anbieten und vertreiben