Android 7.0之后安装APK,拍照 出现FileUriExposedException,多个provider配置

来源:互联网 发布:人民网 网络彩票牌照 编辑:程序博客网 时间:2024/06/04 20:13

做项目在主页检查更新的时候,检查到apk需要更新,于是我美滋滋的得到了下载的apk,然后调用一下去安装apk方法,以为理所当然的没啥问题,可是当我下载完了的时候,在调用安装的代码时,抛出了一个异常FileUriExposedException,MMP 这是个什么鬼,欺负我英语不好吗,于是日常百度,搜嘎,原来由于

在android7.0,修改了对私有存储的限制,而我的编译版本为25,导致在获取资源的时候,不能通过Uri.fromFile(..)来获取uri了,但是在写入数据的时候是可以通过Uri.fromFile(..)来获取uri的,android 官网给出的解决办法是通过FileProvider来解决这一问题,我们需要在AndroidManifest.xml 配制provider节点 

原来如此那就好整了,开干开干

第一步: 在AndroidManifest.xml文件添加  provider节点配置
<provider    android:name="android.support.v4.content.FileProvider"    android:authorities="${applicationId}.fileprovider"    android:grantUriPermissions="true"    android:exported="false">    <meta-data        android:name="android.support.FILE_PROVIDER_PATHS"        android:resource="@xml/file_path" /></provider>
注意了,这个applacationId 必须要在grade文件里面配置哦 如果你不配置的话你可以直接写上你的包名

第二步: 在res文件夹下面新建一个xml文件夹,然后在xml文件夹中新建一个xml 这个xml的名字
必须与你在第一步的配置文件里面名字一致,如图



第三步 xml 里面的内容
<?xml version="1.0" encoding="utf-8"?><paths>    <external-path path="Android/data/你的包名/" name="files_root" />    <external-path path="." name="external_storage_root" /></paths>


注意了 这里请必须要填上你自己的包名,
ok了,文件都配置好了,就差最后的代码了,

第四步
/** 安装一个apk文件 */public static void install(Context  context, File uriFile) {    Intent intent = new Intent(Intent.ACTION_VIEW);    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.N) {        intent.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION);        Uri contentUri = FileProvider.getUriForFile(context, BuildConfig.APPLICATION_ID+".fileprovider", uriFile);        intent.setDataAndType(contentUri, "application/vnd.android.package-archive");    } else {        intent.setDataAndType(Uri.fromFile(uriFile), "application/vnd.android.package-archive");        intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);    }    if (App.getIntence().getPackageManager().queryIntentActivities(intent, 0).size() > 0) {        App.getIntence().startActivity(intent);    }}
这里要注意的是这句代码,这里BuildConfig 是导入的我当前项目的包名,如果你不想这么做的话,你可以直接写你自己的包名列如: 包名com.test 来替换

题外:
我们项目中可能会用到其他一些第三方sdk有用到拍照功能或者关于某些获取资源操作的话,他为了适配android7.0也添加了这个节点,此时有些人可能就不知道如何下手了,其实很简单我们只要重写一个类 继承自FileProvider,然后就按上述方法在添加一个节点就可以了;例如:
public class MyFileProvider extends FileProvider {    }

然后
<provider    android:name=".util.MyFileProvider"    android:authorities="${applicationId}.provider"    android:grantUriPermissions="true"    android:exported="false">    <meta-data        android:name="android.support.FILE_PROVIDER_PATHS"        android:resource="@xml/file_paths" /></provider>

这个file_paths文件 是第三方sdk的 而不是我新建的那个
大功告成~~~
阅读全文
1 0
原创粉丝点击