I'm trying to extract the APK file of an installed Android app WITHOUT root permissions.
I thought that this was impossible, because all APK files for non-system-apps are located in /data/app, and accessing this folder requires root permission. Then I found that there are numerous apps in the Google Play store that seem to have access to the APK files even on non-rooted devices.
Can someone tell me how this is possible? Aren't there backup apps which backup the APK files without root?
List PackageManager.getInstalledApplications() will give you a list of the installed applications, and ApplicationInfo.sourceDir is the path to the .apk file.
// in oncreate
PackageManager pm = getPackageManager();
for (ApplicationInfo app : pm.getInstalledApplications(0)) {
Log.d("PackageList", "package: " + app.packageName + ", sourceDir: " + app.sourceDir);
}
//output is something like
D/PackageList(5010): package: com.example.xmlparse, sourceDir: /data/app /com.example.xmlparse-2.apk
D/PackageList(5010): package: com.examples.android.calendar, sourceDir: /data/app/com.examples.android.calendar-2.apk
D/PackageList(5010): package: com.facebook.katana, sourceDir: /data/app/com.facebook.katana-1.apk
D/PackageList(5010): package: com.facebook.samples.profilepicture, sourceDir: /data/app/com.facebook.samples.profilepicture-1.apk
D/PackageList(5010): package: com.facebook.samples.sessionlogin, sourceDir: /data/app/com.facebook.samples.sessionlogin-1.apk
D/PackageList(5010): package: com.fitworld, sourceDir: /data/app/com.fitworld-2.apk
D/PackageList(5010): package: com.flipkart.android, sourceDir: /data/app/com.flipkart.android-1.apk
D/PackageList(5010): package: com.fmm.dm, sourceDir: /system/app/FmmDM.apk
D/PackageList(5010): package: com.fmm.ds, sourceDir: /system/app/FmmDS.apk
Or you can get 'Bluetooth File Transfer' from Google Play and set the home folder to /system/
. Then you can even go to /
.
You don't need ROOT permissions to get the list of Installed Apps.
You can do it with android PackageManager.
Below is a small code snippet.
final PackageManager pm = getPackageManager();
//get a list of installed apps.
List<ApplicationInfo> packages = pm.getInstalledApplications(PackageManager.GET_META_DATA);
for (ApplicationInfo packageInfo : packages) {
Log.d(TAG, "Installed package :" + packageInfo.packageName);
Log.d(TAG, "Apk file path:" + packageInfo.sourceDir);
}
Android appends a sequence number to the package name to produce the final APK file name (it's possible that this varies with the version of Android OS). The following sequence of commands works on a non-rooted device:
Get the full path name of the APK file for the desired package.
adb shell pm path com.example.someapp
This gives the output as: package:/data/app/com.example.someapp-2.apk
.
Pull the APK file from the Android device to the development box.
adb pull /data/app/com.example.someapp-2.apk
The location of APK after successful pulling will be at ../sdk/platform-tools/base.apk on your pc/laptop.
When you have Eclipse for Android developement installed:
I found a way to get the APK's package name in a non-root device. it's not so elegant, but works all the time.
Step 1: on your device, open the target APK
Step 2: on PC cmd window, type this commands:
adb shell dumpsys activity a > dump.txt
because the output of this command is numerous, redirect to a file is recommended.
Step 3: open this dump.txt file with any editor.
for device befor Android 4.4:
the beginning of the file would be looked like this:
ACTIVITY MANAGER ACTIVITIES (dumpsys activity activities)
Main stack:
* TaskRecord{41aa9ed0 #4 A com.tencent.mm U 0}
numActivities=1 rootWasReset=true userId=0
affinity=com.tencent.mm
intent={act=android.intent.action.MAIN cat=[android.intent.category.LAUNCHER] flg=0x10600000 cmp=com.tencent.mm/.ui.LauncherUI}
realActivity=com.tencent.mm/.ui.LauncherUI
askedCompatMode=false
lastThumbnail=null lastDescription=null
lastActiveTime=19915965 (inactive for 10s)
* Hist #9: ActivityRecord{41ba1a30 u0 com.tencent.mm/.ui.LauncherUI}
packageName=com.tencent.mm processName=com.tencent.mm
the package name is in the 3rd line, com.tencent.mm for this example.
for Android 4.4 and later:
the dumpsys output has changed a little.
try search "Stack #1", the package name would be very close below it.
Also, search "baseDir", you will find the full path of the apk file!
I got a does not exist error
Here is how I make it works:
adb shell pm list packages -f | findstr zalo
package:/data/app/com.zing.zalo-1/base.apk=com.zing.zalo
adb shell
mido:/ $ cp /data/app/com.zing.zalo-1/base.apk /sdcard/zalo.apk
mido:/ $ exit
adb pull /sdcard/zalo.apk Desktop
/sdcard/zalo.apk: 1 file pulled. 7.7 MB/s (41895394 bytes in 5.200s)
Open ES explorer -> push Menu button at the left upper corner (three horizontal stripes) -> in the Libraries section choose APPs.
Thus, you get the list of all the user apps. Find your app and select it with long pushing on it. Then press "More" in the right low corner and choose "Send". Then you can use different options, e.g. you can choose "ES Save To" in order to save the .apk file to your home directory or anywhere else.
On Nougat(7.0) Android version run adb shell pm list packages
to list the packages installed on the device.
Then run adb shell pm path your-package-name
to show the path of the apk.
After use adb to copy the package to Downloads adb shell cp /data/app/com.test-1/base.apk /storage/emulated/0/Download
.
Then pull the apk from Downloads to your machine by running adb pull /storage/emulated/0/Download/base.apk
.
Source: Stackoverflow.com