什么是代碼混淆
刪除無用代碼瘪菌,將代碼中的各種元素撒会,如包名、類名师妙、函數(shù)名诵肛、變量名等改成無意義的符號,使得反編譯你apk的人無法根據(jù)名字猜測代碼的用途默穴,這是一種加密手段怔檩。
為什么要進行代碼混淆
如果代碼沒經(jīng)過混淆,發(fā)布出去后蓄诽,別人只需要反編譯即可查看你的源碼薛训,這是一種知識產(chǎn)權的保護手段。
代碼混淆是否能保證代碼的絕對安全
混淆的目的是為了加大反編譯的成本,但是并不能徹底防止反編譯
怎么進行代碼混淆
使用Android Studio創(chuàng)建項目時會在項目根目錄下生成一個proguard-rules.pro文件仑氛,該文件便是指定項目混淆規(guī)則的文件乙埃,使用的時候只需要在里面加入相應的混淆規(guī)則即可闸英。也就是說,你在這個文件里面指定 哪些代碼需要混淆介袜,哪些不需要
keep相關語法
1.keep [,modifier,...] class_specification 不混淆指定的類文件和類的成員
例如:
(1).保留某個包下面的類以及子包 -keep public class com.droidyue.com.widget.**
(2).-keep class com.czy.**//不混淆所有com.czy包下的類甫何,** 換成具體的類名則表示不混淆某個具體的類
(3).-keep class com.clock.**{*;}//不混淆所有com.clock包下的類和類中的所有成員變量,**可以換成具體類名遇伞,*可以換成具體的字段辙喂,可參照Serialzable的混淆
2.keepclassmembers [,modifier,...] class_specification 不混淆指定類的成員,如果此類受到保護他們會被保護得更好
例如:
(1).保留所有類中使用otto的public方法:
-keepclassmembers class ** {
@com.squareup.otto.Subscribe public *;
@com.squareup.otto.Produce public *;
}
(2).保留Contants類的BOOK_NAME屬性:
-keepclassmembers class com.example.admin.proguardsample.Constants {
public static java.lang.String BOOK_NAME;
}
3.keepclasseswithmembers [,modifier,...] class_specification 不混淆指定的類和類的成員鸠珠,但條件是所有指定的類和類成員是要存在巍耗。
4.keepnames class_specification 不混淆指定的類和類的成員的 名稱(如果他們不會壓縮步驟中刪除)
5.keepclassmembernames class_specification 不混淆指定的類的 成員的名稱 (如果他們不會壓縮步驟中刪除)
6.keepclasseswithmembernames class_specification 不混淆指定的類和類的成員 的名稱,如果所有指定的類成員出席(在壓縮步驟之后)
7.printseeds {filename} 列出類和類的成員-keep選項的清單跳芳,標準輸出到給定的文件
混淆的基本命令
keep 保留芍锦,例如keepattributes:表示保留屬性 dont 不要,例如dontwarn:表示不要提示警告 ignore 忽略飞盆,例如ignorewarning:表示忽略警告
兩個常用的混淆命令娄琉,注意一顆星表示只是保持該包下的類名,而子包下的類名還是會被混淆吓歇;兩顆星表示把本包和所含子包下的類名都保持孽水;
- keep class com.jiyun.demo**
- keep class com.jiyun.demo.*
- dontusemixedcaseclassnames表示混淆時不使用大小寫混合類名。
- dontskipnonpubliclibraryclasses表示不跳過library中的非public的類城看。
- verbose表示打印混淆的詳細信息女气。
- dontoptimize表示不進行優(yōu)化,建議使用此選項测柠,因為根據(jù)proguard-android-optimize.txt中的描述炼鞠,優(yōu)化可能會造成一些潛在風險,不能保證在所有版本的Dalvik上都正常運行轰胁。
- dontpreverify表示不進行預校驗谒主。這個預校驗是作用在JAVA平臺上的,Android平臺上不需要這項功能赃阀,去掉之后還可以加快混淆速度霎肯。
- keepattributes Annotation表示對注解中的參數(shù)進行保留。
注意事項
保留我們使用的四大組件榛斯,自定義的Application等等這些類不被混淆观游,因為這些子類都有可能被外部調(diào)用。
- 使用了自定義控件那么要保證它們不參與混淆
- 使用了枚舉要保證枚舉不被混淆
- 對第三方庫中的類不進行混淆
- 運用了反射的類也不進行混淆
- 使用了 Gson 之類的工具要使 JavaBean 類即實體類不被混淆
- 在引用第三方庫的時候驮俗,一般會標明庫的混淆規(guī)則的懂缕,建議在使用的時候就把混淆規(guī)則添加上去,免得到最后才去找
- 有用到 WebView 的 JS 調(diào)用也需要保證寫的接口方法不混淆王凑,原因和第一條一樣
- Parcelable 的子類和 Creator 靜態(tài)成員變量不混淆搪柑,否則會產(chǎn)生 Android.os.BadParcelableException 異常