赞
踩
本篇记录笔者对Android开发中代码混淆的认知
关于代码混淆的定义,这里笔者选择自己认为讲的相对完整的话进行呈现
Java 是一种跨平台的、解释型语言,Java 源代码编译成中间”字节码”存储于 class 文件中。由于跨平台的需要,Java 字节码中包括了很多源代码信息,如变量名、方法名,并且通过这些名称来访问变量和方法,这些符号带有许多语义信息,很容易被反编译成 Java 源代码。为了防止这种现象,我们可以使用 Java 混淆器对 Java 字节码进行混淆。
混淆就是对发布出去的程序进行重新组织和处理,使得处理后的代码与处理前代码完成相同的功能,而混淆后的代码很难被反编译,即使反编译成功也很难得出程序的真正语义。被混淆过的程序代码,仍然遵照原来的档案格式和指令集,执行结果也与混淆前一样,只是混淆器将代码中的所有变量、函数、类的名称变为简短的英文字母代号,在缺乏相应的函数名和程序注释的况下,即使被反编译,也将难以阅读。同时混淆是不可逆的,在混淆的过程中一些不影响正常运行的信息将永久丢失,这些信息的丢失使程序变得更加难以理解。
混淆器的作用不仅仅是保护代码,它也有精简编译后程序大小的作用。由于以上介绍的缩短变量和函数名以及丢失部分信息的原因, 编译后 jar文件体积大约能减少25%
根据以上定义,可以简单对混淆的好处和坏处总结如下
混淆的坏处如下
将minifyEnabled的值改为true即开启:其中debug为测试版本,release为发布版本
开启混淆后Android会用自带的混淆进行代码混淆,如在安装Android SDK的目录下的proguard-android.txt或proguard-android-optimize.txt文件为默认混淆文件。对于自己定义的混淆需要在proguard-rules.pro文件中进行配置:
类:需要使用完全限定名;
*:通配符,任意字符串,不包含包名分隔符(.);
**:通配符,任意字符串,包含包名分隔符(.);
extends:继承某类的类;
implement:实现某接口的类;
$:内部类;
:所有构造方法;
:所有成员变量;
:所有方法;
…:任意参数;
修饰符:public private protected
因为我们提供给别人的一般都是release版本的库,所以要在build.gradle中开启release版代码混淆,配置好混淆规则后在Android studio的Terminal界面输入:
gradlew assembleRelease 再回车进行编译打包,如果编译失败则检查配置的混淆规则。成功后即可得到混淆后的aar或apk文件:
将报错的或者自己不需要的删除即可,然后在最后添加自己不需要混淆的代码:
#---------这里提供一份这个lib中最好不要混淆的地方,前边的配置都差不多,主要是第三方包以及其他不需要混淆的代码---- #---------------------------------基本指令以及一些固定不混淆的代码--开始-------------------------------- #<基本指令> -optimizationpasses 5 -dontskipnonpubliclibraryclassmembers -optimizations !code/simplification/cast,!field/*,!class/merging/* -keepattributes *Annotation*,InnerClasses -keepattributes Signature -keepattributes SourceFile,LineNumberTable #忽略警告 -ignorewarning #记录生成的日志数据,gradle build时在本项目根目录输出apk 包内所有 class 的内部结构 -dump class_files.txt #未混淆的类和成员 -printseeds seeds.txt #列出从 apk 中删除的代码 -printusage unused.txt #混淆前后的映射 -printmapping mapping.txt #</基本指令> #<基础> -keep public class * extends android.app.Activity -keep public class * extends android.app.Application -keep public class * extends android.support.multidex.MultiDexApplication -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 * extends android.view.View -keep public class com.android.vending.licensing.ILicensingService -keep class android.support.** {*;} #</基础> #<view相关> -keep public class * extends android.view.View{ *** get*(); void set*(***); public <init>(android.content.Context); public <init>(android.content.Context, android.util.AttributeSet); public <init>(android.content.Context, android.util.AttributeSet, int); } -keepclasseswithmembers class * { public <init>(android.content.Context, android.util.AttributeSet); public <init>(android.content.Context, android.util.AttributeSet, int); } -keepclassmembers class * { public void *(android.view.View); } #</view相关> #<Serializable、Parcelable> -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(); } -keep public class * implements java.io.Serializable {*;} -keep class * implements android.os.Parcelable { public static final android.os.Parcelable$Creator *; } #</Serializable、Parcelable> #<R文件> -keep class **.R$* { *; } #</R文件> #<enum> -keepclassmembers enum * { public static **[] values(); public static ** valueOf(java.lang.String); } #</enum> #<natvie> -keepclasseswithmembernames class * { native <methods>; } #</natvie> #---------------------------------基本指令以及一些固定不混淆的代码--结束----------- #---------------------------------第三方包--开始------------------------------- #<okhttp3.x> -dontwarn com.squareup.okhttp3.** -keep class com.squareup.okhttp3.** { *;} -dontwarn okio.** #</okhttp3.x> #<retrofit2.x> -dontnote retrofit2.Platform -dontwarn retrofit2.Platform$Java8 -keepattributes Signature -keepattributes Exceptions -dontwarn okio.** #</retrofit2.x> #</okhttp3.x> #<ButterKnife 7.0 以上> -keep class butterknife.** { *; } -dontwarn butterknife.internal.** -keep class **$$ViewBinder { *; } -keepclasseswithmembernames class * { @butterknife.* <fields>; } -keepclasseswithmembernames class * { @butterknife.* <methods>; } #</ButterKnife 7.0 以上> #<eventbus 3.0> -keepattributes *Annotation* -keepclassmembers class ** { @org.greenrobot.eventbus.Subscribe <methods>; } -keep enum org.greenrobot.eventbus.ThreadMode { *; } -keepclassmembers class * extends org.greenrobot.eventbus.util.ThrowableFailureEvent { <init>(java.lang.Throwable); } #</eventbus 3.0> #<Gson> -keep class com.google.gson.** {*;} -keep class com.google.**{*;} -keep class sun.misc.Unsafe { *; } -keep class com.google.gson.stream.** { *; } -keep class com.google.gson.examples.android.model.** { *; } #</Gson> #<glide> -keep public class * implements com.bumptech.glide.module.GlideModule -keep public enum com.bumptech.glide.load.resource.bitmap.ImageHeaderParser$** { **[] $VALUES; public *; } #</glide> #<Rxjava RxAndroid> -dontwarn rx.* -dontwarn sun.misc.** -keepclassmembers class rx.internal.util.unsafe.*ArrayQueue*Field* { long producerIndex; long consumerIndex; } -keepclassmembers class rx.internal.util.unsafe.BaseLinkedQueueProducerNodeRef { rx.internal.util.atomic.LinkedQueueNode producerNode; } -keepclassmembers class rx.internal.util.unsafe.BaseLinkedQueueConsumerNodeRef { rx.internal.util.atomic.LinkedQueueNode consumerNode; } #</Rxjava RxAndroid> #----------------------------------第三方包--结束-------------------------- #---------------------------------一些不要混淆的代码--开始------------------- -keep class net.arvin.afbaselibrary.nets.** { *; } -keep class net.arvin.afbaselibrary.data.** { *; } #<反射> -keep class net.arvin.afbaselibrary.nets.BaseNet{*;} #</反射> #<js> #</js> #<自定义View的类> -keep class net.arvin.afbaselibrary.ui.views.** {*;} #</自定义View的类> #---------------------------------一些不要混淆的代码--结束-------------------
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。