Limite 64k superato su API precedenti rispetto al lollipop, ma non più recente

Quindi mi sto chiedendo perché incontro il limite del metodo 64k dex quando provo a eseguire la mia app su versioni Android precedenti al lollipop, quando viene eseguita correttamente nelle versioni più recenti.

Potrebbe essere, perché le librerie di supporto vengono effettivamente referenziate quando sono in esecuzione sulle versioni precedenti?

Questo è il mio gradle:

apply plugin: 'com.android.application' android { compileSdkVersion 23 buildToolsVersion '23.0.2' lintOptions { checkReleaseBuilds true // Or, if you prefer, you can continue to check for errors in release builds, // but continue the build even when errors are found: abortOnError false } defaultConfig { applicationId "com.domain.myapp" minSdkVersion 16 targetSdkVersion 23 versionCode 27 versionName "1.2" // Vector compat vectorDrawables.useSupportLibrary = true } buildTypes { release { minifyEnabled true shrinkResources true proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } compileOptions { sourceCompatibility JavaVersion.VERSION_1_7 targetCompatibility JavaVersion.VERSION_1_7 } } dependencies { compile files('libs/commons-io-2.4.jar') compile files('libs/activation.jar') compile files('libs/additionnal.jar') compile files('libs/mail.jar') compile project(':libraries:preferencefragment') // Gmail API compile('com.google.api-client:google-api-client-android:1.20.0') { exclude group: 'org.apache.httpcomponents' } compile('com.google.apis:google-api-services-gmail:v1-rev29-1.20.0') { exclude group: 'org.apache.httpcomponents' } // Play Services compile 'com.google.android.gms:play-services-location:8.4.0' compile 'com.google.android.gms:play-services-maps:8.4.0' compile 'com.google.android.gms:play-services-ads:8.4.0' compile 'com.google.android.gms:play-services-analytics:8.4.0' compile 'com.google.android.gms:play-services-identity:8.4.0' // Support libraries compile 'com.android.support:support-v4:23.3.0' compile 'com.android.support:appcompat-v7:23.3.0' compile 'com.android.support:cardview-v7:23.3.0' compile 'com.android.support:design:23.3.0' compile 'com.github.bumptech.glide:glide:3.6.1' compile 'com.anjlab.android.iab.v3:library:1.0.20' compile 'com.sothree.slidinguppanel:library:2.0.3' compile 'com.commit451:PhotoView:1.2.5' compile('com.github.afollestad.material-dialogs:core:0.8.5.7@aar') { transitive = true } } 

MODIFICARE:

Per chiarire: questo accade quando provo a eseguire l’app su un emulatore che gira ad es. KitKat API 19

Registri di arresto anomalo dalla console gradle:

 ... :App:generateDebugInstantRunAppInfo :App:transformClassesWithDexForDebug AGPBI: {"kind":"error","text":"The number of method references in a .dex file cannot exceed 64K.\nLearn how to resolve this issue at https://developer.android.com/tools/building/multidex.html","sources":[{}],"original":"UNEXPECTED TOP-LEVEL EXCEPTION:\ncom.android.dex.DexIndexOverflowException: method ID not in [0, 0xffff]: 65536\n\tat com.android.dx.merge.DexMerger$6.updateIndex(DexMerger.java:484)\n\tat com.android.dx.merge.DexMerger$IdMerger.mergeSorted(DexMerger.java:261)\n\tat com.android.dx.merge.DexMerger.mergeMethodIds(DexMerger.java:473)\n\tat com.android.dx.merge.DexMerger.mergeDexes(DexMerger.java:161)\n\tat com.android.dx.merge.DexMerger.merge(DexMerger.java:188)\n\tat com.android.dx.command.dexer.Main.mergeLibraryDexBuffers(Main.java:504)\n\tat com.android.dx.command.dexer.Main.runMonoDex(Main.java:334)\n\tat com.android.dx.command.dexer.Main.run(Main.java:277)\n\tat com.android.dx.command.dexer.Main.main(Main.java:245)\n\tat com.android.dx.command.Main.main(Main.java:106)\n","tool":"Dex"} FAILED FAILURE: Build failed with an exception. * What went wrong: Execution failed for task ':App:transformClassesWithDexForDebug'. > com.android.build.api.transform.TransformException: com.android.ide.common.process.ProcessException: java.util.concurrent.ExecutionException: com.android.ide.common.process.ProcessException: org.gradle.process.internal.ExecException: Process 'command '/Library/Java/JavaVirtualMachines/jdk1.7.0_79.jdk/Contents/Home/bin/java'' finished with non-zero exit value 2 * Try: Run with --stacktrace option to get the stack trace. Run with --info or --debug option to get more log output. BUILD FAILED 

Messaggio di blocco dalla finestra del messaggio:

 :App:transformClassesWithDexForDebug Error:The number of method references in a .dex file cannot exceed 64K. Learn how to resolve this issue at https://developer.android.com/tools/building/multidex.html Error:Execution failed for task ':App:transformClassesWithDexForDebug'. > com.android.build.api.transform.TransformException: com.android.ide.common.process.ProcessException: java.util.concurrent.ExecutionException: com.android.ide.common.process.ProcessException: org.gradle.process.internal.ExecException: Process 'command '/Library/Java/JavaVirtualMachines/jdk1.7.0_79.jdk/Contents/Home/bin/java'' finished with non-zero exit value 2 

Solutions Collecting From Web of "Limite 64k superato su API precedenti rispetto al lollipop, ma non più recente"

Per rispondere alla tua domanda specifica è:

  • Questa limitazione del conteggio dei metodi si trova nel file DEX (eseguibile Dalvik).
  • Una soluzione alternativa comune a questa limitazione è di avere più file DEX.
  • Le versioni precedenti di Android non supportano in modo nativo più file DEX.
  • A partire da Lollipop il sistema lo supporta in modo nativo.

Ecco perché non funziona sui dispositivi più vecchi, ma funziona su dispositivi più recenti. Non ha nulla a che fare con le librerie di supporto.

Per aggiungere altri contenuti utili alla mia risposta:

Ma forse quello che alcuni potrebbero voler sapere è come risolverlo su dispositivi più vecchi, si noti che ho usato la parola in natively sui miei punti elenco sopra. Ciò significa che esistono soluzioni alternative per far sì che le piattaforms precedenti lo supportino, ma devi codificare tali soluzioni alternative nella tua app.

La soluzione alternativa (e anche il problema stesso) è spiegata in dettaglio in questa guida di Google: http://developer.android.com/tools/building/multidex.html

La base di esso è:

  • aggiungi multidex alle tue dipendenze compile 'com.android.support:multidex:+'
  • abilita multiDex sul tuo script di build all’interno di android-> default config multiDexEnabled true
  • sul manifest la tua applicazione si estende da MultidexApplication android:name="android.support.multidex.MultiDexApplication" o, se hai bisogno di sottoclassi Application per la tua app, fai estendere la tua applicazione da essa.

Completamente d’accordo con @Budius. È necessario menzionare una class di applicazione in manifest. E fai in modo che la tua class di applicazione estenda MultiDexApplication.

C’è ancora una cosa necessaria. Chiamare il contesto di base allegato nella class MultiDexApplication

 public class MyApplicationClass extends MultiDexApplication... { .... @Override protected void attachBaseContext(Context base) { super.attachBaseContext(base); MultiDex.install(MyApplicationClass.this); } ... } 

Questo ha funzionato bene per me su dispositivi pre e post lecca-lecca.

Il problema si verifica quando si utilizzano i dispositivi Instant Run e pre-lollipop!

https://code.google.com/p/android/issues/detail?id=208577 https://code.google.com/p/android/issues/detail?id=196809

dovresti aggiungere multiDexEnabled = true al tuo defaultConfig nel file gradle.