如何使用FileProvider?提供来自SECONDARY外部存储的文件?
FileProvider句柄的当前实现只返回第一个目录ContextCompat.getExternalFilesDirs
...
} else if (TAG_EXTERNAL_FILES.equals(tag)) {
File[] externalFilesDirs = ContextCompat.getExternalFilesDirs(context, null);
if (externalFilesDirs.length > 0) {
target = externalFilesDirs[0];
}
}
...
Run Code Online (Sandbox Code Playgroud)
看来,没有办法为匹配辅助外部存储路径的<path>条目定义FileProvider...
我在我的应用程序中使用FileProvider,当我从应用程序拍照时存储在那里.我的应用程序也有不同的应用程序ID用于调试和发布版本
我已经定义了这样的文件提供程序
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="@string/authority_file_provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths" />
</provider>
Run Code Online (Sandbox Code Playgroud)
价值@string/authority_file_provider将变成:
而我@xml/file_paths的定义就像
<?xml version="1.0" encoding="utf-8"?>
<paths>
<external-path name="my_images" path="Android/data/com.rkmax.myapp/files/Pictures" />
</paths>
Run Code Online (Sandbox Code Playgroud)
如果我尝试更改类似的东西Pictures或files/Pictures我的应用程序失败
Failed to find configured root that contains/storage/emulated/0/Android/data/com.rkmax.myapp.debug/files/Pictures/20161112_073128-251269360.jpg
Run Code Online (Sandbox Code Playgroud)
我如何在文件提供程序路径中定义相对路径?
目前,当文件在外部SD上时,FileProvider getUriForFile方法会生成IllegalArgumentException
当文件在设备内存中时(在/ storage/emulated/0下),它可以正常工作.
Uri videoUri = FileProvider.getUriForFile(this,
getApplicationContext().getPackageName() + ".provider",
new File(videoPath));
Run Code Online (Sandbox Code Playgroud)
这里videoPath具有以下值:
videoPath = /storage/extSdCard/Android/data/com.podcastcutter.debug/files/episodeMp3/TEDTalks (video)/Why you should love statistics - Alan Smith.mp4
Run Code Online (Sandbox Code Playgroud)
我的清单文件包含:
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="${applicationId}.provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths"/>
</provider>
Run Code Online (Sandbox Code Playgroud)
这里是provider_paths:
<external-path name="external_files" path="."/>
Run Code Online (Sandbox Code Playgroud)
如何修改FileProvider配置以解决此问题?
提前致谢.
产生异常:
java.lang.IllegalArgumentException: Failed to find configured root that contains /storage/extSdCard/Android/data/com.podcastcutter.debug/files/episodeMp3/TEDTalks (video)/Why you should love statistics - Alan Smith.mp4
android.support.v4.content.FileProvider$SimplePathStrategy.getUriForFile(FileProvider.java:711)
android.support.v4.content.FileProvider.getUriForFile(FileProvider.java:400)
Run Code Online (Sandbox Code Playgroud)
其他配置信息:
compileSdkVersion 25
buildToolsVersion "23.0.3"
minSdkVersion 16
targetSdkVersion 25
support libraries version : 25.1.1
Run Code Online (Sandbox Code Playgroud) Context.getFilesDir() 对应的 XML 是什么?
我当前的 XML:
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<files-path name="internal" path="." />
</paths>
Run Code Online (Sandbox Code Playgroud)
文件创建:
File video = new File(getFilesDir(), "movie.mp4");
videoUri = FileProvider.getUriForFile(this, "my.package.name.provider", video);
Run Code Online (Sandbox Code Playgroud) 根据FileProvider 文档,该fileProvider.openFile()方法返回
一个新的ParcelFileDescriptor,您可以使用它访问该文件。
我查看了ParcelFileDescriptor,但我看不到如何访问该文件。那么如何从 ParcelFileDescriptor 访问文件呢?
首先要提到的是,这里问题的答案没有帮助。
源代码如下所示:
Intent intent = new Intent("com.mycompany.action.PICK_FILE");
String authority = "com.mycompany.fileprovider";
File file = Environment.getExternalStorageDirectory();
intent.setData(FileProvider.getUriForFile(this, authority, file));
Run Code Online (Sandbox Code Playgroud)
FileProvider.getUriForFile抛出异常,这是堆栈跟踪:
java.lang.StringIndexOutOfBoundsException: length=15; index=16
at java.lang.String.indexAndLength(String.java:500)
at java.lang.String.substring(String.java:1313)
at android.support.v4.content.FileProvider$SimplePathStrategy.getUriForFile(FileProvider.java:687)
at android.support.v4.content.FileProvider.getUriForFile(FileProvider.java:377)
Run Code Online (Sandbox Code Playgroud)
在标签AndroidManifest.xml内部application我添加了以下内容:
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="com.mycompany.fileprovider"
android:exported="false"
android:grantUriPermissions="true"
>
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/file_paths"
/>
</provider>
Run Code Online (Sandbox Code Playgroud)
内容file_paths.xml如下:
<paths xmlns:android="http://schemas.android.com/apk/res/android">
<external-path name="input_files" path="." />
<external-path name="output_files" path="MyAppName/" />
</paths>
Run Code Online (Sandbox Code Playgroud)
output_files在此上下文中不使用路径。
我已经通过运行调试器FileProvider.SimplePathStrategy.getUriForFile()。相关代码片段如下(第683-688行):
final String rootPath = mostSpecific.getValue().getPath();
if (rootPath.endsWith("/")) {
path = path.substring(rootPath.length());
} …Run Code Online (Sandbox Code Playgroud) 我正在尝试打开我下载并保存在外部存储中的pdf文件.但是当我打开我的应用程序时,它会崩溃并显示以下错误;
08-31 00:58:31.304 1807-1807/? E/AndroidRuntime: FATAL EXCEPTION: main
Process: medimanage.corporate.mobile, PID: 1807
java.lang.RuntimeException: Unable to get provider android.support.v4.content.FileProvider: java.lang.IllegalArgumentException: Missing android.support.FILE_PROVIDER_PATHS meta-data
at android.app.ActivityThread.installProvider(ActivityThread.java:5856)
at android.app.ActivityThread.installContentProviders(ActivityThread.java:5445)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5384)
at android.app.ActivityThread.-wrap2(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1545)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6119)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776)
Caused by: java.lang.IllegalArgumentException: Missing android.support.FILE_PROVIDER_PATHS meta-data
at android.support.v4.content.FileProvider.parsePathStrategy(FileProvider.java:586)
at android.support.v4.content.FileProvider.getPathStrategy(FileProvider.java:557)
at android.support.v4.content.FileProvider.attachInfo(FileProvider.java:375)
at android.app.ActivityThread.installProvider(ActivityThread.java:5853)
at android.app.ActivityThread.installContentProviders(ActivityThread.java:5445)
at android.app.ActivityThread.handleBindApplication(ActivityThread.java:5384)
at android.app.ActivityThread.-wrap2(ActivityThread.java)
at android.app.ActivityThread$H.handleMessage(ActivityThread.java:1545)
at android.os.Handler.dispatchMessage(Handler.java:102)
at android.os.Looper.loop(Looper.java:154)
at android.app.ActivityThread.main(ActivityThread.java:6119)
at java.lang.reflect.Method.invoke(Native Method)
at com.android.internal.os.ZygoteInit$MethodAndArgsCaller.run(ZygoteInit.java:886)
at com.android.internal.os.ZygoteInit.main(ZygoteInit.java:776) …Run Code Online (Sandbox Code Playgroud) 我正在尝试在android设备上拍照,并按照本教程操作。
下面的代码给我一个错误android.support.v4.content.FileProvider。Android studio表示未解决的类'FileProvider'。
我有以下AndroidManifest.xml文件:
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
package="com.example.camera">
<uses-permission android:name="android.permission.CAMERA" />
<application
android:label="@string/app_name">
<activity android:name=".LandingPageActivity" />
<provider
android:name="android.support.v4.content.FileProvider"
android:authorities="${applicationId}.provider"
android:exported="false"
android:grantUriPermissions="true">
<meta-data
android:name="android.support.FILE_PROVIDER_PATHS"
android:resource="@xml/provider_paths" />
</provider>
</application>
</manifest>
Run Code Online (Sandbox Code Playgroud)
我已添加implementation 'com.android.support:support-v4:28.0.0'到我的build.gradle文件。
apply plugin: 'com.android.application'
android {
compileSdkVersion 28
defaultConfig {
applicationId "com.example.camera"
minSdkVersion 15
targetSdkVersion 28
versionCode 1
versionName "1.0"
testInstrumentationRunner "androidx.test.runner.AndroidJUnitRunner"
vectorDrawables.useSupportLibrary = true
}
buildTypes {
release {
minifyEnabled false
proguardFiles getDefaultProguardFile('proguard-android-optimize.txt'), 'proguard-rules.pro'
}
}
}
dependencies {
implementation …Run Code Online (Sandbox Code Playgroud) 由于Android在有关文件访问的不同主要版本之间非常不一致,因此我感到有些失落。我尝试尽可能简单地描述问题:
我的公司使用商业本地DRM保护我们提供的其他本地库。我们有一个许可应用程序,该应用程序调用了一些Voodoo来结束/ sdcard / companyname / LicenseContainer /中的许可文件。其他受保护的应用程序以本机代码查看此目录,检查用户是否具有有效的许可证。
但是,Android 10更新仅提供,使该工作流程完全无效scoped storage access。我们可以使用一种方法Storage Manager来授予访问权限,不幸的是,现在也已弃用该方法。
所以我的问题是:一个应用程序如何将文件保存到/ sdcard / FOLDER上的某个位置
对于所有可能的解决方案(SAF,FileProvider等),我有点不知所措,这些解决方案通常会调用一个应用程序将权限授予另一个应用程序的权限。但是,如果没有安装的第一个应用程序将文件放到那里,则应该可以访问这些文件。
我知道必须有解决方案,因为最近的FileManagers(即Files by Google)可以访问整个/sdcard/目录。
在不调用“黑客”之类的情况下,最简单,最适合未来的路线是什么 android:requestLegacyExternalStorage="true"
android file android-fileprovider storage-access-framework scoped-storage
我在 chromebook 上有一个(大)问题,其功能在“经典”Android 设备(手机、平板电脑)上运行良好。
我尝试发送带有附件的电子邮件。
这是部分代码(api>=23)。
Run Code Online (Sandbox Code Playgroud)Intent email = new Intent(Intent.ACTION_SEND); String[] str = new String[1]; str[0] = "destination@yahoo.fr"; email.putExtra(Intent.EXTRA_EMAIL, str); email.putExtra(Intent.EXTRA_TEXT, "My text"); email.putExtra(Intent.EXTRA_SUBJECT, "My subject"); Uri uri = FileProvider.getUriForFile(this, "com.TTT.fileprovider", new File(dest)); email.putExtra(android.content.Intent.EXTRA_STREAM, uri); email.setFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION | Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION); email.setType("message/rfc822"); startActivity(email);
在我的手机(android 9 api 28)上,调用了 gmail 应用程序,所有文本字段都填充了正确的信息,并且文件 (myResume.pdf) 已正确附加。
发送然后接收时,电子邮件包含一个可读的 pdf 文件。这很酷。
使用我的 chromebook (PB 314 / v. 83.0.4103.119),gmail 被调用,所有文本字段都填充了正确的信息,但没有附加文件。
LogCat 表示:
2020-06-27 15:25:50.886 127-2348/? I/ActivityManager: START u0 {act=android.intent.action.SEND typ=message/rfc822 flg=0x43 cmp=org.chromium.arc.applauncher/.ChromeBrowserProxyActivity clip={message/rfc822 T:My text} (has …Run Code Online (Sandbox Code Playgroud)