Secure your codes by enabling Proguard in Android App
Nowadays it is quite easy to reverse engineer and android application. An .apk file can be decompiled easily back to its original code by using some tools for example dex2jar, javadecompilers. A beginner level android developer or hacker or some bad guys can reuse your code by decompiling your .apk file. So there is a need to optimize your code. Is’t there ?
Don’t be afraid,your solution is here. To prevent someone to read your code you can use a tool that will make your codes harder to read. And the tool is Proguard.
Functions of Proguard
The main function of proguard: Obfuscation. It has also two other important functions: Shrinking and Optimization.
- Obfuscation: Obfuscation is a process that make potential attacker’s life harder to read your code. It renames the remaining classes, fields, and methods using short meaningless names and — make your APK difficult to reverse engineer which is especially valuable when your app uses security-sensitive features, such as licensed verification.
- Shrinking: detects and removes unused codes and resources and — make the APK as small as possible.
- Optimization: analyzes and optimizes the bytecode of the methods.
{ Note: Proguard does not prevent reverse engineering. But it does make it harder, “ The obfuscated code makes your APK difficult to reverse engineer” according to android developer docs. }
Enable Proguard in Android Studio
Enabling proguard in android studio is really easy. Because Proguard is being added to android studio as a default tool but by default it remain disable. You just have to make minifyEnabled true from build.gradle file in your project and proguard will start working. Below is the process how to enable default ProGuard in Android Studio.
- Go to the build.gradle(Module: app) file of app. This is the default build.gradle(Module:app) where minifyEnabled false.
1 2 3 4 5 6 |
buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } |
2. Just make minifyEnabled true for enable proguard. You may also enable shrinkResources and useProguard true for reducing your apk size by removing unused codes and resources.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 |
buildTypes { debug { shrinkResources true minifyEnabled true useProguard true debuggable true proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } release { shrinkResources true // Shrink your resources minifyEnabled true // Obfuscate and minify your code useProguard true // Remove your unused codes proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } |
Here i configured my files both for release and debug mode. You may disabled proguard for debug mode. In that case just make minifyEnabled false, shrinkResources false, useProguard false in debug.
{Now if your project doesn’t have any third party library, it will work file. But if you add any third party library in your project you must specify proguard-rules for that specific library in proguard-rules.pro
file. Otherwise your log will full with a lots of errors and it will be very pathetic.}
Maximum third party library provide their proguard-rules in their repository. If you failed to find them, you may search in google or whatever. Here i am providing proguard-rules for some libraries that we normally use in our apps.
Proguard Configuration for Retrofit/GSON
- If you use Retrofit in your application and you want to enable proguard, you will need to configure ProGuard to exclude certain Retrofit and related JSON data classes files from being obfuscated.
- Also you must note that if you are using GSON for conversion from JSONto POJO representation, you must ignore those POJO classes from being obfuscated, this is required as if those POJO class field names are obfuscated, conversion to POJO’s from JSON would fail because POJO field names are inferred from JSON response.
Bottom Line: You must exclude the POJO’s from being obfuscated that you have created for mapping JSON response in Retrofit/Application or any class that will be serialized/deserialized over Gson.
Let say i do not want to obfuscate apiResponse package that contained all POJO classes , then i have to add the following rule:
1 |
<strong class="markup--strong markup--pre-strong">-keep </strong>class shishirtstudio.com.proguardtest.data.network.apiResponse.** { *; } |
Some Text files generated with Proguard Enabled
When you build an APK with ProGuard enabled, there are additional output text files are created. The files are:
dump.txt — describes the internal structure of all the class files in the APK.
mapping.txt — provides a translation between the original and obfuscated class, method, and field names. You must have to upload it at different places like PlayStore Console for seeing the original stack-trace of the crashes.
seeds.txt — lists the classes and members that were not obfuscated.
usage.txt — lists the code that was removed from the APK.
These files are saved at — app/build/outputs/mapping/release/
[{ After uploading our release apk we can see crash report that contained class name, method name etc if there is a crash. But if we obfuscate our codes with proguard, you know class name, method name will be changed. So it will very difficult/impossible to read that crash. So what should we do ?
There is a easy solution. just upload the mapping.text file in playstore with your apk and Google will handle everything. To upload you mapping.text
file follow the below process }]
- Sign in to your Play Console.
- Select your app.
- On the left menu, click Android vitals > Deobfuscation files.
- Next to a version of your app, click Upload.
- Upload the ProGuard
mapping.txt
file for the version of your app.
Some important points while using Proguard.
- If you want to use proguard in your app. Then try to use from beginning.
- While using proguard it will take more time to build your app. That’s why you may disable (false) proguard in debug mode. But in that case you must enable it for checking your whole project before generating released apk.
- Do not forget to add the proguard rules in
proguard-rules.pro
file for any library that you have included in your project. - Do not forget to upload
mapping.text
file in playstore. - Say, your app started crashing for a specific class after enabling proguard. But you aren’t finding any reason for that. In this case you should exclude that class to be obfuscated be specifying rules in proguard-rules.pro file.
- If you want to just obfuscate your codes but do not want to remove any unused classes then add add two lines in
proguard-rules.pro
file.
1 2 |
-dontshrink -dontoptimize |
- During the build process, proguard checks the
AndroidManifest
and keeps all activity classes. This is needed for your app to run. You should not obfuscate classes which extend android.app.Activity.
Syntax of writing proguard-rules (Proguard Manual)
There are different ways to keep
option that you can use to configure Proguard:
-keep : keep classes and class members.
-keepclassmembers : keep class members only.
-keepclasseswithmembers : keep classes and class members, if class members present.
For more info see here.
- To exclude a class from obfuscation, Keep the attributes of InnerClasses, keep your class and keep the class members of the class. For example:
1 2 |
-keepattributes InnerClasses -keep class com.yourproject.YourClass** {*;} |
{ Here, keep class means you are telling proGuard: Don’t Touch this class, dontwarn means, whatever problems happen … don’t tell me }
- To exclude all class of a specific package from obfuscation use the following configuration.
1 |
-keep public class com.yourproject.yourpackage.* |
- To exclude all public class of a specific package and its sub packages from obfuscation use the following configuration.
1 |
-keep public class com.yourproject.yourpackage.** |
- To exclude all public/protected/private classes/fields/methods of a specified package and its sub packages use the following configuration.
1 |
-keep public class com.yourproject.yourpackage.** { *;} |
{ Here, double-asterisk in the package means every class under every package under that top-level package; and the asterisk inside the curly braces applies to every member (variables, methods, and constants) inside those class. }
APK Analyzer and ProGuard
Android Studio includes an APK Analyzer that provides immediate insight into the composition of your APK after the build process completes. Using the APK Analyzer can reduce the time you spend debugging issues with DEX files and resources within your app, and help reduce your APK size. (From developer.android.com)
There are three ways to access the APK Analyzer when a project is open:
- Drag an APK into the Editor window of Android Studio.
- Switch to the Project perspective in the Project window and then double-click the APK in the default
build/output/apks/
directory. - Select Build > Analyze APK in the menu bar and then select your APK.
— APK Analyzer also shows raw file size and download file size values for each entity.
— The APK Analyzer in Android Studio can help you see the obfuscated codes also which classes were removed by ProGuard and generate keep rules for them.
— By load mapping text files into the APK Analyzer (using the “Load Proguard mappings… “ button), you get some additional functionality in the dex tree view.(Do google for that).
Note: APK Analyzer works best with release builds. If you need to analyze a debug build of your app, make sure you are using an APK that is not instrumented for Instant Run
I hope you liked this article. Feel free to give your feedback in comment below. I would be very happy to get new suggestions.
Happy Coding 🙂
1 2 3 4 5 6 |
buildTypes { release { minifyEnabled false proguardFiles getDefaultProguardFile('proguard-android.txt'), 'proguard-rules.pro' } } |
Recent Comments