我正在尝试提取没有root权限的已安装Android应用的APK文件。
我以为这是不可能的,因为非系统应用程序的所有APK文件都位于/ data / app中,并且访问此文件夹需要root权限。然后,我发现Google Play商店中有许多应用程序似乎可以访问APK文件,即使在非根目录设备上也是如此。
有人可以告诉我这怎么可能吗?没有备份应用程序可以无根备份APK文件吗?
我正在尝试提取没有root权限的已安装Android应用的APK文件。
我以为这是不可能的,因为非系统应用程序的所有APK文件都位于/ data / app中,并且访问此文件夹需要root权限。然后,我发现Google Play商店中有许多应用程序似乎可以访问APK文件,即使在非根目录设备上也是如此。
有人可以告诉我这怎么可能吗?没有备份应用程序可以无根备份APK文件吗?
Answers:
无需root许可即可访问/ data / app;该目录的权限为rwxrwx--x。对目录具有执行权限意味着您可以访问它,但是缺少读取权限意味着您无法获得其内容的列表-因此,要访问该目录,您必须知道将要访问的文件的名称。Android的软件包管理器将告诉您给定软件包的已存储apk的名称。
要从命令行执行此操作,请使用adb shell pm list packages
来获取已安装软件包的列表并找到所需的软件包。
使用包名称,我们可以使用来获取APK的实际文件名和位置adb shell pm path your-package-name
。
知道完整目录后,我们终于可以使用 adb pull full/directory/of/the.apk
感谢@tarn指出在Lollipop下,apk路径将是 /data/app/your-package-name-1/base.apk
adb shell pm list packages
来获取已安装软件包的列表,选择所需的软件包,追加-1.apk
到该软件包,然后从中提取/data/app
。示例:如果程序包名称为org.mozilla.firefox
,请使用adb pull /data/app/org.mozilla.firefox-1.apk
。
adb: error: remote object '/data/app/com.Slack-1/base.apk' does not exist
Android会在包名称后附加一个序列号以产生最终的APK文件名(这可能会随Android OS的版本而有所不同)。以下命令序列在无根设备上运行:
获取所需包的APK文件的完整路径名。
adb shell pm path com.example.someapp
输出为:package:/data/app/com.example.someapp-2.apk
。
将APK文件从Android设备拉至开发框。
adb pull /data/app/com.example.someapp-2.apk
成功拉取后,APK的位置将位于PC /笔记本电脑上的../sdk/platform-tools/base.apk。
您不需要ROOT权限即可获取已安装应用程序的列表。
您可以使用android PackageManager做到这一点。
以下是一个小代码段。
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);
}
当您安装了Eclipse for Android开发时:
在牛轧糖(7.0)上运行Android版本adb shell pm list packages
以列出设备上安装的软件包。然后运行adb shell pm path your-package-name
以显示apk的路径。使用adb将包复制到Downloads之后adb shell cp /data/app/com.test-1/base.apk /storage/emulated/0/Download
。然后通过运行将“下载”中的apk拉到您的计算机上adb pull /storage/emulated/0/Download/base.apk
。
我有一个 does not exist error
这是我的工作方式:
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)
列表PackageManager.getInstalledApplications()将为您提供已安装应用程序的列表,ApplicationInfo.sourceDir是.apk文件的路径。
// 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
我找到了一种在非root用户设备中获取APK软件包名称的方法。它不是很优雅,但是可以一直工作。
步骤1:在您的设备上,打开目标APK
步骤2:在PC cmd窗口中,键入以下命令:
adb shell dumpsys activity a > dump.txt
因为此命令的输出很多,所以建议重定向到文件。
步骤3:使用任何编辑器打开dump.txt文件。
对于Android 4.4之前的设备:
文件的开头如下所示:
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
软件包名称在第三行com.tencent.mm在本示例中为。
对于Android 4.4及更高版本:
dumpsys的输出已更改了一点。尝试搜索“堆栈#1”,程序包名称将在其下方非常接近。
另外,搜索“ baseDir”,您将找到apk文件的完整路径!