EXTRA_INITIAL_URI isn't working

Hi,
I’ve two fragments where user is provided the option to pick a storage location and in both fragments, I use the following method for this purpose:

private void launchFilePicker(boolean shouldDownload) {
    Intent intent = new Intent(Intent.ACTION_OPEN_DOCUMENT_TREE);
    // Try to open the default/last location
    if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
        // Get the persisted uri
        Uri uri = mListener.getDownloadDirUri();
        if (uri != null) {
            DocumentFile location = DocumentFile.fromTreeUri(mActivity, uri);
            if (location != null) {
                intent.putExtra(DocumentsContract.EXTRA_INITIAL_URI, location.getUri());
            }
        }
    }
    intent.addFlags(Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION
            | Intent.FLAG_GRANT_READ_URI_PERMISSION | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
    startActivityForResult(intent, Constants.REQ_DOWNLOAD_LOC);
}

The methods to persist Uri and request code are obviously different in both fragments.

Here is the code when user selects a Uri:

@Override
public void onActivityResult(int requestCode, int resultCode, @Nullable Intent data) {
    super.onActivityResult(requestCode, resultCode, data);
    if (requestCode == Constants.REQ_DOWNLOAD_LOC) {
        if (resultCode == RESULT_OK && data != null && data.getData() != null) {
            Uri uri = data.getData();
                mListener.setDownloadDirUri(uri);
        }
    }
}

Here is when Uri is persisted:

@Override
public void setDownloadDirUri(Uri uri) {
    Uri oldUri = getDownloadDirUri();
    if (oldUri != null && uri.compareTo(oldUri) != 0) {
        getContentResolver().releasePersistableUriPermission(oldUri,
            Intent.FLAG_GRANT_READ_URI_PERMISSION |
                        Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
    }
    getContentResolver().takePersistableUriPermission(uri,
            Intent.FLAG_GRANT_READ_URI_PERMISSION |
                    Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
    getSharedPreferences(PreferenceKey.PREFS_FILES, MODE_PRIVATE).edit()
            .putString(PreferenceKey.KEY_DOWNLOAD_LOCATION, uri.toString()).apply();
}

What happens is that the file picker doesn’t show the respective persisted location as the initial location; it rather shows the location last selected in any of the two fragments. So, if I select a location in Fragment A and persist it in its distinct Key-Value pair, this same location will be opened as initial location in Fragment B without regard to which location was persisted for Fragment B earlier.
I’m testing it on a physical device with Android P.

Would really appreciate if you could suggest a solution for that.

Thanks!

1 Like

I do not believe that any of those flags are useful in this scenario.

I don’t know what the implementation of getDownloadDirUri() is, but if I understand your situation correctly, you have a bug there. Your EXTRA_INITIAL_URI value is derived from this, and by your description it appears to be returning the previous value (caching?).

BTW, rather than taking persistable permission for the individual documents, have you tried doing it just for the whole tree? I think you get access to the contents of that tree, without needing to persist the permissions for the individual documents.

1 Like

That’s exactly what I’m doing: persisting the Uri of the whole tree.

1 Like

:man_facepalming:

Sorry, I wasn’t paying close attention there!

1 Like

Here it is:

public Uri getDownloadDirUri() {
    String uriString = getSharedPreferences(PreferenceKey.PREFS_FILES, Context.MODE_PRIVATE)
            .getString(PreferenceKey.KEY_DOWNLOAD_LOCATION, "");
    return Uri.parse(uriString);
}
1 Like

I misunderstood this earlier as well. SharedPreferences are per-app, not per-fragment. So, both fragments are sharing the SharedPreferences, and they both appear to use the same key, so they will share a common value. If you want each fragment to have its own value, each fragment needs its own key.

1 Like

As per the documentation:

Location should specify a document URI or a tree URI with document ID.

Any idea about what document ID means in above statement?

1 Like

No, sorry. I do not know what it would mean for a tree Uri to have a document ID.

1 Like

OK, thanks anyway. Oh and I’m using separate SharedPreferences keys for each fragment. Problem is somewhere else.

1 Like

Where are you doing the apply or commit after your edit on SharedPref?

Please have a look at the code pasted in my question. It is already mentioned in there.

Okay. I see it now. Maybe I didn’t scroll far enough to the right the first time. Hope you got your problem solved.