Android 静默更新安装 apk

版权声明:原创文章,转载请注明来源 http://blog.csdn.net/lxmy2012 https://blog.csdn.net/lxmy2012/article/details/79799003

Android 静默更新安装 apk

需要说明的是:一般的应用没有权限干这事,这里需要Root权限。
集成系统预装应用时用到,记录之。

一般系统intent安装

/**
 * 安装apk
 *
 * @param context
 * @param file
 */
public static void installFile(Context context, File file) {
    Intent intent = new Intent();
    intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    intent.setAction(android.content.Intent.ACTION_VIEW);
    intent.setDataAndType(Uri.fromFile(file), "application/vnd.android.package-archive");
    context.startActivity(intent);
}

/**
 * 卸载apk
 *
 * @param context
 * @param pkgName
 */
public static void unstallApk(Context context, String pkgName) {
    Uri packageURI = Uri.parse("package:" + pkgName);
    Intent uninstallIntent = new Intent(Intent.ACTION_DELETE, packageURI);
    context.startActivity(uninstallIntent);
}

静默安装

andorid 代码是可以执行adb shell 命令的,这里静默安装apk,用的就是adb命令。

adb install -r newVersion.apk

核心代码

// 执行指定命令
public static String execCommand(String... command) {
    Process process = null;
    InputStream errIs = null;
    InputStream inIs = null;
    String result = "";

    try {
        process = new ProcessBuilder().command(command).start();
        ByteArrayOutputStream baos = new ByteArrayOutputStream();
        int read = -1;
        errIs = process.getErrorStream();
        while ((read = errIs.read()) != -1) {
            baos.write(read);
        }
        inIs = process.getInputStream();
        while ((read = inIs.read()) != -1) {
            baos.write(read);
        }
        result = new String(baos.toByteArray());
        if (inIs != null)
            inIs.close();
        if (errIs != null)
            errIs.close();
        process.destroy();
    } catch (IOException e) {
        Log.e(App.TAG, e.getLocalizedMessage());
        result = e.getMessage();
    }
    return result;
}

安装apk文件

/**
 * 静默安装apk
 *
 * @param filePath apk文件路径
 */
public static void installApk(String filePath) {
    execCommand("pm", "install", "-r", filePath);
}

需要权限

<uses-permission android:name="android.permission.INSTALL_PACKAGES" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>

系统应用

作为系统应用,还需要在AndroidManifest.xml中的 manfest 节点添加android:sharedUserId=”android.uid.system”

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    xmlns:tools="http://schemas.android.com/tools"
    package="com.lxmy.demo"
    android:sharedUserId="android.uid.system">

    ......

</manifest>

然后使用系统签名打包,需要 3个文件,可以在原生源码中获取,如果是定制的rom,可能需要rom方提供。

  • signapk.jar
  • platform.pk8
  • platform.x509.pem

签名命令如下

java -jar signapk.jar platform.x509.pem 未签名.apk 签名完成.apk

其它

隐藏应用图标, 在入口的activity,添加

<data android:scheme="access" />
<data android:host="com.lxmy.demo.hide" />

这样应用看不到图标,同时支持intent隐式启动。

<application
        android:name=".app.App"
        android:allowBackup="true"
        android:icon="@mipmap/ic_launcher"
        android:label="@string/app_name"
        android:roundIcon="@mipmap/ic_launcher_round"
        android:supportsRtl="true"
        android:theme="@style/AppTheme">
        <activity android:name=".MainActivity">
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />

                <data android:scheme="access" />
                <data android:host="com.lxmy.demo.hide" />

                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>

        .... 

</application>

参看
https://blog.csdn.net/gaobobo138968/article/details/45197943
https://blog.csdn.net/ydt_lwj/article/details/9419239

猜你喜欢

转载自blog.csdn.net/lxmy2012/article/details/79799003