android - Android - 使用 PackageInstaller 和 PackageInstaller.Session 静默安装 APK
问题描述
查看 Android 的源代码 (AOSP),installPackage
标记为已弃用并检查 Android 的 PackageManager 应用程序,它使用PackageInstaller
该类创建一个PackageInstaller.Session
实例来执行 APK 的安装。
我正在尝试在我的应用程序中做同样的事情。我使用系统密钥签名,并且确实INSTALL_PACKAGES
在清单中包含了权限。
这是我的代码:
val packageName = "com.spotify.music"
val inputStream = File(filesDir, "spotify.apk").inputStream()
// ...
val packageInstaller = context.packageManager.packageInstaller
val params = PackageInstaller.SessionParams(PackageInstaller.SessionParams.MODE_FULL_INSTALL)
params.setAppPackageName(packageName)
val sessionId = packageInstaller.createSession(params)
val session = packageInstaller.openSession(sessionId)
val out = session.openWrite("COSU", 0, -1)
inputStream.copyTo(out)
session.fsync(out)
inputStream.close()
out.close()
session.commit(null)
但是,我收到以下奇怪的空指针异常:
Error while installing: java.lang.NullPointerException: Attempt to invoke virtual method 'void android.app.AppOpsManager.checkPackage(int, java.lang.String)' on a null object reference
有人知道这里出了什么问题吗?
解决方案
你不能null
传给session.commit()
. 请参阅Android 开发人员的文档。您需要的是一个 IntentSender,它是从 PendingIntent 中获得的,而 PendingIntent 又应包含您的应用程序可以接收的意图(可以在 Activity、Service 或 BroadcastReceiver 中)。
提交会话时,结果将作为附加内容包含在接收到的意图中。
推荐阅读
- sql-server - 在具有动态 SQL 的 SSRS 中使用多值参数
- github - 使用 Intellij Idea 推送到 Github 时使用“DontNeedGithubAccount”而不是用户名
- c# - 从列表中删除它们后,如何删除数据库中的孤立嵌套实体?
- javascript - 如何使用 Vue 无限地为 CSS 设置动画
- extjs - 如何处理 Extjs 存储异常?
- android - 一个 Android 库模块可以作为一个完整的应用程序吗?
- javascript - 为什么在监视表达式中更新滑块选项时,AngularJS Slider (rzslider) 不能正确更新?
- python - If-Elif Python 的条件无法正常工作
- php - 从多个表中选择过滤器
- ios - 如何从 swift 4 应用程序打开 /var/mobile/Containers/...?