3

Since building a release version of my app with ProGuard enabled, my plot style is reset to the default and I see many warnings in Logcat informing me of unsupported parameters:

Error inflating XML: Setter for field "[...]" does not exist.

I've pinpointed this to be coming from AndroidPlot's Configurator, but haven't found any official ProGuard configuration for this project.

Paul Lammertsma
  • 37,593
  • 16
  • 136
  • 187

3 Answers3

6

The mechanism through which AndroidPlot sets the configuration parameters relies heavily on reflection, and in that light I've decided it's useless to try to obfuscate anything inside this library:

-keep class com.androidplot.** { *; }
Paul Lammertsma
  • 37,593
  • 16
  • 136
  • 187
  • 1
    Out of curiosity is the primary motivation for obfuscation security or APK size? If the former then it's probably not worth the effort. If the later, depending on what kind of plot(s) your app displays, you may be able get a reasonable reduction just by filtering out unused packages. – Nick Apr 17 '14 at 17:47
  • It may indeed be worthwhile to sort out, but would take some significant looking in to how AndroidPlot's Configurator works. Unfortunately, regardless of the approach, you would need to individually add exclusions in the ProGuard configuration as the methods and fields provided through the XML configuration are parsed and applied through reflection. (Incidentally, I don't like the approach they've gone for due to this reason. Also, without attribute descriptions the data types and attribute names are obscured.) – Paul Lammertsma Apr 17 '14 at 18:16
  • 1
    If for example, your app only uses a pie chart then you can safely tell proguard to remove all of com.androidplot.xy, which should reduce the library size by at least half, or if the inverse is true, remove all of com.androidplot.pie. This only yields shrink benefits, but obfuscating an open source library for security reasons is in *most* cases ineffective. I do wholeheartedly agree that the "configurator" is ugly and painful. We've tried a couple times to replace it with something else but always run into platform limitations caused by the need to distribute Androidplot as a jar. – Nick Apr 17 '14 at 18:32
  • Thanks for the suggestions, I'll look into it. Of course it's only for shrinking as you say. Perhaps the discussion about attribute use can be continued elsewhere. Why the need for a jar? A project library for Eclipse is fine, and AAR through Gradle is a great option these days. – Paul Lammertsma Apr 17 '14 at 18:42
  • Let's definitely continue the conversation - I've created a [discussion thread here](https://groups.google.com/forum/?fromgroups#!topic/androidplot/QXgCLIz_cf0). – Nick Apr 17 '14 at 19:12
1

In my case, I had been using proguard for debug builds and it worked fine. Then I ran a release build (which adds obfuscation to the proguard configuration) and that crashed when it tried to inflate XYPlot in a view.

Binary XML file line #12: Binary XML file line #12: Error inflating class com.androidplot.xy.XYPlot

To fix it, I just configured proguard to not obfuscate the names of any androidplot objects:

-keepnames class com.androidplot.**
Jon
  • 9,156
  • 9
  • 56
  • 73
0

That did not work for me yet. For troubleshooting I set the switches -dontshrink -dontoptimize -dontobfuscate in the first step (if that doesn't help, the reason is probably not to be found in ProGuard). After that you can step by step exclude single groups of classes, e.g. "-keep, includedescriptorclasses, includecode class my.path.to.R*{*;}". In my case the resource classes created by Android Studio had to be "-keep'ed":

-keep, includedescriptorclasses, includecode class com.androidplot.** {*;}

-keepclassmembers class **.R$* {
    public static <fields>;
}

see https://www.guardsquare.com/en/products/proguard/manual/examples

"We're keeping the static fields of referenced inner classes of auto-generated R classes, just in case your code is accessing those fields by introspection. Note that the compiler already inlines primitive fields, so ProGuard can generally remove all these classes entirely anyway (because the classes are not referenced and therefore not required)."