【发布时间】:2019-05-31 10:31:44
【问题描述】:
我的 Android 应用想要在 Google Drive 中创建一个文件夹并从设备上的 Drive 应用获取 uri。
它发送一个intent,你可以看下面的代码:
private void createFolder(String folderName) {
Intent intent = new Intent(Intent.ACTION_CREATE_DOCUMENT);
intent.addCategory(Intent.CATEGORY_OPENABLE);
// Create a file with the requested MIME type.
intent.setType("vnd.android.document/directory");
intent.putExtra(Intent.EXTRA_TITLE, folderName);
startActivityForResult(intent, WRITE_REQUEST_CODE);
}
然后获取返回的数据,可以看下面的代码:
@Override
protected void onActivityResult(int requestCode, int resultCode, Intent resultData)
{
if (requestCode == WRITE_REQUEST_CODE && resultCode == Activity.RESULT_OK) {
Uri uri = null;
if (resultData != null) {
uri = resultData.getData();
Log.i("result", "Uri: " + uri.toString());
DocumentFile pickedDir = DocumentFile.fromTreeUri(this, uri); //this line gives the error
}
}
}
我使用了一种在 Internet 上找到的 mimetype,它似乎是一种标准类型。使用“application/vnd.google-apps.folder”时也会出现同样的错误。 目标是拥有一个文档树,但在 logcat 中我收到以下错误:
java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=43, result=-1, data=Intent { dat=content://com.google.android.apps.docs.storage/document/acc=1;doc=encoded=LongStringWithRandomCharactersHere/j flg=0x43 }} to activity {com.example.myapplication/com.example.myapplication.MainActivity}: java.lang.IllegalArgumentException: Invalid URI: content://com.google.android.apps.docs.storage/document/acc%3D1%3Bdoc%3Dencoded%3DSameLongStringWithRandomCharactersHere%2Fj
及以下
Caused by: java.lang.IllegalArgumentException: Invalid URI: content://com.google.android.apps.docs.storage/document/acc%3D1%3Bdoc%3Dencoded%3DAnotherLongStringWithDifferentRandomDataHere
这是完整的堆栈跟踪:
2019-05-31 15:06:50.167 31184-31184/com.example.myapplication E/AndroidRuntime: FATAL EXCEPTION: main
Process: com.example.myapplication, PID: 31184
java.lang.RuntimeException: Failure delivering result ResultInfo{who=null, request=43, result=-1, data=Intent { dat=content://com.google.android.apps.docs.storage/document/acc=1;doc=encoded=randomcharacters flg=0x43 }} to activity {com.example.myapplication/com.example.myapplication.MainActivity}: java.lang.IllegalArgumentException: Invalid URI: content://com.google.android.apps.docs.storage/document/acc%3D1%3Bdoc%3Dencoded%3Drandomcharacters
at android.app.ActivityThread.deliverResults(ActivityThread.java:4365)
at android.app.ActivityThread.handleSendResult(ActivityThread.java:4409)
at android.app.ActivityThread.-wrap19(Unknown Source:0)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1670)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6687)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:810)
Caused by: java.lang.IllegalArgumentException: Invalid URI: content://com.google.android.apps.docs.storage/document/acc%3D1%3Bdoc%3Dencoded%3Drandomcharacters
at android.provider.DocumentsContract.getTreeDocumentId(DocumentsContract.java:1023)
at android.support.v4.provider.DocumentFile.fromTreeUri(DocumentFile.java:138)
at com.example.myapplication.MainActivity.onActivityResult(MainActivity.java:254)
at android.app.Activity.dispatchActivityResult(Activity.java:7295)
at android.app.ActivityThread.deliverResults(ActivityThread.java:4361)
at android.app.ActivityThread.handleSendResult(ActivityThread.java:4409)
at android.app.ActivityThread.-wrap19(Unknown Source:0)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1670)
at android.os.Handler.dispatchMessage(Handler.java:106)
at android.os.Looper.loop(Looper.java:164)
at android.app.ActivityThread.main(ActivityThread.java:6687)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.RuntimeInit$MethodAndArgsCaller.run(RuntimeInit.java:438)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:810)
uri 没有错,因为我可以进一步提取在云端硬盘上成功创建的文件夹名称(并且大小=0)。 相反有什么问题?看来我的应用程序无法将其作为文档树处理。
【问题讨论】:
-
“怎么了?” --
ACTION_CREATE_DOCUMENT用于创建文档,而不是树。没有要求任何DocumentsProvider以您期望的方式尊重该 MIME 类型。 “看来我的应用程序无法将其作为文档树处理”——存储访问框架大概将其视为文档,因为这是您通过ACTION_CREATE_DOCUMENT要求创建的。 -
@CommonsWare "document" 在 SAF 行话中也是一个文件夹,实际上,一个文档可以在其级别下有其他文档。至少云端硬盘应用对此感到满意或容忍它,因为我看到文件夹已创建。
-
这并不意味着存储访问框架中间件会按照您认为的方式工作。
-
@CommonsWare 好的,但是要请求什么操作(对于文字游戏很抱歉)以使中间件满意?
-
@CommonsWare 如果我使用 ACTION_OPEN_DOCUMENT_TREE Android 说没有应用程序能够处理意图(驱动器无法打开),所以我认为它没有实现(我在设备上有其他云应用程序,即使使用 createChooser 选项,它们也不会出现)
标签: java android uri directory-structure storage-access-framework