Android 14读取其他设备生成的同目录文件时出现EACCES权限拒绝
问题分析与解决方案
核心问题
- 权限配置错误:
MANAGE_DOCUMENTS权限名末尾多了一个点,导致权限未正常生效。 - Android 14存储访问限制:Scoped Storage规则下,APP无法直接通过文件路径访问非自身创建的公共目录文件,必须通过
ContentResolver结合Uri读取。 - 过时配置无效:
requestLegacyExternalStorage仅在Android 10/11(API30/31)生效,Android 14已完全忽略该配置。
修复步骤
1. 修正权限配置
修改Manifest中的MANAGE_DOCUMENTS权限,去掉末尾的多余点:
<uses-permission android:name="android.permission.MANAGE_DOCUMENTS"/>
注:Android 14已不再使用READ_EXTERNAL_STORAGE(maxSdkVersion32),该权限可保留但不会对API34设备生效。
2. 替换文件读取方式
放弃通过本地File路径读取文件的逻辑,直接使用ContentResolver借助Uri读取内容,修改getExpRep函数的核心读取代码:
fun getExpRep(uri: Uri, context: Context): ExportedRep? { val docFile = fromSingleUri(context, uri) val name = docFile?.name if (name.isNotNull()) { try { // 通过ContentResolver直接读取Uri对应的文件内容 context.contentResolver.openInputStream(uri)?.use { inputStream -> val repJSON = inputStream.bufferedReader().readText() return Gson().fromJson(repJSON, ExportedRep::class.java) } } catch (e: Exception) { e.printStackTrace() Toast.makeText(context, "Select Exported Report", Toast.LENGTH_SHORT).show() return null } } return null }
3. 移除无效配置
删除application标签中的android:requestLegacyExternalStorage="true",该配置在Android 14环境下已无作用。
原理说明
- 自身设备创建的文件:APP在Scoped Storage规则下拥有该文件的直接访问权限,因此可通过File路径正常读取。
- 其他设备复制的文件:这类文件不属于APP创建的“私有”文件,Scoped Storage限制APP直接通过路径访问,必须依赖系统提供的Uri权限,借助
ContentResolver完成读取操作。
内容的提问来源于stack exchange,提问作者Siddhant Samarth
相关产品推荐
相关产品推荐

