我的编程空间,编程开发者的网络收藏夹
学习永远不晚

Android P静默安装/卸载App

短信预约 -IT技能 免费直播动态提醒
省份

北京

  • 北京
  • 上海
  • 天津
  • 重庆
  • 河北
  • 山东
  • 辽宁
  • 黑龙江
  • 吉林
  • 甘肃
  • 青海
  • 河南
  • 江苏
  • 湖北
  • 湖南
  • 江西
  • 浙江
  • 广东
  • 云南
  • 福建
  • 海南
  • 山西
  • 四川
  • 陕西
  • 贵州
  • 安徽
  • 广西
  • 内蒙
  • 西藏
  • 新疆
  • 宁夏
  • 兵团
手机号立即预约

请填写图片验证码后获取短信验证码

看不清楚,换张图片

免费获取短信验证码

Android P静默安装/卸载App

           Android P静默安装/卸载App
前言

   公司最近上马了Android 9和10的平台,我们也得哼哧哼哧的进行相关的开发。我只能说谷歌的工程师为了KPI考核对Android修改的老开心了,可苦了我们啊。这不今天在进行Android的静默安装的API封装,尼玛原来的相关接口都没有了。那么今天要说的就是在Android P上面怎么实施静默安装/卸载接口的封装。



一.开干

静默安装时比较高的权限,一般应用是不能的,所以必须具备system权限,这个是前提。好了不多说啥了,直接上代码。


1.1 实例代码

package com.pax.android9_api;
// Need the following import to get access to the app resources, since this
// class is in a sub-package.
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import android.app.Activity;
import android.app.PendingIntent;
import android.content.Context;
import android.content.Intent;
import android.content.IntentSender;
import android.content.pm.PackageInstaller;
import android.os.Bundle;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.Toast;

public class InstallApkSessionApi extends Activity {
    private static final String PACKAGE_INSTALLED_ACTION =
            "com.pax.install";
    private static final String PACKAGE_UNINSTALLED_ACTION =
            "com.pax.uninstall";
    private static final String TAG = "install";
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.install_apk_session_api);
        // Watch for button clicks.
        Button button = (Button) findViewById(R.id.install);
        button.setOnClickListener(new OnClickListener() {
            public void onClick(View v) {
                PackageInstaller.Session session = null;
                try {
                    //获取PackageInstaller对象
                    PackageInstaller packageInstaller = getPackageManager().getPackageInstaller();
                    PackageInstaller.SessionParams params = new PackageInstaller.SessionParams(
                            PackageInstaller.SessionParams.MODE_FULL_INSTALL);
                    //创建一个Session
                    int sessionId = packageInstaller.createSession(params);
                    //建立和PackageManager的socket通道,Android中的通信不仅仅有Binder还有很多其它的
                    session = packageInstaller.openSession(sessionId);
                    //将App的内容通过session传输
                    addApkToInstallSession("HelloActivity.apk", session);
                    // Create an install status receiver.
                    Context context = InstallApkSessionApi.this;
                    Intent intent = new Intent(context, InstallApkSessionApi.class);
                    intent.setAction(PACKAGE_INSTALLED_ACTION);
                    PendingIntent pendingIntent = PendingIntent.getActivity(context, 0, intent, 0);
                    IntentSender statusReceiver = pendingIntent.getIntentSender();
                    // Commit the session (this will start the installation workflow).
                    //开启安装
                    session.commit(statusReceiver);
                } catch (IOException e) {
                    throw new RuntimeException("Couldn't install package", e);
                } catch (RuntimeException e) {
                    if (session != null) {
                        session.abandon();
                    }
                    throw e;
                }
            }
        });
        Button uninstall = (Button)findViewById(R.id.uninstall);
        uninstall.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View arg0) {
                // TODO Auto-generated method stub
                uninstall("com.example.android.helloactivity");
            }
        });
    }
    private void addApkToInstallSession(String assetName, PackageInstaller.Session session)
            throws IOException {
        // It's recommended to pass the file size to openWrite(). Otherwise installation may fail
        // if the disk is almost full.
        try (OutputStream packageInSession = session.openWrite("package", 0, -1);
             InputStream is = getAssets().open(assetName)) {
            byte[] buffer = new byte[16384];
            int n;
            while ((n = is.read(buffer)) >= 0) {
                packageInSession.write(buffer, 0, n);
            }
        }
    }
    // Note: this Activity must run in singleTop launchMode for it to be able to receive the intent
    // in onNewIntent().
    //此处一定要运行单例模式或者singleTop模式,否则会一直创建该Activity
    @Override
    protected void onNewIntent(Intent intent) {
        Bundle extras = intent.getExtras();
        Log.e(TAG, intent.toString());
        if (PACKAGE_INSTALLED_ACTION.equals(intent.getAction())) {
            Log.e(TAG, intent.getAction());
            int status = extras.getInt(PackageInstaller.EXTRA_STATUS);
            String message = extras.getString(PackageInstaller.EXTRA_STATUS_MESSAGE);
            switch (status) {
                case PackageInstaller.STATUS_PENDING_USER_ACTION:
                    // This test app isn't privileged, so the user has to confirm the install.
                    Intent confirmIntent = (Intent) extras.get(Intent.EXTRA_INTENT);
                    startActivity(confirmIntent);
                    break;
                case PackageInstaller.STATUS_SUCCESS:
                    Toast.makeText(this, "Install succeeded!", Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Install succeeded!");
                    break;
                case PackageInstaller.STATUS_FAILURE:
                case PackageInstaller.STATUS_FAILURE_ABORTED:
                case PackageInstaller.STATUS_FAILURE_BLOCKED:
                case PackageInstaller.STATUS_FAILURE_CONFLICT:
                case PackageInstaller.STATUS_FAILURE_INCOMPATIBLE:
                case PackageInstaller.STATUS_FAILURE_INVALID:
                case PackageInstaller.STATUS_FAILURE_STORAGE:
                    Toast.makeText(this, "Install failed! " + status + ", " + message,
                            Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Install failed! " + status + ", " + message);
                    break;
                default:
                    Toast.makeText(this, "Unrecognized status received from installer: " + status,
                            Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Unrecognized status received from installer: " + status);
            }
        }
        else if(PACKAGE_UNINSTALLED_ACTION.equals(intent.getAction())){
            Log.e(TAG, intent.getAction());
            int status = extras.getInt(PackageInstaller.EXTRA_STATUS);
            String message = extras.getString(PackageInstaller.EXTRA_STATUS_MESSAGE);
            switch (status) {
                case PackageInstaller.STATUS_PENDING_USER_ACTION:
                    // This test app isn't privileged, so the user has to confirm the install.
                    Intent confirmIntent = (Intent) extras.get(Intent.EXTRA_INTENT);
                    startActivity(confirmIntent);
                    break;
                case PackageInstaller.STATUS_SUCCESS:
                    Toast.makeText(this, "Uninstall succeeded!", Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Uninstall succeeded!");
                    break;
                case PackageInstaller.STATUS_FAILURE:
                case PackageInstaller.STATUS_FAILURE_ABORTED:
                case PackageInstaller.STATUS_FAILURE_BLOCKED:
                case PackageInstaller.STATUS_FAILURE_CONFLICT:
                case PackageInstaller.STATUS_FAILURE_INCOMPATIBLE:
                case PackageInstaller.STATUS_FAILURE_INVALID:
                case PackageInstaller.STATUS_FAILURE_STORAGE:
                    Toast.makeText(this, "Install failed! " + status + ", " + message,
                            Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Uninstall failed! " + status + ", " + message);
                    break;
                default:
                    Toast.makeText(this, "Unrecognized status received from installer: " + status,
                            Toast.LENGTH_SHORT).show();
                    Log.e(TAG,"Unrecognized status received from installer: " + status);
            }
        }
    }
    
    public void uninstall(String packageName) {
        Intent broadcastIntent = new Intent(this, InstallApkSessionApi.class);
        broadcastIntent.setAction(PACKAGE_UNINSTALLED_ACTION);
        PendingIntent pendingIntent = PendingIntent.getActivity(this, 0, broadcastIntent, PendingIntent.FLAG_UPDATE_CURRENT);
        PackageInstaller packageInstaller = getPackageManager().getPackageInstaller();
        packageInstaller.uninstall(packageName, pendingIntent.getIntentSender());
    }
}

1.2 代码分析

好了实例代码,已经编写OK,让我们简单分析一下,及其步骤:
安装流程

通过PackageManagerService获取getPackageInstaller对象 通过packageInstaller调用openSession创建PackageInstaller.Session 将要静默安装的app写入Session中 然后调用Session的commit开始安装

卸载流程:比较简单就不细述了。

这里需要注意的是这个测试Activiyt的Mode必须是此处一定要运行单例模式或者singleTop模式,否则会一直创建该Activity。


1.3 运行实例演示

运行实例,静默安装和卸载成功。

msm8953_64:/ # logcat  -s install
--------- beginning of main
--------- beginning of system
01-15 02:10:45.258  7087  7087 E install : Intent { act=com.pax.install flg=0x10000000 cmp=com.pax.android9_api/.InstallApkSessionApi (has extras) }
01-15 02:10:45.259  7087  7087 E install : com.pax.install
01-15 02:10:45.304  7087  7087 E install : Install succeeded!
01-15 02:10:48.340  7087  7087 E install : Intent { act=com.pax.uninstall flg=0x10000000 cmp=com.pax.android9_api/.InstallApkSessionApi (has extras) }
01-15 02:10:48.340  7087  7087 E install : com.pax.uninstall
01-15 02:10:48.372  7087  7087 E install : Uninstall succeeded!

在这里插入图片描述



总结

文章至此,关于Android P静默安装和卸载的封装就结束了,如果想更详细的了解那么就只能跟读Android FrameWork的源码了。我也在跟进中,各位如果有兴趣也可以一起聊聊。


作者:进阶的凯子


免责声明:

① 本站未注明“稿件来源”的信息均来自网络整理。其文字、图片和音视频稿件的所属权归原作者所有。本站收集整理出于非商业性的教育和科研之目的,并不意味着本站赞同其观点或证实其内容的真实性。仅作为临时的测试数据,供内部测试之用。本站并未授权任何人以任何方式主动获取本站任何信息。

② 本站未注明“稿件来源”的临时测试数据将在测试完成后最终做删除处理。有问题或投稿请发送至: 邮箱/279061341@qq.com QQ/279061341

Android P静默安装/卸载App

下载Word文档到电脑,方便收藏和打印~

下载Word文档

猜你喜欢

Android P静默安装/卸载App

Android P静默安装/卸载App前言公司最近上马了Android 9和10的平台,我们也得哼哧哼哧的进行相关的开发。我只能说谷歌的工程师为了KPI考核对Android修改的老开心了,可苦了我们啊。这不今天在进行Android的静默安装
2022-06-06

静默安装卸载 ORACLE

静默安装:使用 dbca.rsp 模板# 修改第78 行的全局数据库的名字=SID+主机域名DBNAME="orcl.sczq"# 修改第149行的ORACLE SIDSID="orcl"# 修改第415行的数据库编码CHARACTERSET="AL32UTF
静默安装卸载 ORACLE
2017-03-01

Android中怎么实现静默安装和卸载

Android中怎么实现静默安装和卸载,针对这个问题,这篇文章详细介绍了相对应的分析和解答,希望可以帮助更多想解决这个问题的小伙伴找到更简单易行的方法。一. 条件系统签名需要放到 /system/app里作为系统app二. 适用环境机顶盒开
2023-05-30

android实现静默安装与卸载的方法

本文实例讲述了android实现静默安装与卸载的方法。分享给大家供大家参考。具体如下: 方法1:【使用调用接口方法,由于安装卸载应用程序的部分API是隐藏的,所以必须下载Android系统源码,在源码下开发并编译之后使用MM命令编译生成AP
2022-06-06

Android如何在一个app中安装并卸载另一个app

这篇文章主要介绍“Android如何在一个app中安装并卸载另一个app”,在日常操作中,相信很多人在Android如何在一个app中安装并卸载另一个app问题上存在疑惑,小编查阅了各式资料,整理出简单好用的操作方法,希望对大家解答”And
2023-06-13

Android 静默方式实现批量安装卸载应用程序的深入分析

前段时间做了一个批量安装卸载应用程序的小应用,由于安装卸载应用程序的部分API是隐藏的,所以必须在ubuntu下下载Android系统源码,并编译之后使用MM命令编译生成APK文件,其实也难。思路是这样的,在XX/packages/apps
2022-06-06

Android 静默安装实现方法

Android静默安装的方法,静默安装就是绕过安装程序时的提示窗口,直接在后台安装。 注意:静默安装的前提是设备有ROOT权限。 代码如下: public bool
2022-06-06

如何实现静默安装Android应用

这期内容当中小编将会给大家带来有关如何实现静默安装Android应用,文章内容丰富且以专业的角度为大家分析和叙述,阅读完这篇文章希望大家可以有所收获。1、root权限静默安装实现实现实际使用的是su pm install -r filePa
2023-05-31

android监听安装和卸载示例

BroadcastReceiver 是系统全局广播监听类, 其主要方法是onReceive(),自定义的广播类继承于它并实现自己的onReceive()处理逻辑BroadcastReceiver 使用前,需要进行注册监听(xml和代码两种方
2022-06-06

Android无需root实现apk的静默安装

Android的静默安装似乎是一个很有趣很诱人的东西,但是,用普通做法,如果手机没有root权限的话,似乎很难实现静默安装,因为Android并不提供显示的Intent调用,一般是通过以下方式安装apk:Intent intent = ne
2022-06-06

Android实现静默安装的两种方法

前言 一般情况下,Android系统安装apk会出现一个安装界面,用户可以点击确定或者取消来进行apk的安装。 但在实际的项目需求中,有一种需求,就是希望apk在后台安装(不出现安装界面的提示),这种安装方式称为静默安装。下面这篇文章就给大
2022-06-06

android静默安装升级的方法是什么

在Android中,静默安装和升级应用程序的方法是使用命令行工具adb(Android Debug Bridge)。以下是在设备上执行静默安装和升级的步骤:1. 确保你的设备已连接到计算机上,并且已启用USB调试模式。2. 打开命令提示符或
2023-10-18

vbs脚本怎么实现下载jre包并静默安装

这篇文章主要讲解了“vbs脚本怎么实现下载jre包并静默安装”,文中的讲解内容简单清晰,易于学习与理解,下面请大家跟着小编的思路慢慢深入,一起来研究和学习“vbs脚本怎么实现下载jre包并静默安装”吧!安装完成后可以回调,替换echo 12
2023-06-08

Android编程之软件的安装和卸载方法

本文实例讲述了Android编程之软件的安装和卸载方法。分享给大家供大家参考,具体如下: 安装:从sdcardString fileName = Environment.getExternalStorageDirectory() + "/m
2022-06-06

Android开发中怎么实现一个静默安装功能

这篇文章给大家介绍Android开发中怎么实现一个静默安装功能,内容非常详细,感兴趣的小伙伴们可以参考借鉴,希望对大家能有所帮助。静默安装主要分为以下几种方式:一、在ROOT过的机器上,在App中使用pm install指令安装APK:
2023-05-31

Android静默安装实现方案 仿360手机助手秒装和智能安装功能

之前有很多朋友都问过我,在Android系统中怎样才能实现静默安装呢?所谓的静默安装,就是不用弹出系统的安装界面,在不影响用户任何操作的情况下不知不觉地将程序装好。虽说这种方式看上去不打搅用户,但是却存在着一个问题,因为Android系统会
2022-06-06

编程热搜

  • Android:VolumeShaper
    VolumeShaper(支持版本改一下,minsdkversion:26,android8.0(api26)进一步学习对声音的编辑,可以让音频的声音有变化的播放 VolumeShaper.Configuration的三个参数 durati
    Android:VolumeShaper
  • Android崩溃异常捕获方法
    开发中最让人头疼的是应用突然爆炸,然后跳回到桌面。而且我们常常不知道这种状况会何时出现,在应用调试阶段还好,还可以通过调试工具的日志查看错误出现在哪里。但平时使用的时候给你闹崩溃,那你就欲哭无泪了。 那么今天主要讲一下如何去捕捉系统出现的U
    Android崩溃异常捕获方法
  • android开发教程之获取power_profile.xml文件的方法(android运行时能耗值)
    系统的设置–>电池–>使用情况中,统计的能耗的使用情况也是以power_profile.xml的value作为基础参数的1、我的手机中power_profile.xml的内容: HTC t328w代码如下:
    android开发教程之获取power_profile.xml文件的方法(android运行时能耗值)
  • Android SQLite数据库基本操作方法
    程序的最主要的功能在于对数据进行操作,通过对数据进行操作来实现某个功能。而数据库就是很重要的一个方面的,Android中内置了小巧轻便,功能却很强的一个数据库–SQLite数据库。那么就来看一下在Android程序中怎么去操作SQLite数
    Android SQLite数据库基本操作方法
  • ubuntu21.04怎么创建桌面快捷图标?ubuntu软件放到桌面的技巧
    工作的时候为了方便直接打开编辑文件,一些常用的软件或者文件我们会放在桌面,但是在ubuntu20.04下直接直接拖拽文件到桌面根本没有效果,在进入桌面后发现软件列表中的软件只能收藏到面板,无法复制到桌面使用,不知道为什么会这样,似乎并不是很
    ubuntu21.04怎么创建桌面快捷图标?ubuntu软件放到桌面的技巧
  • android获取当前手机号示例程序
    代码如下: public String getLocalNumber() { TelephonyManager tManager =
    android获取当前手机号示例程序
  • Android音视频开发(三)TextureView
    简介 TextureView与SurfaceView类似,可用于显示视频或OpenGL场景。 与SurfaceView的区别 SurfaceView不能使用变换和缩放等操作,不能叠加(Overlay)两个SurfaceView。 Textu
    Android音视频开发(三)TextureView
  • android获取屏幕高度和宽度的实现方法
    本文实例讲述了android获取屏幕高度和宽度的实现方法。分享给大家供大家参考。具体分析如下: 我们需要获取Android手机或Pad的屏幕的物理尺寸,以便于界面的设计或是其他功能的实现。下面就介绍讲一讲如何获取屏幕的物理尺寸 下面的代码即
    android获取屏幕高度和宽度的实现方法
  • Android自定义popupwindow实例代码
    先来看看效果图:一、布局
  • Android第一次实验
    一、实验原理 1.1实验目标 编程实现用户名与密码的存储与调用。 1.2实验要求 设计用户登录界面、登录成功界面、用户注册界面,用户注册时,将其用户名、密码保存到SharedPreference中,登录时输入用户名、密码,读取SharedP
    Android第一次实验

目录