web-dev-qa-db-fra.com

PROGUARD ET GSON ON Android (ClasscastException)

Je commence à avoir une époque avec GSON et PROGUARD. J'ai un objet simple et quand je pars Tojson, sauvegardez-vous sur SQLLITE et relevez de la base de données afin de recharger le JSON à mon objet, je reçois une java.lang.classcastException. Si je n'utilise pas PROGUARD, Everything Works Fine.

J'ai vérifié que la chaîne JSON étant envoyée et obtenue de la base de données est la même. L'exception n'est pas lancée lorsqu'elle se convertit de JSON, mais plutôt lorsque j'essaie d'accéder à l'objet.

Voici mon objet simple:

public class ScanLog extends ArrayList<SingleFrame>
{
     private static final long serialVersionUID = 1L;

     public ScanLog()
     {

     }
}

public final class SingleFrame 
{
    public int Position;
    public int Time;
    public Map<Integer,String> MainDataMap;
    public Map<Integer,String> DataMap;

    public SingleFrame(int position, int time, 
                    Map<Integer,String> mainDataMap, Map<Integer,String> dataMap)
    {
        this.Position = position;
        this.Time = time;
        this.MainDataMap = mainDataMap;
        this.DataMap = dataMap;
    }

}

Tous les autres aspects de mon application vont bien, mais quelque chose avec PROGUARD fait que cela se produise ... IVE essayé toutes sortes de commandes de maintien dans le PROGUARD.CFG, mais je ne suis pas sûr de ce que je fais est juste.

Modifier - Ajout de PROGUARD.CFG

-dontusemixedcaseclassnames
-dontskipnonpubliclibraryclasses
-dontpreverify
-verbose
-dontshrink
-dontoptimize

-keep public class * extends Android.app.Activity
-keep public class * extends Android.app.Application
-keep public class * extends Android.app.Service
-keep public class * extends Android.content.BroadcastReceiver
-keep public class * extends Android.content.ContentProvider
-keep public class * extends Android.app.backup.BackupAgentHelper
-keep public class * extends Android.preference.Preference
-keep public class com.Android.vending.licensing.ILicensingService

#keep all classes that might be used in XML layouts
-keep public class * extends Android.view.View
-keep public class * extends Android.app.Fragment
-keep public class * extends Android.support.v4.Fragment

#keep all classes
-keep public class *{
public protected *;
}

#keep all public and protected methods that could be used by Java reflection
-keepclassmembernames class * {
    public protected <methods>;
}


-keepclasseswithmembernames class * {
    native <methods>;
}

-keep public class org.scanner.scanlog.SingleFrame


-keepclassmembers class org.scanner.scanlog.ScanLog { 
        private <fields>; 
        public <fields>; 
}

-keepclassmembers class org.scanner.scanlog.SingleFrame { 
        private <fields>; 
        public <fields>; 
}

-keepclasseswithmembernames class * {
    public <init>(Android.content.Context, Android.util.AttributeSet);
}

-keepclasseswithmembernames class * {
    public <init>(Android.content.Context, Android.util.AttributeSet, int);
}

-keepclassmembers enum * {
    public static **[] values();
    public static ** valueOf(Java.lang.String);
}

-keep class * implements Android.os.Parcelable {
  public static final Android.os.Parcelable$Creator *;
}

-dontwarn **CompatHoneycomb
-dontwarn org.htmlcleaner.*
#-keep class Android.support.v4.** { *; }

EDIT - D'accord, j'ai eu l'ACRA mis en place avec succès dans mon application, une très grande fonctionnalité! Voici la trace de la pile:

Java.lang.ClassCastException: Java.lang.Object
    at org.scanner.activity.ReaderMainActivity.AdvanceScanLog(SourceFile:1499)
    at org.scanner.activity.r.onProgressChanged(SourceFile:271)
    at Android.widget.SeekBar.onProgressRefresh(SeekBar.Java:89)
    at Android.widget.ProgressBar.doRefreshProgress(ProgressBar.Java:507)
    at Android.widget.ProgressBar.refreshProgress(ProgressBar.Java:516)
    at Android.widget.ProgressBar.setProgress(ProgressBar.Java:565)
    at Android.widget.AbsSeekBar.trackTouchEvent(AbsSeekBar.Java:337)
    at Android.widget.AbsSeekBar.onTouchEvent(AbsSeekBar.Java:292)
    at Android.view.View.dispatchTouchEvent(View.Java:3932)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at Android.view.ViewGroup.dispatchTouchEvent(ViewGroup.Java:906)
    at com.Android.internal.policy.impl.PhoneWindow$DecorView.superDispatchTouchEvent(PhoneWindow.Java:1784)
    at com.Android.internal.policy.impl.PhoneWindow.superDispatchTouchEvent(PhoneWindow.Java:1157)
    at Android.app.Activity.dispatchTouchEvent(Activity.Java:2181)
    at com.Android.internal.policy.impl.PhoneWindow$DecorView.dispatchTouchEvent(PhoneWindow.Java:1759)
    at Android.view.ViewRoot.deliverPointerEvent(ViewRoot.Java:2336)
    at Android.view.ViewRoot.handleMessage(ViewRoot.Java:1976)
    at Android.os.Handler.dispatchMessage(Handler.Java:99)
    at Android.os.Looper.loop(Looper.Java:143)
    at Android.app.ActivityThread.main(ActivityThread.Java:4263)
    at Java.lang.reflect.Method.invokeNative(Native Method)
    at Java.lang.reflect.Method.invoke(Method.Java:507)
    at com.Android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.Java:839)
    at com.Android.internal.os.ZygoteInit.main(ZygoteInit.Java:597)
    at dalvik.system.NativeStart.main(Native Method)
32
Jesse

Pour la dernière version du fichier de configurateur proguard recommandé, veuillez consulter le gson fourni Android PROGUARD Exemple à: https://github.com/google/gson/blob/master/ Exemples/Android-PROGUARD-EXEMPLE/PROGUARD.CFG

68
Guy

Ces paramètres de la configuration ont fonctionné pour moi dans l'une de mes applications:

# Add the gson class
-keep public class com.google.gson

# Add any classes the interact with gson
-keep class com.someapp.Android.models.ChatModel { *; }
-keep class com.someapp.Android.models.FeedModel { *; }

# Add the path to the jar
-libraryjars /Users/someuser/Documents/workspace/someapp/lib/gson-1.7.1.jar

J'espère que cela vous aidera.

25
Stokedbits

Appliquer les modifications trouvées dans le Exemple Android dans le projet GSON a fonctionné pour moi

Les lignes nécessaires étaient:

-keepattributes Signature
-keep class Sun.misc.Unsafe { *; }
# and keeping the classes that will be serialized/deserialized
14
Daddyboy

Je sais que la question initiale a été résolue en adoptant une approche différente, mais j'avais un problème très similaire à l'aide de Flexjson et de PROGUARD sur Android, et je l'ai résolu, au cas où tout le monde s'enfonce eux-mêmes.

Lors de la conversion de JSON à mon objet de valeur, qui comprenait des arraylistes, je recevrais la même classeCastException. Je l'ai eu pour travailler en essentiellement d'obfuscation activée, mais tournez toutes les parties de l'obfuscation (-Markeekeekekekepassmembers tout et maintiennent tout), puis de travailler en arrière en permettant aux choses un peu à la fois.

Le résultat; Garder toute la bibliothèque Flexjson:

-keep class flexjson**
--keepclassmembers class flexjson** {
   *;
}

et garder la signature et annotation attribut:

-keepattributes Signature, *Annotation*

J'ai pu utiliser la bibliothèque Flexjson sans incident après cela dans une version de la libération progressive de mon application.

6
HTLD

Je reçois des erreurs pour les classes de modèle avec PROGUARD si vous regardez

gson proguard Vous trouverez une ligne

# Application classes that will be serialized/deserialized over Gson
-keep class com.google.gson.examples.Android.model.** { *; }

remplacer com.google.gson.examples.Android.model. Avec votre package model dans mon cas, je l'ai remplacé par -keep class com.consumer.myProject.model.** { *; }

repos je suis copié en tant que tel

2
DeltaCap019

Ainsi, j'ai fini par abandonner la bibliothèque GSON et au lieu de convertir mon objet à JSON à l'aide de GSON, j'ai créé une classe personnalisée dans mon application pour sérialiser et désérialiser l'objet et stocker les données de cette façon.

Je suis globalement plus heureux, même si cela m'a coûté plus de 12 heures d'essayer de le comprendre. Apparemment, Proguard et Gson ne doivent pas trop se ressembler?

comme un avantage extrêmement ajouté Pour ne pas avoir à utiliser Gson, j'ai remarqué que, en sortant de la bibliothèque GSON, ma taille d'application est coupée en deux. Mon application était de 577 kb et est maintenant seulement 260 Ko après avoir retiré le GSON LIB.

1
Jesse

On dirait que vous surveillez tout de votre classe (champs, méthodes et la classe elle-même). Mais pour vous assurer que vous pouvez ajouter -printseeds outputfile.txt au fichier PROGUARD.CFG pour vérifier que PROGUARD garde vraiment tout ce dont vous avez besoin une fois l'obscurité terminée.

BTW, vous pouvez penser à ajouter quelque chose comme ARCRA ou Android Demand StackTrace Vous permettant d'inspecter StackTraces sur une application construite.

1
THelper