Flutter如何通过path_provider获取本地Download文件夹实现文件上传
问题解决方案
问题根因
你当前遇到的问题是安卓分区存储机制的限制导致的:
- 安卓10(API 29)及以上版本默认开启分区存储,普通应用无权限直接读取公共目录的文件列表,所以硬编码Download目录路径读取返回空数组属于正常现象
getExternalStorageDirectories()方法的设计初衷就是返回应用专属的外部存储路径,本身就不会返回公共目录的路径,无法满足你的需求- 你添加的
READ_EXTERNAL_STORAGE权限仅对安卓9(API 28)及以下版本生效,更高版本的系统不会授予该权限的访问能力
推荐最优方案(适配全安卓版本,符合谷歌应用市场审核规则)
不需要自行实现文件列表读取、界面渲染,直接调用系统原生文件选择器即可实现和示例图完全一致的类WhatsApp文件选择效果,不需要处理复杂的版本适配和权限申请逻辑。我们可以使用成熟的file_picker插件实现该功能:
1. 引入依赖
在pubspec.yaml中添加依赖:
dependencies: file_picker: ^6.1.1
2. 安卓端权限配置
在AndroidManifest.xml中添加对应权限:
- 若你的应用最小兼容版本
minSdkVersion <= 32,添加:
<uses-permission android:name="android.permission.READ_EXTERNAL_STORAGE" />
- 若
minSdkVersion >= 33,添加对应媒体权限即可:
<uses-permission android:name="android.permission.READ_MEDIA_IMAGES" /> <uses-permission android:name="android.permission.READ_MEDIA_VIDEO" />
如果仅需要选择pdf、txt等非媒体文件,不需要额外添加权限,插件会自动通过系统存储访问框架调用文件选择能力。
3. 功能调用代码示例
import 'package:file_picker/file_picker.dart'; import 'dart:io'; // 选择文件方法 _pickFiles() async { FilePickerResult? result = await FilePicker.platform.pickFiles( // 支持多选,和WhatsApp的多选逻辑一致 allowMultiple: true, // 过滤你需要支持的文件类型:图片、pdf、txt type: FileType.custom, allowedExtensions: ['jpg', 'png', 'jpeg', 'pdf', 'txt'], ); if (result != null) { // 拿到所有选中的文件对象,直接使用即可 List<File> selectedFiles = result.paths.map((path) => File(path!)).toList(); // 后续执行上传逻辑 } else { // 用户主动取消了文件选择 } }
不推荐方案(如需自行遍历公共目录)
如果确实需要自行遍历所有公共存储的文件,需要申请特殊权限MANAGE_EXTERNAL_STORAGE,但该权限仅允许文件管理、杀毒类等需要访问全量存储的应用申请,普通聊天类应用申请该权限大概率会被谷歌Play商店驳回,因此不建议使用。
内容的提问来源于stack exchange,提问作者user16754196
相关产品推荐
相关产品推荐

