Java.lang.SecurityException:許可の拒否:ProcessRecord {430b1748 29271:com.xxx/u0a88}(pid = 29271、uid = 10088)からプロバイダーcom.Android.providers.media.MediaDocumentsProviderを開くには、Android.permission.MANAGE_DOCUMENTSまたはAndroidが必要です。 permission.MANAGE_DOCUMENTS
MANAGE_DOCUMENTS
およびREAD_EXTERNAL_STORAGE
権限を追加しましたが、まだこのエラーが発生しています。問題のコード:
public static String getImagePath(HailoDriverApplication app, Uri uri) {
Cursor cursor = null;
if (uri == null) {
return null;
}
try {
cursor = app.getContentResolver().query(uri, new String[] {
MediaStore.Images.Media.DATA
}, null, null, null);
int column_index = cursor.getColumnIndexOrThrow(MediaStore.Images.Media.DATA);
if (cursor.moveToFirst()) {
return cursor.getString(column_index);
}
} finally {
if (cursor != null) {
cursor.close();
}
}
return null;
}
マニフェストのリクエストされたスニペット:
<manifest xmlns:Android="http://schemas.Android.com/apk/res/Android"
xmlns:tools="http://schemas.Android.com/tools"
package="com.x.x.x" >
<uses-sdk
Android:minSdkVersion="8"
Android:targetSdkVersion="16" />
<uses-permission Android:name="Android.permission.INTERNET" />
<uses-permission Android:name="Android.permission.VIBRATE" />
<uses-permission Android:name="Android.permission.ACCESS_NETWORK_STATE" />
<uses-permission Android:name="Android.permission.ACCESS_COURSE_LOCATION" />
<uses-permission Android:name="Android.permission.ACCESS_FINE_LOCATION" />
<uses-permission Android:name="Android.permission.RECEIVE_BOOT_COMPLETED" />
<uses-permission Android:name="Android.permission.WAKE_LOCK" />
<uses-permission Android:name="Android.permission.READ_LOGS" />
<uses-permission Android:name="Android.permission.READ_PHONE_STATE" />
<uses-permission Android:name="Android.permission.READ_CONTACTS" />
<uses-permission Android:name="Android.permission.CHANGE_WIFI_STATE" />
<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />
<uses-permission Android:name="Android.permission.WRITE_EXTERNAL_STORAGE" />
<uses-permission Android:name="Android.permission.READ_EXTERNAL_STORAGE" />
<uses-permission Android:name="Android.permission.MANAGE_DOCUMENTS" />
<uses-permission Android:name="Android.permission.SYSTEM_ALERT_WINDOW" />
<uses-permission Android:name="com.google.Android.providers.gsf.permission.READ_GSERVICES" />
<uses-permission
Android:name="Android.permission.UPDATE_DEVICE_STATS"
tools:ignore="ProtectedPermissions" />
<uses-permission Android:name="Android.permission.WRITE_SETTINGS" />
<uses-permission Android:name="Android.intent.action.BATTERY_CHANGED" />
<uses-permission
Android:name="Android.permission.INSTALL_PACKAGES"
tools:ignore="ProtectedPermissions" />
<uses-permission Android:name="Android.permission.GET_ACCOUNTS" />
<uses-permission Android:name="com.google.Android.c2dm.permission.RECEIVE" />
過去数日間同じ問題がありました。いくつかのソリューションを試しましたが、何らかの理由で、マニフェストにAndroid.permission.MANAGE_DOCUMENTS権限が追加されていても、一部の画像のUriコンテンツプロバイダーで権限が拒否されました。
当面の回避策は次のとおりです。
i = new Intent(Intent.ACTION_PICK, Android.provider.MediaStore.Images.Media.EXTERNAL_CONTENT_URI);
startActivityForResult(i, CHOOSE_IMAGE);
これにより、新しいKitKatドキュメントビューではなく、古い画像ギャラリーが強制的に開かれます。
これで、onActivityResultで次を呼び出すことでUriを取得できます。
Uri selectedImageURI = data.getData();
お役に立てれば。
ユーザーにファイルの追加を促すために使用されるインテントで、Intent.ACTION_GET_CONTENTまたはIntent.ACTION_PICKの代わりにIntent.ACTION_OPEN_DOCUMENT(KitKat API 19以降)を使用します。次に、Uriを使用するときは、@ feriのリンク( https://developer.Android.com/guide/topics/providers/document -provider.html#permissions ):
final int takeFlags = data.getFlags()
& (Intent.FLAG_GRANT_READ_URI_PERMISSION
| Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
// Check for the freshest data.
getContentResolver().takePersistableUriPermission(originalUri, takeFlags);
Intent.ACTION_GET_CONTENT、Intent.ACTION_PICK、およびIntent.ACTION_OPEN_DOCUMENTの違いについて詳しくは、こちらをご覧ください。 http://developer.Android.com/reference/Android/content/Intent.html#ACTION_OPEN_DOCUMENT
OK、問題を乗り越える実用的なサンプルを見つけました:
intent = new Intent(Intent.ACTION_OPEN_DOCUMENT);
intent.addCategory(Intent.CATEGORY_OPENABLE);
intent.setType("image/*");
startActivityForResult(intent, myClassConstant.SELECT_PICTURE);
これが私が学んだことです...これはキットカットの変更であり、このコードはAPI 19以上でのみ動作します。古いバージョンでは機能しないため、KitKatより前のメソッドも必要です。 Category_Openable引数(私の場合は画像)を使用してファイルを取得したら、URIとして参照することで使用できます。私の場合、URIString(ファイルパス)を保存し、オープンが発生した後、それを使用して必要なことを行うことができます。
今私が理解しようとしている問題は、ファイルのアクセス許可がどのくらい持続するかです。私のコードはUriStringを探し、ファイルを開こうとするため、昨日から期限切れになっているようです。上記のコードを使用して画像を選択すると、それが機能します-名前が保存され、プログラムを終了して戻ることができました...しかし、今朝の最初のプログラムの実行(後12時間以上触れないでください)、ファイルを見つけることができなかったように動作しました(そして、デバッガーを見ると、重大ではないエラーが再び表示されるのがわかります)。
だから今質問は次のとおりです。ファイル(名前)が何であるかを知った後、どのようにアクセス許可を保持しますか。
表示したいUriは、Android 4.4 KitKat。これはギャラリーとGoogleドライブのどちらでもよい。これらのドキュメントにアクセスするには、システムファイルピッカーを使用するようです。ユーザーが開くファイルを選択すると、システムはアプリに許可を与え、ファイルを開くダイアログを開始します。他の画像にはアクセスできず、セキュリティ例外が発生します。
Uriが永続化されている場合、Uriへのアクセスを許可された権利も永続化されなければなりません。詳細については、こちらをご覧ください: https://developer.Android.com/guide/topics/providers/document-provider.html#permissions
MANAGE_DOCUMENTS
パーミッションは、システムのみが保持できます:
MANAGE_DOCUMENTS権限。デフォルトでは、プロバイダーは誰でも利用できます。この許可を追加すると、プロバイダーがシステムに制限されます。この制限はセキュリティにとって重要です。
( Storage Access Framework から取得)
したがって、DocumentProvider
でこの権限を使用すると、プロバイダーへのアクセスをシステムのみに制限できます。つまり、System UI picker
のみがファイルにアクセスできます。そのため、アプリがProvider
からファイルを選択するには、ACTION_OPEN_DOCUMENT
でIntent
を起動する必要があり、実際にはSystem UI picker
を起動します。ユーザーはそこからファイルを選択し、URI
が返されます。
解決策は、ギャラリーの画像にアクセスする代わりに、 http://developer.Android.com/guide/topics/providers/document-provider.html#client を使用しているようです
他のアプローチがうまくいかない理由はわかりません。しかし、現時点では短期的な修正です。