我的应用程序中有一个 Activity ,该 Activity 允许用户从设备中一个接一个地选择多个文件,我使用的是这样的意图:

Intent intent = new Intent();
intent.setType("*/*");
intent.setAction(Intent.ACTION_GET_CONTENT);
startActivityForResult(Intent.createChooser(intent, getString(R.string.select_attachments_activity_chooser_label)), SELECT_PICTURE);

这工作得很好,我正在选择文件的Uri,它们看起来像这样:
content://com.android.providers.media.documents/document/image%3A42555

然后,如果文件是图像,则使用以下命令对其进行解码:
InputStream streamForDecodeBitmap = MyApp.getContext().getContentResolver().openInputStream(uri);
Bitmap bitmap = BitmapFactory.decodeStream(streamForDecodeBitmap, null, options);

当用户单击按钮时,我通过意图将Uris列表传递给另一个 Activity ,并且在此 Activity 中,在AsyncTask中,我将文件编码为base64以通过网络发送:
InputStream is = MyApp.getContext().getContentResolver().openInputStream(uri);
byte[] inputData = getBytes(is);
is.close();
return Base64.encodeToString(inputData, Base64.DEFAULT);

问题是当我打开inputStream时,有时它可以工作,但是在大多数情况下,我会收到此异常:
E/AndroidRuntime(22270): Caused by: java.lang.SecurityException: Permission Denial: opening provider com.android.providers.media.MediaDocumentsProvider from ProcessRecord{42858fe0 22270:co.uk.manifesto.freeagentapp/u0a246} (pid=22270, uid=10246) requires android.permission.MANAGE_DOCUMENTS or android.permission.MANAGE_DOCUMENTS

这些是 list 中的所有权限:
<uses-permission android:name="android.permission.INTERNET" />
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" />
<uses-permission android:name="android.permission.GET_TASKS" />
<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE"/>
<uses-permission android:name="android.permission.MANAGE_DOCUMENTS"/>

我正在使用KITKAT(API 19)的设备中进行测试。

最佳答案

请也检查以下问题:
Android KitKat securityException when trying to read from MediaStore
Permission denial: opening provider

对于KitKat上的相同问题,我使用了它。这是我从Stack Overflow链接之一中找到的一个选项/解决方法,您将能够从Downloads/Recent中选择文件。

public static final int KITKAT_VALUE = 1002;

Intent intent;

if (Build.VERSION.SDK_INT < 19) {
    intent = new Intent();
    intent.setAction(Intent.ACTION_GET_CONTENT);
    intent.setType("*/*");
    startActivityForResult(intent, KITKAT_VALUE);
} else {
    intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
    intent.addCategory(Intent.CATEGORY_OPENABLE);
    intent.setType("*/*");
    startActivityForResult(intent, KITKAT_VALUE);
}

@Override
public void onActivityResult(int requestCode, int resultCode, Intent data) {
    if (requestCode == KITKAT_VALUE ) {
        if (resultCode == Activity.RESULT_OK) {
            // do something here
        }
    }
}

引用:
Android Gallery on KitKat returns different Uri for Intent.ACTION_GET_CONTENT
http://developer.android.com/guide/topics/providers/document-provider.html#client

10-08 18:18