to ∞ (~65k) and beyond! - sebastiano gottardo - codemotion milan 2016
TRANSCRIPT
![Page 1: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/1.jpg)
To ∞ (~65K) and beyond!Sebastiano Gottardo, Android Engineer +SebastianoGottardo - @rotxed
1
![Page 2: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/2.jpg)
Context
2
![Page 3: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/3.jpg)
Context
• OSS, community, libraries, frameworksThe Android open-source community is enormous, and brings to the table thousands of libraries and frameworks.
• ✓ Faster development, contributions and improvements These tools allows you to build better apps quicker. In addition, contributions by other users lead to improvements.
• ✗ Using too many can lead to heavy APK, long loading times, bugs There are tradeoffs.
3
![Page 4: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/4.jpg)
4
65536
![Page 5: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/5.jpg)
Dalvik Executable (DEX)
• Container of the compiled source code .java files are compiled into .class files, then packed into a .dex file
5
![Page 6: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/6.jpg)
Where is the limit
• Not runtime, not DEX, but Dalvik’s instruction set!
6
https://goo.gl/ajlxwX
![Page 7: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/7.jpg)
Crossing the limit
• Unable to build an APK
• Panic
• Console output
7
Older build system Newer build system
![Page 8: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/8.jpg)
Is this going to change?
8
![Page 9: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/9.jpg)
Context
• No(t likely)Lose retro-compatibility!
• ART (Android Runtime)The new runtime used starting with Lollipop provides a way around.
• What to do then?There are different solutions/approaches.
9
![Page 10: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/10.jpg)
Approaches
• MultiDexGoogle’s own solution.
• Secondary DEX Get your hands dirty.
• Shrinking / Reasoning ProGuard is your friend, and so is your brain.
10
![Page 11: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/11.jpg)
MultiDex
11
![Page 12: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/12.jpg)
MultiDex
• Google’s way around this limitation aka what’s in the docs
• Still not the “recommended” approach More on that later on.
• Different working mechanisms depending on platformDalvik ≠ ART.
12
![Page 13: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/13.jpg)
MultiDex: Dalvik VS ART
13
ARTDalvik
![Page 14: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/14.jpg)
MultiDex with ART
• App’s source code is compiled and packed into multiple DEX files Ultimately packed in the APK
• At install time, the OS compiles the code of the DEX files into a single OAT file (ELF)AOT compilation instead of JIT compilation
14
![Page 15: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/15.jpg)
MultiDex: Dalvik VS ART
15
ARTDalvik
![Page 16: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/16.jpg)
MultiDex with Dalvik
• App’s source code is compiled and packed into a single DEX fileUltimately packed in the APK
• Dalvik is unaware of DEX files other than the main oneclasses.dex
• Multiple DEX files must be loaded at runtimeCan be troublesome (a.k.a. sucks)
16
![Page 17: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/17.jpg)
MultiDex - Setup
17
![Page 18: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/18.jpg)
Setup 1/3
1. Gradle-wise setup
18
android { compileSdkVersion 23 buildToolsVersion "23.0.2" defaultConfig { ... minSdkVersion 15 targetSdkVersion 23 ... // Enabling multidex support. multiDexEnabled true } ...}
![Page 19: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/19.jpg)
Setup 2/3
2. Include the MultiDex support library
19
dependencies { compile 'com.android.support:multidex:1.0.0'}
![Page 20: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/20.jpg)
Setup 3/3
3. Enable MultiDex in your code
20
<manifest xmlns:android="http://schemas.android.com/apk/res/android" package="com.example.android.multidex.myapplication"> <application ... android:name="android.support.multidex.MultiDexApplication"> ... </application></manifest>
a
public class YourAwesomeApplication extends MultiDexApplication { ...
}b
@Overrideprotected void attachBaseContext(Context base) { super.attachBaseContext(base); MultiDex.install(this); }
c
![Page 21: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/21.jpg)
Advantages
• Well integrated with the build chainNo magic involved.
• Seamless support across platform versionsBeing a support library. One code, one love!
• Extremely easy to enableLiterally takes 3 minutes.
21
![Page 22: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/22.jpg)
Disadvantages
• Limited in choosing what goes whereEsp. true for libraries that sport native components.
• MultiDex on Dalvik is unreliableFor 14 < API < 21 crashes may occur.
• Secondary DEX files are loaded at runtimeStartup time is increased! (unless you defer installation)
• Build times increaseVariants may help (dev — min 21, speeds things up)
22
![Page 23: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/23.jpg)
Secondary DEX
23
![Page 24: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/24.jpg)
Secondary DEX
• Historically, the first workaroundA blog post by Fred Chung, a Googler at the time (2007)
• Relied on customizing the build chain Some Ant magic
• Used an interface-based approach
24
![Page 25: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/25.jpg)
How does it work
• Put one or more libraries into a separate DEX file Limited to .jar files, .aar not supported
• At runtime, load the secondary DEX on a custom ClassLoaderDifferent from the default ClassLoader!
• Invoke the libraries’ methodsInterface, Reflection
25
![Page 26: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/26.jpg)
Quick example w/ Reflection
26
twitter = new TwitterFactory().getInstance(); twitter.setOAuthConsumer(TWITTER_APP_KEY, TWITTER_APP_SECRET); twitter.setOAuthAccessToken(new AccessToken(token, tokenSecret));
![Page 27: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/27.jpg)
Quick example w/ Reflection
27
...twitter = twitterManager.initializeTwitter(TWITTER_APP_KEY, TWITTER_APP_SECRET, token, tokenSecret); ...
public Object initializeTwitter(String TWITTER_APP_KEY, String TWITTER_APP_SECRET, String token, String tokenSecret) { try { Object twitterFactoryInstance = getClassCached(twitterFactoryFQN).newInstance(); Method getInstanceMethod = getMethodCached(twitterFactoryFQN, "getInstance", null); Object twitterInstance = getInstanceMethod.invoke(twitterFactoryInstance, null); Method setOAuthConsumerMethod = getMethodCached(twitterFQN, "setOAuthConsumer", String.class, String.class); setOAuthConsumerMethod.invoke(twitterInstance, TWITTER_APP_KEY, TWITTER_APP_SECRET); Class atClass = getClassCached(accessTokenFQN); Object atInstance = atClass.getDeclaredConstructor(new Class[] {String.class, String.class}).newInstance(token, tokenSecret); Method setOAuthAccessTokenMethod = getMethodCached(twitterFQN, "setOAuthAccessToken", atClass); setOAuthAccessTokenMethod.invoke(twitterInstance, atInstance); return twitterInstance; } catch (Exception e) { e.printStackTrace(); } return null;}
![Page 28: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/28.jpg)
Advantages
• Choose exactly what goes whereTake that, MultiDex
• Choose exactly when to load secondary DEXSo not to impact cold start times
28
![Page 29: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/29.jpg)
Disadvantages
• Quite hard to setupCopy DEX to the appropriate dir, create ClassLoader instance
• Quite hard to work withEsp. if you rely on Reflection
• Versioning! How to handle updates?
29
![Page 30: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/30.jpg)
Improvements
• Same approach as Google’s MultiDexPatches the Class Loader so to look for other DEX files
• Specify the dependencies as ‘provided’So to be resolved at compile/build time, stripped in the final APK
• Best of two worlds (kind of)Removes the need for ifaces, Reflection, still a bit cumbersome
30
![Page 31: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/31.jpg)
Shrinking / Reasoning
31
![Page 32: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/32.jpg)
— Google MultiDex online documentation
Before configuring your app to enable use of 65K or more method references, you should take steps to reduce the total number of references called by your app code, including methods defined by your app code or included libraries.
32
![Page 33: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/33.jpg)
ProGuard in pills
• Shrink, optimize, obfuscate
• Works both for your code and for third-party libraries
• Has an impact on APK size, methods number, performance and security
33
![Page 34: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/34.jpg)
ProGuard ProTips
• Get familiar with writing appropriate rulesThe stricter, the better
34
-keep class !android.support.v7.internal.view.menu.**,android.support.** {*;}
• What’s wrong with the following keep rule?
-keep class com.google.** { *; }
-keepnames class com.google.** { *; }
-keepclassmembernames class * { @com.google.android.gms.common.annotation.KeepName *; }
• Adopts an exclusion-based approach
![Page 35: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/35.jpg)
ProGuard ProTips
35
-keep class !android.support.v7.internal.view.menu.**,android.support.** {*;}
-keep class com.google.** { *; }
-keepnames class com.google.** { *; }
-keepclassmembernames class * { @com.google.android.gms.common.annotation.KeepName *; }
• Adopts an exclusion-based approach
• Get familiar with writing appropriate rulesThe stricter, the better
• What’s wrong with the following keep rule?
![Page 36: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/36.jpg)
ProGuard: default rules
36
android { ... buildTypes { release { minifyEnabled true proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } }
• ProGuard already includes common rules for common cases~/sdk/tools/proguard/lib/proguard-android.txt
-keepclasseswithmembernames class * { native <methods>; }
![Page 37: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/37.jpg)
DexGuard: beefier, for beefier companies
37
• ProGuard’s bigger (and pricier) brother
• Advanced features: res/strings/.so encryption, stronger obfuscation,tamper detection, its own multidex! and more
• Pluggable encryption! I mean, seriously, that exclamation mark has a reason
• Default rules are much more extensive
![Page 38: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/38.jpg)
ProGuard and third-party libs
38
• Many provide the ProGuard statement (a.k.a RTFM)e.g., Square, Facebook, …
• Pay attention to ‘keep-all’ rules!especially for libraries with many methods
![Page 39: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/39.jpg)
… wait, how do I count libraries methods?
39
… how do I count methods at all?!
![Page 40: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/40.jpg)
inloop’s “APK method count”
40
![Page 41: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/41.jpg)
inloop’s “APK method count”
41
![Page 42: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/42.jpg)
inloop’s “APK method count”
• Simple website with drag-and-drop interface
• Drop the APK and see the (locally) computed countNo APKs uploaded :+1:
• http://inloop.github.io/apk-method-count/
42
✓ Easy, immediate, private✗ Build every time
![Page 43: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/43.jpg)
ClassyShark
• Useful Java tool to inspect APKsWritten by Boris Farber (Googler)
• Inspect number of classes, members, methods, dependencies, …Acts as a simple decompiler, too
43
![Page 44: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/44.jpg)
ClassyShark
44
![Page 45: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/45.jpg)
ClassyShark
45
![Page 46: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/46.jpg)
ClassyShark
• Useful Java tool to inspect APKsWritten by Boris Farber (Googler)
• Inspect number of classes, members, methods, dependencies, …Acts as a simple decompiler, too
46
✓ Easy, plenty of info, multi-purpose✗ Build every time, more oriented to agnostic debugging
![Page 47: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/47.jpg)
dexcount-gradle-plugin
• Gradle plugin, developed by KeepSafe
• See the current methods count every time you buildJust open the Gradle console
• Outputs per-package information in a ${variant}.txt file
47
![Page 48: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/48.jpg)
dexcount-gradle-plugin
48
![Page 49: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/49.jpg)
dexcount-gradle-plugin
49
![Page 50: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/50.jpg)
dexcount-gradle-plugin
• Gradle plugin, developed by KeepSafe
• See the current methods count every time you buildJust open the Gradle console
• Outputs per-package information in a ${variant}.txt file
50
✓ Keep the count controlled at a glance✗ Cumbersome to see single deps count
![Page 51: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/51.jpg)
MethodsCount
• Developed by Sebastiano Gottardo, Nicola Miotto, Dario Marcato
• Allows to see methods and dependencies for libraries beforehand
• Compare different libraries in terms of “lightweight-ness”
51
![Page 52: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/52.jpg)
MethodsCount
52
• More than 20000 libraries and dependenciesWhat’s missing is calculated upon the first request
• For each entry
1. dex/jar size
2. direct count + dependencies count
3. multiple versions (monitor changes over time) + charts
![Page 53: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/53.jpg)
MethodsCount
53
![Page 54: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/54.jpg)
MethodsCount
54
![Page 55: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/55.jpg)
MethodsCount
55
![Page 56: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/56.jpg)
MethodsCount - AS plugin
56
• Parses `build.gradle` and directly shows the count
• Convenient when you drop a dependency right away
![Page 57: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/57.jpg)
MethodsCount - AS plugin
57
• Parses `build.gradle` and directly shows the count
• Convenient when you drop a dependency right away
![Page 58: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/58.jpg)
MethodsCount
58
✓ See the count before having to hit the limit✓ Compare different libraries Worth having 4000 methods instead of 900?✓ Analyze dependencies No, Guava is not a good excuse to have 15000+ methods✓ Integrated in AS, thanks to the plugin
✗ The count is before ProGuard → Upper bound!
![Page 59: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/59.jpg)
Bottom line
59
![Page 60: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/60.jpg)
Bottom line
• The limit is here, at least for some timeLearn to deal with it
• The recommended way is “Do NOT cross the limit!”And use ProGuard. Your nerves will thank you later!
• If you do need to cross, there are solutions (with drawbacks)MultiDex, secondary DEX
60
![Page 61: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/61.jpg)
Routine
1. PM shows interest in a new library:eyes_roll:
2. With dex-gradle-plugin, check the current count
3. Check MethodsCount to see how many methods, size and deps
4. Evaluate whether fits a secondary DEX
5. Consider alternatives (again, MethodsCount)
61
![Page 62: To ∞ (~65K) and beyond! - Sebastiano Gottardo - Codemotion Milan 2016](https://reader034.vdocuments.site/reader034/viewer/2022042600/5870814f1a28ab57368b66bd/html5/thumbnails/62.jpg)
Useful resources
• Timothy Mellor: https://github.com/tmelz/multidex_notes
• Jeroen Mols: http://jeroenmols.com/blog/2016/05/06/methodcount/
62
@rotxed+SebastianoGottardo
Follow me