首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >从URI创建可写DocumentFile

从URI创建可写DocumentFile
EN

Stack Overflow用户
提问于 2019-12-05 06:43:28
回答 1查看 3.1K关注 0票数 2

我正在尝试将File-based文档系统调整为使用DocumentFile的东西,以便允许API >= 29上的外部存储读写访问。

我让用户使用Intent.ACTION_OPEN_DOCUMENT_TREE选择SD卡根目录,并按预期获得一个Uri,然后可以使用以下方法处理:

代码语言:javascript
复制
    getContentResolver().takePersistableUriPermission(resultData.getData(),
                            Intent.FLAG_GRANT_READ_URI_PERMISSION
                            | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);

我可以在选定的根目录下成功浏览外部存储内容。一切都很好。

但是我需要做的是在所选的(子)文件夹中编写一个任意的文件,这就是我遇到问题的地方。

代码语言:javascript
复制
    DocumentFile file = DocumentFile.fromSingleUri(mContext, Uri.parse(toPath));
    Uri uri = file.getUri();
    FileOutputStream output = mContext.getContentResolver().openOutputStream(uri);

除了我接到的openOutputStream()电话:

java.io.FileNotFoundException: Failed to open for writing: java.io.FileNotFoundException: open failed: EISDIR (Is a directory)

这让我有点困惑,但“未找到的文件”部分建议我可能需要首先创建空白输出文件,因此我尝试这样做:

代码语言:javascript
复制
    DocumentFile file = DocumentFile.fromSingleUri(mContext, Uri.parse(toPath));
    Uri uri = file.getUri();
    if (file == null) {
        return false;
    }
    if (file.exists()) {
        file.delete();
    }
    DocumentFile.fromTreeUri(mContext, Uri.parse(getParentPath(toPath))).createFile("", uri.getLastPathSegment());
    FileOutputStream output = mContext.getContentResolver().openOutputStream(uri);

我得到了一个java.io.IOException

代码语言:javascript
复制
    java.lang.IllegalStateException: Failed to touch /mnt/media_rw/0B07-1910/Testing.tmp: java.io.IOException: Read-only file system
    at android.os.Parcel.createException(Parcel.java:2079)
    at android.os.Parcel.readException(Parcel.java:2039)
    at android.database.DatabaseUtils.readExceptionFromParcel(DatabaseUtils.java:188)
    at android.database.DatabaseUtils.readExceptionFromParcel(DatabaseUtils.java:140)
    at android.content.ContentProviderProxy.call(ContentProviderNative.java:658)
    at android.content.ContentResolver.call(ContentResolver.java:2042)
    at android.provider.DocumentsContract.createDocument(DocumentsContract.java:1327)
    at androidx.documentfile.provider.TreeDocumentFile.createFile(TreeDocumentFile.java:53)
    at androidx.documentfile.provider.TreeDocumentFile.createFile(TreeDocumentFile.java:45)

这对我来说毫无意义,因为这棵树应该是可写的。

值得注意的是,我从Intent.ACTION_OPEN_DOCUMENT_TREE中得到的Intent.ACTION_OPEN_DOCUMENT_TREE如下所示:

content://com.android.externalstorage.documents/tree/0B07-1910%3A

有趣的是,当我使用这个Uri创建一个要浏览的DocumentFile对象时,使用documentFile = DocumentFile.fromTreeUri(context, uri),那么documentFile.getURI().toString()看起来如下:

content://com.android.externalstorage.documents/tree/0B07-1910%3A/document/0B07-1910%3A

也就是说,它的末尾附加了一些东西。

然后,我下降到应该是可写文件夹(如“下载”),并尝试创建一个可写文件,如上文所述。“下载”文件夹获取Uri

content://com.android.externalstorage.documents/tree/0B07-1910%3A/document/0B07-1910%3ADownload

我在上面为toPath使用的toPath是:

content://com.android.externalstorage.documents/tree/0B07-1910%3A/document/0B07-1910%3ADownload/Testing.tmp

这将导致前面描述的试图创建它的问题。

实际上,我还没有找到任何关于在限制下编写任意文件的适当信息。

我做错了什么?谢谢。:)

EN

回答 1

Stack Overflow用户

发布于 2019-12-05 14:25:23

代码语言:javascript
复制
Uri uri = uri obtained from ACTION_OPEN_DOCUMENT_TREE

String folderName = "questions.59189631";

DocumentFile documentDir = DocumentFile.fromTreeUri(context, uri);

DocumentFile folder = documentDir.createDirectory(folderName);

return folder.getUri();

对可写文件使用createFile()。

票数 1
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/59189631

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档