Search code examples
javaandroidfilechooser

File Chooser on newer OS - file not found


In my Android app, I need to load a text file from the storage using a file chooser dialog. Some time ago, I followed the instructions in this Android file chooser topic (original answer).

On the phone with Android 4.2.2 (API 17) everything works fine. This code (actually as the uri.getPath() itself) returns the real path of the file:

public static String getPath(Context context, Uri uri) throws URISyntaxException {
    if ("content".equalsIgnoreCase(uri.getScheme())) {
        String[] projection = { "_data" };
        Cursor cursor = null;
        try {
            cursor = context.getContentResolver().query(uri, projection, null, null, null);
            int column_index = cursor.getColumnIndexOrThrow("_data");
            if (cursor.moveToFirst()) {
                return cursor.getString(column_index);
            }
        } catch (Exception e) {
            ...
        }
        ...
    }
    ...
}

It returns something like this: /storage/sdcard1/Directory/myFile.txt

..and I can further work with the file.

However, on the phones with Android 7 and 8 (API 24-26), the cursor.getString(column_index) always returns null, and the uri.getPath() return paths like:

  • /document/254 - Android 8 (external storage)
  • /document/primary:myFile.txt - Android 8 (internal storage)
  • /document/C5F9-13FC:myFile.txt - Android 7

... and when I want to work with the file created by new File(path) and read its content with BufferedReader, I get the FileNotFoundException.

I do not think this is a permission problem because when I read the file with hardcoded path using the following code, everything works fine:

File storage = Environment.getExternalStorageDirectory();
File file = new File(storage, fileName);

My question is:

Is there any way to get the real file path from the file chooser or should I adress this problem on devices with newer Android API in a completely different way like using an external library?


Solution

  • I found a solution here.

    The problem was that I wanted to read the file using the following code:

    File file = new File(intent.getData().getPath());
    BufferedReader br = new BufferedReader(new FileReader(file));
    

    Instead, I should be using this:

    InputStream is = getContentResolver().openInputStream(intent.getData());
    BufferedReader br = new BufferedReader(new InputStreamReader(is));