美文网首页我爱编程
常用混淆配置

常用混淆配置

作者: DorisSunny | 来源:发表于2018-04-13 18:30 被阅读0次

    我们的APK发布之前都需要混淆签名,打包,发布。最近接触混淆,所以写个文章记录一下自己的学习路径,以后用的时候也好回顾一下,善于总结,变成我自己的知识。
    混淆是的官网地址:http://proguard.sourceforge.net/

    AndroidStudiobuild.gradle中配置相应的混淆项,首先build.gradle里面默认有如下一段代码:

    buildTypes {
            release {
                minifyEnabled false
                proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro'
            }
        }
    

    默认不开启混淆,如果需要开启混淆,则将minifyEnabled改成true.

    常见库的混淆配置:
    在Android中有默认的混淆配置,但是可能不满足你的所有的需求,有一些类或者方法不希望被混淆,这个时候就要配置自己的混淆项。

    混淆文件是module的proguard-rules中。

    混淆语法

    -libraryjars class_path 避免混淆第三方jar包 ,后面连接包路径
    -keep {Modifier} {class_specification} 保护指定的类文件和类的成员
    -keepclassmembers {modifier} {class_specification} 保护指定类的成员,如果此类受到保护他们会保护的更好
    -keepclasseswithmembers {class_specification} 保护指定的类和类的成员,但条件是所有指定的类和类成员是要存在。
    -keepnames {class_specification} 保护指定的类和类的成员的名称(如果他们不会压缩步骤中删除)
    -keepclassmembernames {class_specification} 保护指定的类的成员的名称(如果他们不会压缩步骤中删除)
    -keepclasseswithmembernames {class_specification} 保护指定的类和类的成员的名称,如果所有指定的类成员存在(在压缩步骤之后)

    常见配置如下:

    ###-----------基本指令--------------------
    ###-----------指定代码的压缩级别------------
    -optimizationpasses 5
    ###-----------是否使用大小写混合------------
    -dontusemixedcaseclassnames
    ###-----------混淆时是否做预校验------------
    -dontpreverify
    ###-----------混淆时是否记录日志------------
    -verbose
    ###-----------忽略警告------------
    -ignorewarnings
    -keepattributes EnclosingMethod
    
    ###-----------保证异常时显示行号------------
    -renamesourcefileattribute SourceFile
    -keepattributes SourceFile,LineNumberTable
    
     #dump文件列出apk包内所有class的内部结构
    -dump class_files.txt        
    
    #seeds.txt文件列出未混淆的类和成员
    -printseeds seeds.txt
    
    #usage.txt文件列出从apk中删除的代码
    -printusage unused.txt
    
    #mapping文件列出混淆前后的映射
    -printmapping mapping.txt
    
    ###-----------注解------------
    -keepattributes *Annotation*
    
    ###-----------泛型------------
    -keepattributes Signature
    
    ###-----------异常------------
    -keepattributes Exceptions
    
    ###-----------混淆时所采用的算法------------
    -optimizations !code/simplification/arithmetic,!field/*,!class/merging/*
    ###-----------避免混淆Android基本组件的配置--------------------
    ###-----------保持Activity类不被混淆------------
    -keep public class * extends android.app.Activity
    ###-----------保持AppCompatActivity类不被混淆------------
    -keep public class * extends android.support.v7.app.AppCompatActivity
    ###-----------保持DialogFragment类不被混淆------------
    -keep public class * extends android.app.DialogFragment
    ###-----------保持Application类不被混淆------------
    -keep public class * extends android.app.Application
    ###-----------保持Service类不被混淆------------
    -keep public class * extends android.app.Service
    ###-----------保持BroadcastReceiver类不被混淆------------
    -keep public class * extends android.content.BroadcastReceiver
    ###-----------保持ContentProvider类不被混淆------------
    -keep public class * extends android.content.ContentProvider
    ###-----------保持BackupAgentHelper类不被混淆------------
    -keep public class * extends android.app.backup.BackupAgentHelper
    ###-----------保持Preference类不被混淆------------
    -keep public class * extends android.preference.Preference
    ###-----------保持ILicensingService类不被混淆------------
    -keep public class com.android.vending.licensing.ILicensingService
    
    ###-----------保持 native 方法不被混淆------------
    -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 * extends android.app.Activity {
        public void *(android.view.View);
    }
    
    ###-----------保持枚举 enum 类不被混淆------------
    -keepclassmembers enum * {
        public static **[] values();
        public static ** valueOf(java.lang.String);
    }
    
    ###-----------# 保持 Parcelable 不被混淆------------
    -keep class * implements android.os.Parcelable {
        public static final android.os.Parcelable$Creator *;
    } 
    
    ###----------混淆第三方库-----------------
    
    ###-----------保持 retrofit client 不被混淆------------
    -keep class com.excellence.retrofit.RetrofitHttpService { *; }
    
    ###-----------保持 retrofit 不被混淆------------
    -dontwarn retrofit2.**
    -keep class retrofit2.** { *; }
    -dontwarn javax.annotation.**
    
    ###-----------保持 okhttp 不被混淆------------
    -dontwarn com.squareup.okhttp3.**
    -keep class com.squareup.okhttp3.** { *;}
    -dontwarn okio.**
    
    ###-----------保持 GreenDao 不被混淆------------
    -keepclassmembers class * extends org.greenrobot.greendao.AbstractDao {
    public static java.lang.String TABLENAME;
    }
    -keep class **$Properties
    
    ###-----------保持 eventbus 不被混淆------------
    -keepattributes *Annotation*
    -keepclassmembers class ** {
        @org.greenrobot.eventbus.Subscribe <methods>;
    }
    -keep enum org.greenrobot.eventbus.ThreadMode { *; }
    # Only required if you use AsyncExecutor
    -keepclassmembers class * extends org.greenrobot.eventbus.util.ThrowableFailureEvent {
        <init>(java.lang.Throwable);
    }
    
    ###-----------保持 bugly 不被混淆------------
    -dontwarn com.tencent.bugly.**
    -keep public class com.tencent.bugly.**{*;}
    
    ###-----------保持 gson 不被混淆------------
    -keep class sun.misc.Unsafe { *; }
    -keep class com.google.gson.stream.** { *; }
    
    ###-----------保持 Rxjava RxAndroid 不被混淆------------
    -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;
    }
    
    ###-----------保持 volley 不被混淆------------
    -keep class com.android.volley.** { *; }
    -keep class com.android.volley.toolbox.** { *; }
    

    当你的工程引用了其他库的时候,你应该对该库也进行混淆配置。混淆配置完了之后需要详细的测试是否有问题,可能由于混淆导致某个类找不到了从而程序不能正常运行。

    混淆虽然可以一定程度上防止别人反编译你的代码,但是混淆也存在缺点,混淆之后的代码,对于开发人员定位问题的位置不太友好,因为报错都是abcd之类的名字,我们也不知道是哪个类,哪个方法了。不过还好,我们有工具协助。可以将错误还原成原来的代码。

    首先找到你的Android的sdk目录。然后找到tools--> proguard -->bin-->proguardgui.bat.双击打开之后如下图:

    2中mapping.txt的路径app\build\outputs\mapping\发布渠道\release\mapping.txt,这个文件记录了混淆的规则,混淆前类和混淆后类的对应关系,所以可以根据这个文件还原混淆前的类,我觉得翻译成原来的类更为贴切。
    这样你就可以对已经发布的apk,bug的log进行翻译并且定位了。

    PS: 工程配置了混淆之后,需要详细测试,因为可能由于混淆之后某些类找不到从而影响程序正常运作。

    参考:
    Android混淆总结篇(一)
    5分钟搞定android混淆

    相关文章

      网友评论

        本文标题:常用混淆配置

        本文链接:https://www.haomeiwen.com/subject/hwrhkftx.html