I'm currently using an Android library that uses a lot of reflection.
As soon as I enable proguard, and run it... it crashes.
Why? It uses a lot of reflection and the methods are only invoked via reflection, so they are detected by proguard as unused and removed during the shrinking process, so a a NoSuchMethodError
is thrown.
Why this happens? That is easy to figure out they are removed during the shrinking process as proguard considers they are unused and therefore removes that pieces of code (all the methods)
So, how can I configure proguard to avoid shrinking or obfuscating an entire package? (the library)
Note: I don't want to use the -dontshrink option, as it's all or nothing and I just want to avoid a specific package.
More info:
The runtime error is the following:
E/AndroidRuntime: FATAL EXCEPTION: main Process: com.my.app.debug, PID: 3771
java.lang.NoSuchMethodError: observeValueForKeyPath [class java.lang.String, class java.lang.Object, class com.my.lib.util.Dictionary, class java.lang.Object]
at com.my.lib.util.Observable$ObservationManager$Observer.<init>(SourceFile:47)
at com.my.lib.util.Observable$ObservationManager$Observer.<init>(SourceFile:26)
at com.my.lib.util.Observable$ObservationManager.addObserver(SourceFile:159)
...
Take note that the problem is one an inner inner class...
My current configuration has something like:
-keep,includedescriptorclasses class com.my.** { *; }
-keepclassmembers class com.my.lib** { *; }
-keep,includedescriptorclasses class com.my.lib.util.Observable$* { *; }
-keep,includedescriptorclasses class com.my.lib.util.Observable$*$* { *; }
But this apparently only avoids obfuscating the methods not removed during the shrinking process... I need to avoid removing methods during shrinking.
-keepclassmembernames. This is the most permissive keep directive; it lets ProGuard do almost all of its work. Unused classes are removed, the remaining classes are renamed, unused members of those classes are removed, but then the remaining members keep their original names.
Obfuscating package names myapplication. MyMain is the main application class that is kept by the configuration. All other class names can be obfuscated. Note that not all levels of obfuscation of package names may be acceptable for all code.
Obfuscation decreases the efficiency of compression algorithms, so obfuscating all the code in the app may increase its file size significantly.
According to the documentation -keep
should work even when shrinking, while -keepclassmembers
only works "if [the] classes are preserved as well".
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With