求Android 7.0以上手机自动升级安装失败补救方案,这里发生的问题与百度搜的不太一样

问题如下,我们此次软件升级后发现,软件下载后无法正确安装,报错信息如下:

Caused by: android.os.FileUriExposedException: 
file:///storage/emulated/0/Download/myApp.apk exposed beyond app through Intent.getData()

 

百度搜了一下,是因为Android7.0执行了“StrictMode API 政策禁”的原因,导致未升级之前的软件无法访问本地下载好的要升级的apk,现在问题是,我们原来的软件没有做这方面的支持,如何能够平滑的过度到新软件上来,因为老软件用户已经在使用,无法做百度上教的增加fileprovider和临时授权的动作,因为这些都是要在老软件上面做更改才能实现,而老软件已经被下载下去使用了无法更改,目前只能暂停更新,寻找好的解决办法。求有经验的大佬能指条明路。如果有完美的解决方案提供者,会有酬金另谢。

没玩过,来学习看看

转载自:https://blog.csdn.net/qq_41466437/article/details/102827692

原因:
android 23 以后传递软件包网域外的 file://URI 可能给接收器留下无法访问的路径。 因此,尝试传递 file://URI 会触发 FileUriExposedException。若要在应用间共享文件,您应发送一项 content://URI,并授予 URI 临时访问权限

解决办法1、

在需要的activity的onCreate方法中添加如下代码:

//API24以上系统分享支持file:///开头
StrictMode.VmPolicy.Builder builder = newStrictMode.VmPolicy.Builder();
StrictMode.setVmPolicy(builder.build());
builder.detectFileUriExposure();

该方法关闭了StrictMode严格模式中虚拟机策略检测中关于文件uri暴露的检测:detectFileUriExposure()。
如果要使用这种方法,推荐使用更加暴力的
builder.detectAll()
关闭所有检测

解决办法2、
使用 FileProvider ,这也是官方推荐使用的方式

1、在AndroidManifest.xml文件中添加:

<application>    
...
<provider        
android:authorities="你应用的包名.fileprovider"        
android:name="android.support.v4.content.FileProvider"        
android:grantUriPermissions="true"        
android:exported="false">        
<meta-data            
android:name="android.support.FILE_PROVIDER_PATHS"            
android:resource="@xml/filepaths"/>    
</provider>    
...
</application>

其中:
authorities:app的包名.fileProvider
grantUriPermissions:必须是true,表示授予 URI 临时访问权限
exported:必须是false
resource:中的@xml/file_paths是我们接下来要添加的文件

2、在res目录下新建一个xml文件夹,并且新建一个文件名为 filepaths 的xml文件,内容如下:

<?xml version="1.0" encoding="utf-8"?>
<paths>    
<external-path path="CHINARES_UT/" name="files_path" />
</paths>

其中:
paths标签中:
files-path代表的根目录: Context.getFilesDir().getPath()
external-path代表的根目录: Environment.getExternalStorageDirectory().getPath()
cache-path代表的根目录: getCacheDir().getPath()

path 代表需要共享的目录
name 只是一个标识,随便取

例:如上配置共享了使用 Environment.getExternalStorageDirectory().getPath() 方式获取的根目录下 CHINARES_UT 文件夹的内容

3、使用:

只需要在构建资源标识符Uri时,判断当前SDK是否大于等于24,然后采用不同方式构建即可,代码如下:

Uri uri;
File file = new File("文件路径");
int currentapiVersion = android.os.Build.VERSION.SDK_INT;
if (currentapiVersion >= 24) {    
uri = FileProvider.getUriForFile(this.getApplicationContext(), "应用包名.fileprovider", file);
} else {    
uri = Uri.fromFile(file);
}

转载自:https://blog.csdn.net/qq_41466437/article/details/102827692