google example code android gson proguard obfuscation

example - gson gradle android



Usando GSON con proguard habilitado (4)

Cuando aplica un script de proguard a sus clases modelo, confunde sus nombres y los de sus propiedades. Así que después de la ofuscación de String descripcionCategoria; String aaaa; algo como String aaaa;

Gson trabaja a través de la reflexión de Java e intentará usar un nombre de propiedad mientras analiza los datos. Por lo tanto, después de aplicar la ofuscación a las clases modelo, no podrá analizar sus datos.

Por lo tanto, excluya las clases modelo de su secuencia de comandos de proguard y podrá analizar nuevamente.

Mi código funciona perfectamente sin proguard, pero GSON no funciona cuando se habilita proguard.

Esta es la parte del código donde no funciona.

JSONArray mensaje = response.getJSONArray("categorias"); // Parsear con Gson Categorias[] categorias = gson.fromJson(mensaje.toString(), Categorias[].class); Log.d("mainfragment","desc categoria "+categorias[0].getDescripcionCategoria());

El registro de mainfragment se imprime nulo

# Output D/Dato categorias﹕ Respuesta: {"categorias":[{"idCategoria":"22","imagenCategoria":"ic_aseguradora","descripcionCategoria":"Aseguradoras"},{"idCategoria":"24","imagenCategoria":"ic_bar","descripcionCategoria":"Bares"},{"idCategoria":"12","imagenCategoria":"ic_boutique","descripcionCategoria":"Boutiques"},{"idCategoria":"6","imagenCategoria":"ic_cafe","descripcionCategoria":"Cafeterias"},{"idCategoria":"21","imagenCategoria":"ic_ciber","descripcionCategoria":"Ciber"},{"idCategoria":"10","imagenCategoria":"ic_estetica","descripcionCategoria":"Estéticas"},{"idCategoria":"1","imagenCategoria":"ic_farmacia","descripcionCategoria":"Farmacias"},{"idCategoria":"7","imagenCategoria":"ic_ferreteria","descripcionCategoria":"Ferreterias"},{"idCategoria":"16","imagenCategoria":"ic_gas","descripcionCategoria":"Gas"},{"idCategoria":"23","imagenCategoria":"ic_gasolinera","descripcionCategoria":"Gasolineras"},{"idCategoria":"4","imagenCategoria":"ic_gym","descripcionCategoria":"Gimnasios"},{"idCategoria":"2","imagenCategoria":"ic_hotel","descripcionCategoria":"Hoteles"},{"idCategoria":"15","imagenCategoria":"ic_lavanderia","descripcionCategoria":"Lavanderias"},{"idCategoria":"19","imagenCategoria":"ic_muebleria","descripcionCategoria":"Mueblerias"},{"idCategoria":"25","imagenCategoria":"ic_optica","descripcionCategoria":"Ópticas"},{"idCategoria":"20","imagenCategoria":"ic_pasteleria","descripcionCategoria":"Pastelerias"},{"idCategoria":"17","imagenCategoria":"ic_pizza","descripcionCategoria":"Pizzerías"},{"idCategoria":"13","imagenCategoria":"ic_purificadora","descripcionCategoria":"Purificadoras de agua"},{"idCategoria":"5","imagenCategoria":"ic_restaurant","descripcionCategoria":"Restaurantes"},{"idCategoria":"11","imagenCategoria":"ic_ropa","descripcionCategoria":"Ropa"},{"idCategoria":"9","imagenCategoria":"ic_salon","descripcionCategoria":"Salones de fiestas"},{"idCategoria":"3","imagenCategoria":"ic_sonido","descripcionCategoria":"Sonidos"},{"idCategoria":"28","imagenCategoria":"ic_taqueria","descripcionCategoria":"Taquería"},{"idCategoria":"8","imagenCategoria":"ic_taxi","descripcionCategoria":"Taxis"},{"idCategoria":"14","imagenCategoria":"ic_tortilleria","descripcionCategoria":"Tortillerias"},{"idCategoria":"27","imagenCategoria":"ic_veterinaria","descripcionCategoria":"Veterinarias"},{"idCategoria":"18","imagenCategoria":"ic_vinateria","descripcionCategoria":"Vinaterías"},{"idCategoria":"26","imagenCategoria":"ic_zapateria","descripcionCategoria":"Zapaterías"}],"estado":1} D/mainfragment﹕ desc categoria null

Estas son mis reglas proguard

#GoogleMaps -keep class * extends java.util.ListResourceBundle { protected Object[][] getContents(); } -keep public class com.google.android.gms.common.internal.safeparcel.SafeParcelable { public static final *** NULL; } -keepnames @com.google.android.gms.common.annotation.KeepName class * -keepclassmembernames class * { @ccom.google.android.gms.common.annotation.KeepName *; } -keepnames class * implements android.os.Parcelable { public static final ** CREATOR; } #Volley? -optimizationpasses 5 -dontusemixedcaseclassnames -dontskipnonpubliclibraryclasses -dontpreverify -verbose -optimizations !code/simplification/arithmetic,!field/*,!class/merging/* -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 -dontnote com.android.vending.licensing.ILicensingService -keepclassmembers class * implements java.io.Serializable { static final long serialVersionUID; private static final java.io.ObjectStreamField[] serialPersistentFields; private void writeObject(java.io.ObjectOutputStream); private void readObject(java.io.ObjectInputStream); java.lang.Object writeReplace(); java.lang.Object readResolve(); } -keepclasseswithmembernames class * { native <methods>; } -keepclasseswithmembers class * { public <init>(android.content.Context, android.util.AttributeSet); } -keepclasseswithmembers class * { public <init>(android.content.Context, android.util.AttributeSet, int); } -keepclassmembers class **.R$* { public static <fields>; } -keepclassmembers class * extends android.app.Activity { public void *(android.view.View); } -keepclassmembers enum * { public static **[] values(); public static ** valueOf(java.lang.String); } -keep public class * { public protected *; } -keep class * implements android.os.Parcelable { public static final android.os.Parcelable$Creator *; } -keep class android.support.v7.widget.SearchView -keep class android.support.v7.widget.**{*;} -keep class android.support.v4.app.** { *; } -keep interface android.support.v4.app.** { *; } -keep class com.actionbarsherlock.** { *; } -keep interface com.actionbarsherlock.** { *; } -keep class com.android.volley.** { *; } -keep interface com.android.volley.** { *; } -keepattributes *Annotation* ##---------------Begin: proguard configuration for Gson ---------- # Gson uses generic type information stored in a class file when working with fields. Proguard # removes such information by default, so configure it to keep all of it. -keepattributes Signature # For using GSON @Expose annotation #-keepattributes *Annotation* -keepattributes EnclosingMethod # Gson specific classes -keep class sun.misc.Unsafe { *; } -keep class com.google.gson.stream.** { *; } # Application classes that will be serialized/deserialized over Gson -keep class Categorias.data.model.** { *; } -keep class Categorias.** { *; } # Application classes that will be serialized/deserialized over Gson -keep class com.google.gson.examples.android.model.** { *; } -keep class com.puertosoft.appcomercialdelpuerto.android.model.** { *; } -keep class com.puertosoft.appcomercialdelpuerto.model.** { *; } -keep class com.puertosoft.appcomercialdelpuerto.model.User { *; } # Add the gson class -keep public class com.google.gson # Add any classes the interact with gson -keep class com.puertosoft.appcomercialdelpuerto.models.ChatModel { *; } -keep class com.puertosoft.appcomercialdelpuerto.models.FeedModel { *; } -keep class com.puertosoft.appcomercialdelpuerto.android.models.ChatModel { *; } -keep class com.puertosoft.appcomercialdelpuerto.android.models.FeedModel { *; } -libraryjars /build/intermediates/pre-dexed/debug/gson-2.3-08958b96da94c86264ec30e35a9d524bac95d2df.jar -printmapping outputfile.txt -renamesourcefileattribute SourceFile #-keepattributes SourceFile,LineNumberTable

Esta es la clase afectada.

public class Categorias { private String idCategoria; private String descripcionCategoria; private String imagenCategoria; public Categorias(String idCategoria, String descripcionCategoria, String imagenCategoria){ this.idCategoria=idCategoria; this.descripcionCategoria=descripcionCategoria; this.imagenCategoria=imagenCategoria; } public String getIdCategoria(){ return idCategoria; } public String getDescripcionCategoria(){ return descripcionCategoria; } public String getImagenCategoria(){ return imagenCategoria; } }


Debe excluir la ofuscación de sus clases modelo como a continuación, donde excluí todas las clases modelo en el paquete in.intellicode.webservices.models

-keep class in.intellicode.webservices.models.** { *; } -keep class in.intellicode.models.** { *; } -keep class in.intellicode.events.*{ *; } -keepattributes Signature -keepattributes *Annotation* -keep class sun.misc.Unsafe { *; }


Los nombres de las variables serán ofuscados con proguard, dejándote con algo como

private String a;

En lugar de

private String descripcionCategoria;

Puedes agregar reglas de programación para que algunas clases no se ofusquen. Me salí con la suya usando estos:

-keepattributes Signature # POJOs used with GSON # The variable names are JSON key values and should not be obfuscated -keepclassmembers class com.example.apps.android.Categorias { <fields>; } # You can apply the rule to all the affected classes also # -keepclassmembers class com.example.apps.android.model.** { <fields>; }

Si su nombre de clase POJO también se usa para el análisis, también debe agregar la regla

-keep class com.example.apps.android.model.** { <fields>; }

En su caso, las anotaciones no se utilizan, necesitaría esto si lo hace.

# Keep the annotations -keepattributes *Annotation*

Otra forma de resolver este problema es usar la anotación SerializedName y dejar que la clase se confunda. Para esto todavía necesitará la -keepattributes *Annotation* .

import com.google.gson.annotations.SerializedName @SerializedName("descripcionCategoria") private String descripcionCategoria;


Si desea que sus modelos aún estén ofuscados, use la anotación @SerializedName("name_of_json_field") . Le permitirá a gson saber el nombre real del campo.

Creo que también necesitarás

-keepattributes *Annotation*

para mantener sus anotaciones de ofuscación