从运行Oreo并且没有REQUEST_INSTALL_PACKAGES

时间:2019-02-10 13:41:49

标签: android android-permissions

我正在开发具有自动更新功能的Android应用程序,为此应用程序开发的android设备没有google play,因此我必须在更新的某个位置上载新版本的新APK,并每次以编程方式进行检查如果有新版本,则打开该应用程序;如果有新版本,则我将其下载(apk),然后使用此代码进行安装

Uri apkUri = FileProvider.getUriForFile(this, BuildConfig.APPLICATION_ID + ".provider", file);
Intent intent = new Intent(Intent.ACTION_INSTALL_PACKAGE);
intent.setData(apkUri);
intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
startActivityForResult(intent, 123);

它运行正常,因为运行该应用程序的设备运行的是android7。最近,该设备升级到了Android 8,该功能停止运行。在搜索了许多天后,我发现我必须获得名为{ {1}},如该链接中的文档所述,从Android API 25开始安装新软件包https://developer.android.com/reference/android/Manifest.permission.html#REQUEST_INSTALL_PACKAGES。 我现在有两个问题;

首先:我没有在旧版APK中植入此权限,因此旧版APK的所有用户都必须卸载旧版APK并手动安装新版(新版是具有REQUEST_INSTALL_PACKAGE的用户烫发)

第二:即使他们这样做了,我在那里使用的代码也将用户带到屏幕上,并向他们显示一条可怕的消息,告诉他们“糟糕的是安装新apk的人,他们对此行为负责”。我正在为该邮件添加屏幕截图,即使有需要从Google购买的证书,我也需要删除此邮件,我进行了搜索,但未找到任何内容

enter image description here

任何解决方案,谢谢!

2 个答案:

答案 0 :(得分:2)

  

即使有我需要从Google购买的证书,我也需要删除此消息

对不起,无法删除此消息。注意它只会出现一次。如果用户授予您的应用安装功能的能力,则以后的ACTION_INSTALL_PACKAGE请求不应显示该消息。

  

我没有在旧版apk中植入此权限,因此旧版apk的所有用户都必须卸载旧版apk并手动安装新版apk

他们不需要卸载旧应用。他们确实必须手动安装此更新,但无需删除旧版本。

答案 1 :(得分:1)

向可能需要它的所有软件包添加授予权限,如下所示:

List<ResolveInfo> resInfoList = context.getPackageManager().queryIntentActivities(intent, PackageManager.MATCH_DEFAULT_ONLY);
for (ResolveInfo resolveInfo : resInfoList) {
    String packageName = resolveInfo.activityInfo.packageName;
    context.grantUriPermission(packageName, uri, Intent.FLAG_GRANT_WRITE_URI_PERMISSION | Intent.FLAG_GRANT_READ_URI_PERMISSION);
}

完整(有效)代码为:

File download_file = new File(Environment.getExternalStoragePublicDirectory(Environment.DIRECTORY_DOWNLOADS), "NameApplication.apk");
if (download_file.exists()) {
    if(Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {
        Uri apkUri = FileProvider.getUriForFile(context, context.getApplicationContext().getPackageName() + ".provider", file);
        Intent intent_update = new Intent(Intent.ACTION_VIEW);
        intent_update.setDataAndType(apkUri, "application/vnd.android.package-archive");
        intent_update.setFlags(Intent.FLAG_ACTIVITY_CLEAR_TOP | Intent.FLAG_ACTIVITY_NEW_TASK);
        intent_update.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);
        List<ResolveInfo> resInfoList = context.getPackageManager().queryIntentActivities(intent_update, PackageManager.MATCH_DEFAULT_ONLY);
        for (ResolveInfo resolveInfo : resInfoList) {
            String packageName = resolveInfo.activityInfo.packageName;
            context.grantUriPermission(packageName, apkUri, Intent.FLAG_GRANT_WRITE_URI_PERMISSION | Intent.FLAG_GRANT_READ_URI_PERMISSION);
        }
    } else {
        PrefSingleton prefSingleton = PrefSingleton.getInstance();
        SharedPreferences.Editor editor = prefSingleton.getSharedPrefs().edit();
        editor.putBoolean("update", false);
        editor.apply();
        Uri apkUri = Uri.fromFile(download_file);
        Intent intent_update = new Intent(Intent.ACTION_VIEW);
        intent_update.setDataAndType(apkUri, "application/vnd.android.package-archive");
        intent_update.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
    }
    context.startActivity(intent_update);
} else {
    Toast.makeText(context, "Failed.", Toast.LENGTH_SHORT).show();
}

希望这会有所帮助。