Android 提取(备份)apk(安装包)

Android 提取(备份)apk(安装包)

一、通过安卓代码的方式

主要分三步:

  1. 根据应用找到包名
  2. 根据包名获得apk
  3. 提取apk

提取apk代码

private static final String BACKUP_PATH = "/sdcard/backup1/";
private static final String APK = ".apk";

private void copyApk(String name, String path) {
    String dest = BACKUP_PATH + name + APK;
    //path:app程序源文件路径  dest:新的存储路径  name:app名称
    new Thread(new CopyRunnable(path, dest, name)).start();
}

private String getApk(String packageName) {
    String appDir = null;
    try {
        //通过包名获取程序源文件路径
        appDir = getPackageManager().getApplicationInfo(packageName, 0).sourceDir;
    } catch (PackageManager.NameNotFoundException e) {
        e.printStackTrace();
    }
    return appDir;
}

/**
 * 将程序源文件Copy到指定目录
 */
private class CopyRunnable implements Runnable {
    private String source;
    private String dest;
    private String key;

    public CopyRunnable(String source, String dest, String key) {
        this.source = source;
        this.dest = dest;
        this.key = key;
    }

    @SuppressLint("StringFormatInvalid")
    @Override
    public void run() {
        // TODO Auto-generated method stub
        try {
            int length = 1024 * 1024;
            if (!new File(BACKUP_PATH).exists()) {
                boolean mk = new File(BACKUP_PATH).mkdirs();
                if (mk) {
                    System.out.println("true");
                }
            }

            File fDest = new File(dest);
            if (fDest.exists()) {
                fDest.delete();
            }
            fDest.createNewFile();
            FileInputStream in = new FileInputStream(new File(source));
            FileOutputStream out = new FileOutputStream(fDest);
            FileChannel inC = in.getChannel();
            FileChannel outC = out.getChannel();
            int i = 0;
            while (true) {
                if (inC.position() == inC.size()) {
                    inC.close();
                    outC.close();
                    //成功
                    break;
                }
                if ((inC.size() - inC.position()) < 1024 * 1024) {
                    length = (int) (inC.size() - inC.position());
                } else {
                    length = 1024 * 1024;
                }
                inC.transferTo(inC.position(), length, outC);
                inC.position(inC.position() + length);
                i++;
            }
        } catch (Exception e) {
            // TODO: handle exception
            Log.e("TAG", e.toString());
        }
    }
}

调用

CharSequence label = applicationInfo.loadLabel(getPackageManager());
//百度地图_1.0.1
copyApk(label.toString() + "_" + versionName, getApk(applicationInfo.packageName));

二、通过adb的方式

第一步:找到待提取APK的包名

adb shell pm list packages  #打印系统中所有apk的包名
adb shell pm list packages -3 #列出除了系统应用的第三方应用包名

第二步:通过包名,找到对应的apk文件目录

adb shell pm path com.xxx.xxx 	#进入对应包名的apk文件目录
// 成功后会出现:package:data/data/(包名)/.base.apk或者package:/system/app/xxx/xxx.apk 或者 package:/data/app/xxx/xxx.apk 

第三步:将对应的apk提取出来

// 在apk文件目录中将对应apk提取出来
adb pull /system/app/xxx/xxx.apk   或者 adb pull /data/app/xxx/xxx.apk
// 提取出来的文件在adb的配置目录下,一般是在 C:\Users\Administrator> 目录下
// apk文件位置在执行adb命令的目录

或者手机位置复制

cp apk的位置 /sdcard/xxx.apk

三、通过安卓应用的方式

这里推荐几个应用

  1. MT管理器

  2. Skit

​ 其中 免费版 提供安装包提取、分享和应用列表等大部分核心功能,付费版 可以解锁应用统计、分析与界面自定义功能

  1. My APK

  2. ES文件管理器

  3. 手机QQ

等等,好多应用都支持提取apk

四、架构问题

如果出现从模拟器提取的应用在手机上装不上等问题,可能是apk支持的架构不适用。

请参考

五、参考

Android 备份(提取)apk

Android 获取已安装的APP并提取源文件(.apk安装包)

Android开发中,如何从系统固件里提取可用的APK

  • 10
    点赞
  • 9
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值