2016-05-25 23 views
14

Ho una domanda molto stupida, ma sono seduto qui davanti alla mia app da ore ma non riesco a capire quale sia il problema.Sapore prodotto: classe duplicata trovata

Ho un app Android (scritto in Kotlin) e voglio fare due sapori dei prodotti e sovrascrivere una classe/file nel sapore del prodotto:

Quindi il mio script Gradle è che:

apply plugin: 'com.android.application' 
apply plugin: 'kotlin-android' 


android { 
    ... 
    productFlavors { 
    foo { 
     applicationId "com.foo" 
    } 
    } 
} 

miei file sono strutturati come segue:

- src 
    - androidTest 
    - foo 
     - java 
     - com 
      - example 
      - Bar.kt 
    - main 
     - java 
     - com 
      - example 
      - Bar.kt 
    - test 

Quindi, fondamentalmente vorrei ignorare Bar.kt file in foo sapore del prodotto, ma in qualche modo non funziona: dice che la classe Bar è duplicata.

Qualche suggerimento?

+2

non dovrebbe esistere fonti specifiche sapore solo nelle falvors che avete definito (vale a direnon in principale)? Quindi definiresti almeno due sapori e solo Bar.kt nei set sorgente per quei sapori. – Michael

+0

Hm, forse hai ragione ... in realtà io sto cercando di scavalcare un modulo di pugnale ... quindi 'Bar.kt' è in realtà un pugnale 2 moduli – sockeqwe

+0

Eventuali duplicati di [buildTypes Gradle Android: class Duplicate] (http://stackoverflow.com/questions/18782368/android-gradle-buildtypes-duplicate-class) – miensol

risposta

25

The documentation for variants stati (sottolineatura mia):

Nota: Per una data variante di accumulo, Gradle getta un errore di generazione se incontra due o più directory di origine set che hanno definito la stessa classe Java. Ad esempio, quando si crea un APK di debug, non è possibile definire sia src/debug/Utility.java che src/main/Utility.java. Questo è perché Gradle esamina entrambe queste directory durante il processo di creazione e genera un errore di "duplicazione classe". Se si desiderano versioni diverse di di Utility.java per diversi tipi di build, è possibile fare in modo che ogni tipo di build definisca la propria versione del file e non includerlo in il set di origine/sorgente.

Quindi la soluzione è di avere la propria versione di Bar.kt per variante ed escluderla dal set sorgente principale.

+3

Se ho detto 4-5 sapori e 3 di loro usano la stessa classe e il set usa un codice specifico, devo duplicarlo ovunque o sourceSets può farlo? Non si può fare con i set sorgente –

+1

@AkhilDad Immagino si possa creare un modulo separato per condividere il codice attraverso i sapori. – miensol

7

Come indicato da miensol non è possibile inserire il file su main e gestire cartelle specifiche e aspettarsi che gradle funzioni allo stesso modo in cui funziona il sistema di risorse Android. Ma ho trovato un modo per farlo senza la duplicazione del codice in modo da non dover copiare il tuo Bar.kt in ogni cartella di sapori che hai.

Quindi diciamo che avete tre gusti dev, prod e finta. Volete il vostro speciale simulato simulato, ma la normale implementazione in dev e prod sapori. Metti il ​​tuo file di battuta sulla cartella similare fittizio mock/java/com/something/ e metti la tua implementazione "predefinita" in una nuova cartella con un nome casuale come non-mock/java/com/something/ nominandolo qualcosa di simile a "comune" avrebbe anche senso. Ora devi dire a Gradle dove dovrebbero cercare quei sapori la loro classe Bar.kt.

mettere questo al tuo build.gradle:

android { 
    ... 
    sourceSets { 
     prod { 
      java.srcDirs('src/non-mock/java') 
     } 
     dev { 
      java.srcDirs('src/non-mock/java') 
     } 
    } 

}