Tutorials 31 min read

Your Notes Folder on Android Is Not a Folder

MMNMNOTE
androidscoped storagestorage access frameworkfile permissionsmarkdown vaultnote-takingandroid 11
Updated August 15, 2026

On Android 11 and higher, an app cannot be pointed at a folder path. It receives a per-directory grant that the user picks in a system dialog — and three directories cannot be granted at all: the root of internal storage, the root of any SD-card volume the manufacturer calls reliable, and Download.

This is the fact that breaks the standard cross-device vault advice. Keep your notes as plain Markdown in one folder, the advice runs — then point every app you use at that folder. On a laptop this works, because a folder there is a path and a path is something a program may open.

On Android since version 11 a folder is not a path an app may open. It is a grant — a revocable, per-URI lease the user hands over one directory at a time. It expires on reboot unless the app asks for more, it dies if the directory is moved or deleted, and it can be evicted by the system without anyone revoking anything. Every claim in this reference is pinned to an API level and an Android version, and sourced to the platform's own documentation or to the Android Open Source Project.12

The three directories Android will not grant

On Android 11 (API level 30) and higher, ACTION_OPEN_DOCUMENT_TREE cannot request three locations: the root directory of the internal storage volume, the root of each SD-card volume the manufacturer considers reliable, and the Download directory. Those three are exactly what the "point both apps at the same folder" instruction assumes it can reach.1

The platform states it plainly. "On Android 11 (API level 30) and higher, you cannot use the ACTION_OPEN_DOCUMENT_TREE intent action to request access to the following directories," reads the developer documentation — and then it lists them: "The root directory of the internal storage volume. The root directory of each SD card volume that the device manufacturer considers to be reliable, regardless of whether the card is emulated or removable. A reliable volume is one that an app can successfully access most of the time. The Download directory."1

Read that list against how people actually organise a phone. The storage root is where a file manager drops you. Download is where a browser, a mail client, and most sync tools put a file — and neither can be handed to an app as a directory tree.

What remains grantable is narrow: a directory you created deliberately and picked deliberately, one app at a time.

The second beat: Android/data

A separate restriction closes the other obvious route. "You can no longer use the ACTION_OPEN_DOCUMENT_TREE or the ACTION_OPEN_DOCUMENT intent action to request that the user select individual files from the following directories," the Android 11 storage notes say — "The Android/data/ directory and all subdirectories. The Android/obb/ directory and all subdirectories."2

So an app's own private area is closed to every other app, in both directions. "On Android 11, apps can no longer access files in any other app's dedicated, app-specific directory within external storage."2 This holds even for an app that has been granted the broadest storage permission the platform offers — because "these directories appear as subdirectories of Android/data/ on a storage volume."3

What a folder is on Android: a grant, not a path

The mechanism that replaced the path is the Storage Access Framework. "The ACTION_OPEN_DOCUMENT_TREE intent action, available on Android 5.0 (API level 21) and higher, allows users to select a specific directory, granting your app access to all of the files and sub-directories within that directory."1 The user's pick is the permission — there is no manifest entry to declare.

Google's own framing of the shift is the sentence to hold on to: "More recent versions of Android rely more on a file's purpose than its location for determining an app's ability to access, and write to, a given file."4

Location stopped being the unit of access. Purpose and user consent replaced it.

The default arrived one version earlier. "To give users more control over their files and to limit file clutter, apps that target Android 10 (API level 29) and higher are given scoped access into external storage, or scoped storage, by default."4 Android 11 removed the opt-out: "After you update your app to target Android 11, the system ignores the requestLegacyExternalStorage flag."2

The old permission became inert at the same time — "if your app targets Android 11 (API level 30) or higher, the WRITE_EXTERNAL_STORAGE permission doesn't have any effect on your app's access to storage."4

Here is what asking for a directory looks like in practice. The app fires an intent; the system, not the app, draws the picker:

fun openDirectory(pickerInitialUri: Uri) {
    // Choose a directory using the system's file picker.
    val intent = Intent(Intent.ACTION_OPEN_DOCUMENT_TREE).apply {
        // Optionally, specify a URI for the directory that should be opened in
        // the system file picker when it loads.
        putExtra(DocumentsContract.EXTRA_INITIAL_URI, pickerInitialUri)
    }

    startActivityForResult(intent, your-request-code)
}

What comes back is a URI, not a path:

override fun onActivityResult(
        requestCode: Int, resultCode: Int, resultData: Intent?) {
    if (requestCode == your-request-code
            && resultCode == Activity.RESULT_OK) {
        // The result data contains a URI for the document or directory that
        // the user selected.
        resultData?.data?.also { uri ->
            // Perform operations on the document using its URI.
        }
    }
}

Two properties of that URI decide everything downstream. It is scoped: "When using ACTION_OPEN_DOCUMENT_TREE, your app gains access only to the files in the directory that the user selects. You don't have access to other apps' files that reside outside this user-selected directory."1 And it is consent-shaped — "because the user is involved in selecting the files or directories that your app can access, this mechanism doesn't require any system permissions, and user control and privacy is enhanced."1

Single files use sibling intents. Opening one document:

// Request code for selecting a PDF document.
const val PICK_PDF_FILE = 2

fun openFile(pickerInitialUri: Uri) {
    val intent = Intent(Intent.ACTION_OPEN_DOCUMENT).apply {
        addCategory(Intent.CATEGORY_OPENABLE)
        type = "application/pdf"

        // Optionally, specify a URI for the file that should appear in the
        // system file picker when it loads.
        putExtra(DocumentsContract.EXTRA_INITIAL_URI, pickerInitialUri)
    }

    startActivityForResult(intent, PICK_PDF_FILE)
}

Creating one:

// Request code for creating a PDF document.
const val CREATE_FILE = 1

private fun createFile(pickerInitialUri: Uri) {
    val intent = Intent(Intent.ACTION_CREATE_DOCUMENT).apply {
        addCategory(Intent.CATEGORY_OPENABLE)
        type = "application/pdf"
        putExtra(Intent.EXTRA_TITLE, "invoice.pdf")

        // Optionally, specify a URI for the directory that should be opened in
        // the system file picker before your app creates the document.
        putExtra(DocumentsContract.EXTRA_INITIAL_URI, pickerInitialUri)
    }
    startActivityForResult(intent, CREATE_FILE)
}

Note what the app never learns. It queries metadata through the URI rather than the filesystem — and even the name it gets back is advisory:

val cursor: Cursor? = contentResolver.query(
        uri, null, null, null, null, null)

cursor?.use {
    if (it.moveToFirst()) {
        // Note it's called "Display Name". This is
        // provider-specific, and might not necessarily be the file name.
        val displayName: String =
                it.getString(it.getColumnIndex(OpenableColumns.DISPLAY_NAME))
        Log.i(TAG, "Display Name: $displayName")
    }
}

The grant is a lease, not a deed

A fresh grant is temporary. "When your app opens a file for reading or writing, the system gives your app a URI permission grant for that file, which lasts until the user's device restarts."1 Persistence is a second, explicit step — and even the persistent form has three ways to end without the user ever revoking it.

The app has to ask:

val contentResolver = applicationContext.contentResolver

val takeFlags: Int = Intent.FLAG_GRANT_READ_URI_PERMISSION or
        Intent.FLAG_GRANT_WRITE_URI_PERMISSION
// Check for the freshest data.
contentResolver.takePersistableUriPermission(uri, takeFlags)

The Java form, for the same call:

final int takeFlags = intent.getFlags()
            & (Intent.FLAG_GRANT_READ_URI_PERMISSION
            | Intent.FLAG_GRANT_WRITE_URI_PERMISSION);
// Check for the freshest data.
getContentResolver().takePersistableUriPermission(uri, takeFlags);

The API reference sets the boundary: "Once taken, the permission grant will be remembered across device reboots. Only URI permissions granted with Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION can be persisted."5

Ending one — the directory moves or is deleted. "Even after calling takePersistableUriPermission(), your app doesn't retain access to the URI if the associated document is moved or deleted. In those cases, you need to ask permission again to regain access to the URI."1 Reorganising a vault from a file manager is enough to break a grant a different app was relying on.

Ending two — eviction at a cap. The platform prunes a package's persisted grants once they pass a limit. The limit lives in the Android Open Source Project, not in the documentation:

    // Maximum number of persisted Uri grants a package is allowed
    private static final int MAX_PERSISTED_URI_GRANTS = 512;

And the prune drops the oldest first:

    /**
     * Prune any older {@link UriPermission} for the given UID until outstanding
     * persisted grants are below {@link #MAX_PERSISTED_URI_GRANTS}.
     */
    private boolean maybePrunePersistedUriGrantsLocked(int uid) {
        // ... collect this UID's persisted grants, compute trimCount ...
        Collections.sort(persisted, new UriPermission.PersistedTimeComparator());
        for (int i = 0; i < trimCount; i++) {
            final UriPermission perm = persisted.get(i);
            perm.releasePersistableModes(~0);
            removeUriPermissionIfNeededLocked(perm);
        }

        return true;
    }

The 512-versus-128 correction. A figure of 128 persisted URI grants circulates widely, and it is stale. It was 128 in the Android 8 and Android 9 source, where the constant lived in ActivityManagerService.java — it has been 512 on every release branch from android11-release through android16-release and on current main, where it lives in UriGrantsManagerService.java. Both values are checkable in a loop, and the check is the receipt:

$ for br in main android11-release android13-release android14-release \
            android15-release android16-release; do
    printf '%-18s -> ' "$br"
    curl -sL "https://android.googlesource.com/platform/frameworks/base/+/refs/heads/$br/services/core/java/com/android/server/uri/UriGrantsManagerService.java?format=TEXT" \
      | base64 -d | grep -m1 -o 'MAX_PERSISTED_URI_GRANTS = .*'
  done
main               -> MAX_PERSISTED_URI_GRANTS = 512;
android11-release  -> MAX_PERSISTED_URI_GRANTS = 512;
android13-release  -> MAX_PERSISTED_URI_GRANTS = 512;
android14-release  -> MAX_PERSISTED_URI_GRANTS = 512;
android15-release  -> MAX_PERSISTED_URI_GRANTS = 512;
android16-release  -> MAX_PERSISTED_URI_GRANTS = 512;

$ for tg in android-8.0.0_r1 android-9.0.0_r1; do
    printf '%-18s -> ' "$tg"
    curl -sL "https://android.googlesource.com/platform/frameworks/base/+/refs/tags/$tg/services/core/java/com/android/server/am/ActivityManagerService.java?format=TEXT" \
      | base64 -d | grep -m1 -o 'MAX_PERSISTED_URI_GRANTS = .*'
  done
android-8.0.0_r1   -> MAX_PERSISTED_URI_GRANTS = 128;
android-9.0.0_r1   -> MAX_PERSISTED_URI_GRANTS = 128;

Two honesty notes about that number. It is undocumenteddeveloper.android.com never states it, so a reader who goes looking for a doc page will not find one, and the source line above is the only citable form.6 And because it is an internal constant rather than a published API, it can change without a release note; the 512 figure was read on 15 August 2026 and reproduced across six branches.6

Ending three — the user. Grants are revocable by design, and the platform has been criticised for not surfacing them well. That criticism is in the fairness section below.

MediaStore does not index a Markdown file

The other route an app might take to shared storage is MediaStore — and for a notes vault it is a dead end. The media scanner indexes images, video, audio, and downloads. A .md file is none of those, and under scoped storage the general file collection shows an app only what that same app created.7

The scanned set is enumerated: "The system automatically scans an external storage volume and adds media files to the following well-defined collections" — images in DCIM/ and Pictures/, videos in DCIM/, Movies/, and Pictures/, audio in Alarms/, Audiobooks/, Music/, Notifications/, Podcasts/, and Ringtones/, plus downloaded files.7

Markdown appears nowhere in that list.

The fallback collection is narrower than its name suggests. Of MediaStore.Files, the documentation says: "If scoped storage is enabled, the collection shows only the photos, videos, and audio files that your app has created."7

Google's own split confirms the routing. "Media content: The system provides standard public directories for these kinds of files… Your app can access this content using the platform's MediaStore API," one page says — and immediately after: "Documents and other files: The system has a special directory for containing other file types, such as PDF documents and books that use the EPUB format. Your app can access these files using the platform's Storage Access Framework."8

Documents go to the Storage Access Framework. Notes are documents.

A shipping vendor reached the same conclusion from the outside. Writing on the Nextcloud blog on 13 May 2025, Christoph Weissthaner recounted being told by app review to replace an all-files permission with a privacy-friendlier API — and reported the result of evaluating one of them: "MediaStore API cannot be used as it does not allow access to other files, but only media files."9 That is a team that had to live with the answer, not a reading of a spec.

All-files access, and the policy that gates it

There is an escape hatch. "Android 11 introduces the MANAGE_EXTERNAL_STORAGE permission, which provides write access to files outside the app-specific directory and MediaStore."4 What stops a note app from using it is not the operating system — it is Google Play's distribution policy, which restricts the permission to a short list of app types that does not include note-taking.10

The eligibility list is explicit. "If your app includes a use case similar to any of the following, it's likely that it can request the MANAGE_EXTERNAL_STORAGE permission," the documentation says, then names seven: file managers, backup and restore apps, anti-virus apps, document management apps, on-device file search, disk and file encryption, and device-to-device data migration.3

Two lines spell out what happens to an app that guesses wrong. "Google Play restricts the use of high-risk or sensitive permissions, including special app access called All files access."10 And: "Apps that fail to meet policy requirements or do not submit a Permissions Declaration Form may be removed from Google Play."10

The bar is core functionality — defined as "the main purpose of the app. Without this core functionality, the app is 'broken' or rendered unusable."10

The listing that decides it for a notes tool sits under invalid uses: "Any File selection activity where the user manually selects individual files."10 That is precisely the interaction a person means when they say let me point the app at my vault folder.

The platform's guidance says the same thing from the other side — request the permission "only when your app can't effectively make use of the more privacy-friendly APIs, such as the Storage Access Framework or the Media Store API."3 The policy has a date, though the policy page itself carries none: the developer documentation records that "This policy is in effect as of May 2021."3

For testing, the permission can be toggled from a shell — a useful way to see the difference on your own device without shipping anything:

adb shell appops set --uid PACKAGE_NAME MANAGE_EXTERNAL_STORAGE allow

The enforcement is real, and it is documented by the vendor it hit. Weissthaner's account: "In September 2024, an update of the Nextcloud app for Android was refused out of the blue. We have been asked to remove the permission to all files or use 'a more privacy aware replacement' like Storage Access Framework (SAF) or MediaStore API."9

The episode ended eight months later: "This morning, May 15, Google reached out to us and offered to restore the permission, which will give our users back the functionality that was lost."9 Nextcloud is a file-sync vendor rather than a note app — the point here is the timeline and the technical finding, not the argument the post makes around them.

And even the escape hatch does not reopen the door in the previous section. "Apps that are granted this permission still can't access the app-specific directories that belong to other apps."3

The four access modes, side by side

Four routes exist into storage on a modern Android device, and only one of them can reach a user-created vault folder. This table is the reference the rest of the post builds toward — what each mode requires, whether it can see your notes, and what happens to it on uninstall and on reboot.

ModeHow the app gets itPermission neededCan it reach your vault folder?Survives uninstall?Survives reboot?
App-specific directorygetExternalFilesDir() / getFilesDir()NoneNo — its own directory only, and no other app may enter it23No — the files are removed with the appn/a
SAF tree grantACTION_OPEN_DOCUMENT_TREE (API 21+)1None — the user's pick is the permission1Yes — except the storage root, a reliable SD-card root, and Download1; never Android/data or Android/obb2Yes8Only with takePersistableUriPermission()15; lost if the document is moved or deleted1; prunable at 5126
MediaStoreMediaStore via ContentResolverMedia permissions / photo pickerNo — a .md file is never scanned7; MediaStore.Files shows only your app's own media7Yes7n/a
All-files accessMANAGE_EXTERNAL_STORAGESpecial app access plus Google Play approval10Yes for shared storage — still not other apps' Android/data3YesYes

Read the second row against the fourth. The only mode that reaches a user's own vault is the one the user grants by hand, per app, per directory — and the only mode that would reach everything is gated by a policy naming manual file selection as an invalid reason to ask.10

There is no fifth row. That is the whole map.

What changed after Android 11: for documents, nothing

Storage on Android has a reputation for changing every year, and for media permissions that reputation is earned. For the document model it is not. The rules described above were set in Android 11 (API level 30) and are unchanged through Android 16 and into Android 17 (API level 37), which is in beta as of August 2026.11

The check is mechanical. Fetch every behaviour-changes page for Android 13 through 17 — both the all-apps pages and the ones scoped to apps targeting that release — and count storage-model terms in the body:

$ for p in 13/behavior-changes-13 14/behavior-changes-14 14/behavior-changes-all \
           15/behavior-changes-all 16/behavior-changes-16 16/behavior-changes-all \
           17/behavior-changes-17 17/behavior-changes-all; do
    hits=$(curl -sL "https://developer.android.com/about/versions/$p" \
      | sed -e 's/<[^>]*>/ /g' \
      | grep -ioE 'scoped storage|MANAGE_EXTERNAL_STORAGE|Storage Access Framework|ACTION_OPEN_DOCUMENT_TREE|READ_MEDIA|photo picker|MediaStore' \
      | sort -f | uniq -ci | tr -s ' ' | paste -sd' ' -)
    printf '%-24s %s\n' "$p" "${hits:-none}"
  done
13/behavior-changes-13    2 Photo picker  10 READ_MEDIA
14/behavior-changes-14    1 photo picker  1 READ_MEDIA
14/behavior-changes-all  none
15/behavior-changes-all  none
16/behavior-changes-16    2 MediaStore
16/behavior-changes-all  none
17/behavior-changes-17   none
17/behavior-changes-all  none

Not one of the eight pages mentions scoped storage, the Storage Access Framework, ACTION_OPEN_DOCUMENT_TREE, or MANAGE_EXTERNAL_STORAGE. Every hit that exists is a media hit. Android 13 carries most of them — READ_MEDIA_IMAGES, READ_MEDIA_VIDEO, and READ_MEDIA_AUDIO replacing READ_EXTERNAL_STORAGE for other apps' media, plus the photo picker. Android 14 adds Selected Photos Access, "which allows users to grant apps access to specific images and videos in their library," through READ_MEDIA_VISUAL_USER_SELECTED. Android 16's two hits are a fingerprinting fix: "For apps targeting Android 16 or higher, MediaStore#getVersion() will now be unique to each app."11 You can read your own device's grants for that split directly:

adb shell cmd appops get --uid PACKAGE_NAME

So the folklore that "Android 13, 14, and 15 tightened storage again" is false as applied to documents. Photos and video did get tighter — the rules governing whether an app may open your notes folder have not moved since API level 30. The scan above was run on 15 August 2026 against the live pages, which carry a Last updated 2026-08-13 UTC stamp.11

The case for the model, made by its sharpest critic

A reference that only lists costs is a complaint. The strongest available argument that this design is an improvement comes from Mark Murphy of CommonsWare — the same developer who catalogued its worst failure modes. Writing on 5 June 2019, before Android 11 shipped, he answered the critics of scoped storage on their own ground.12

"Being able to control storage access on a more granular basis is a fairly massive win," Murphy wrote. "Just because App X needs access to one particular file on external storage does not mean that App X should be granted access to all of external storage."12 His verdict on the whole shift: "It is an improvement. It may not be the best possible improvement; there will be collateral damage stemming from this particular approach."12

He also answered the exact complaint this post opens with. If the objection is that users now have to pick a directory in a dialog rather than have an app read a path, his reply is one sentence: "Users have used file dialogs in desktop programs for decades."12

That line deserves to sit next to the headline, because it is true. The picker is not an alien interaction. What is new is that the picker is the only interaction — and that three directories sit outside its reach.

Google's own rationale is on the record too: "This purpose-based storage model improves user privacy because apps are given access only to the areas of the device's file system that they actually use."4

The costs, stated as precisely as the benefits

Murphy named three, and they are worth separating from the folklore that grew around them.

Overhead is structural. "There are two rounds of IPC for every SAF API call (your app to the SAF, then the SAF to the DocumentsProvider). That is going to add overhead, compared to doing the same thing with the filesystem."12

An attribution correction. The frequently repeated line that the Storage Access Framework is "~25 to 50 times slower" than direct file access is not Murphy's. It appears on his page inside a block quotation from the article he was replying to — and any reading that flattens the quotation into the surrounding prose merges the two voices, which is how the figure gets misattributed.

Murphy's own response to it was measured: "I have not run the benchmarks, but that result does not shock me."12 Attribute the benchmark to its author, or do not repeat it.

The picker is the manufacturer's, not Google's. Writing on 1 December 2019, Murphy identified the deeper structural risk: "The biggest is that device manufacturers may unilaterally eliminate the Storage Access Framework, by removing or replacing the activities that handle ACTION_OPEN_DOCUMENT and kin."13 He added that "since Google does not seem to test whether devices support SAF, there is no real pressure for device manufacturers to allow SAF to function."13

His summary of the class of problem: "In many respects, this is the single biggest problem with the death of external storage: the replacement solutions involve multiple parties and multiple sources of bugs."13 These are dated 2019 observations of the design's weak point rather than a current device inventory — no device was tested for this post.

Missing controls. Murphy's one concrete ask in 2019 was a place to see what you have handed out: "Android needs a Settings screen where users can review what durable storage access grants are outstanding and be able to revoke them."12

One boundary is worth drawing before the practical section. This is an access story, not a privacy story. "An app cannot reach that directory" does not mean your notes are safe, and it does not mean the operating system is reading them — it means one specific program was not given one specific grant.

What this means for a plain-Markdown vault

Portability on Android is a property of the format and the export, not of the path. The platform says so itself: "The exact location of where your files can be saved might vary across devices. For this reason, don't use hard-coded file paths."4 Plan around a file you can open — not a folder two apps share.

Five things follow, in order of how often they bite:

  1. Expect to grant per app, by hand. The user's pick is the permission.1 Two apps sharing a directory means two separate grants, made twice, in a system dialog.
  2. Do not put the vault in Download or at the storage root. Neither can be granted as a tree.1 Create a named directory somewhere grantable and keep it there.
  3. Moving the vault breaks the grants. A persisted grant does not survive the document being moved or deleted.1 Reorganising from a file manager silently costs you every grant pointing into the old location.
  4. Uninstalling an app that stored notes in its own app-specific directory takes the notes with it. Shared storage exists for "user data that can or should be accessible to other apps and saved even if the user uninstalls your app."8 Notes you intend to keep belong there.
  5. Treat export as the real portability guarantee. The format that survives the grant model is the one any editor can open — plain Markdown, in files you can copy off the device.

This is the same shape as a trap one layer down in the stack: the filesystem quietly refusing to behave the way a vault guide assumes. The sibling case is filename case, where a vault that works on one machine corrupts itself on another — documented in files.md or Files.md? The Case-Sensitivity Trap That Corrupts a Note Vault Silently.

If the question is which directory an app chooses once it can open one, that is Where Do Your Images and Attachments Actually Live?. If it is whether a tool's local-first claims hold up as a category, that audit is Local-First in 2026: The Seven Ideals, Audited. And the export half of point five is measured in How Well Do Note Apps Actually Let You Leave?.

Frequently Asked Questions

These are the questions people actually type when the folder advice fails on their phone — drawn from Stack Overflow titles and Google's own Android Help community. Each answer is pinned to an API level and quoted from the platform documentation or from the Android Open Source Project source, with the relevant directory or constant named.

Why can't apps access the Android/data folder?

Because Android 11 closed it. "You can no longer use the ACTION_OPEN_DOCUMENT_TREE or the ACTION_OPEN_DOCUMENT intent action to request that the user select individual files from" Android/data/ and Android/obb/ and all their subdirectories.2 Even an app holding all-files access is excluded, since those app-specific directories sit under Android/data/ on the volume.3

Can an app get access to the Download folder on Android 11 or later?

Not as a directory tree. Download is one of the three locations ACTION_OPEN_DOCUMENT_TREE cannot request on Android 11 (API level 30) and higher, alongside the internal storage root and the root of a reliable SD-card volume.1 A user can still select individual files from it through the system picker; what is unavailable is standing access to the directory itself.

How do I grant an app permission to a specific folder on Android?

The app sends an ACTION_OPEN_DOCUMENT_TREE intent and the system shows a directory picker; whatever you select becomes the grant.1 No manifest permission is involved — "because the user is involved in selecting the files or directories that your app can access, this mechanism doesn't require any system permissions."1 The grant covers that directory and its subdirectories, and nothing outside it.1

Does an ACTION_OPEN_DOCUMENT_TREE permission persist across reboots?

Only if the app asks. A plain grant "lasts until the user's device restarts."1 Calling takePersistableUriPermission() makes it survive reboots.5 Even then it ends if the document is moved or deleted,1 and the system prunes a package's oldest persisted grants once they exceed MAX_PERSISTED_URI_GRANTS, which is 512 in the current platform source.6

Will an app regain access to its folder after I uninstall and reinstall it?

Not to an app-specific directory — those files are removed with the app. Shared storage is the location designed for "user data that can or should be accessible to other apps and saved even if the user uninstalls your app."8 A reinstalled app also starts with no grants: it has to ask for the directory again, because the URI permissions belonged to the previous installation.

How do I write files to a publicly accessible documents folder under scoped storage?

Through the Storage Access Framework, using ACTION_CREATE_DOCUMENT for a new file or a tree grant for a directory the user picks.1 Google routes this case explicitly: "Documents and other files… Your app can access these files using the platform's Storage Access Framework."8 Hard-coded paths are the wrong tool — "the exact location of where your files can be saved might vary across devices."4

Why does Google Play reject apps that request MANAGE_EXTERNAL_STORAGE?

Because Play restricts it to a short list of app types — file managers, backup and restore, anti-virus, document management, on-device file search, disk and file encryption, and device-to-device migration.3 "Any File selection activity where the user manually selects individual files" is named an invalid use,10 and apps that "fail to meet policy requirements or do not submit a Permissions Declaration Form may be removed from Google Play."10


Your notes folder on Android is not a folder. It is a lease on a directory, signed by the person holding the phone — and the durable thing is not the lease but the plain text underneath it.


Notes stay on your own device with mnmnote.com — plain Markdown, no account, open in any editor.

Footnotes

  1. Android Developers. "Access documents and other files from shared storage." https://developer.android.com/training/data-storage/shared/documents-files — last updated 2026-08-13 UTC, accessed 2026-08-15. Source of the ACTION_OPEN_DOCUMENT_TREE restriction list, the API-21 availability note, the reboot-scoped grant, the move-or-delete invalidation, the tree-grant scoping rule, and the Kotlin samples reproduced above. 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23

  2. Android Developers. "Storage updates in Android 11." https://developer.android.com/about/versions/11/privacy/storage — last updated 2026-08-13 UTC, accessed 2026-08-15. Source of the Android/data/ and Android/obb/ file-selection restriction, the other-apps' app-specific directory rule, and the requestLegacyExternalStorage change. 2 3 4 5 6 7

  3. Android Developers. "Manage all files on a storage device." https://developer.android.com/training/data-storage/manage-all-files — last updated 2026-08-13 UTC, accessed 2026-08-15. Source of the seven eligible use cases, the Android/data/ exclusion for all-files holders, the privacy-friendly-APIs guidance, and the "This policy is in effect as of May 2021" date. 2 3 4 5 6 7 8 9

  4. Android Developers. "Data and file storage overview." https://developer.android.com/training/data-storage — last updated 2026-08-13 UTC, accessed 2026-08-15. Source of the purpose-over-location statement, the Android 10 scoped-storage default, the WRITE_EXTERNAL_STORAGE change, the MANAGE_EXTERNAL_STORAGE introduction, the privacy rationale, and the hard-coded-paths warning. 2 3 4 5 6 7

  5. Android Developers. ContentResolver API reference — takePersistableUriPermission() and getPersistedUriPermissions(). https://developer.android.com/reference/android/content/ContentResolver — accessed 2026-08-15. 2 3

  6. Android Open Source Project. services/core/java/com/android/server/uri/UriGrantsManagerService.java. https://android.googlesource.com/platform/frameworks/base/+/refs/heads/main/services/core/java/com/android/server/uri/UriGrantsManagerService.java — read 2026-08-15. MAX_PERSISTED_URI_GRANTS = 512 on main and on the android11-release through android16-release branches; the Android 8 and 9 value of 128 read from refs/tags/android-8.0.0_r1 and refs/tags/android-9.0.0_r1 in ActivityManagerService.java. The constant is not documented on developer.android.com. 2 3 4

  7. Android Developers. "Access media files from shared storage." https://developer.android.com/training/data-storage/shared/media — last updated 2026-08-13 UTC, accessed 2026-08-15. Source of the scanned-collection enumeration and the MediaStore.Files scoped-storage limitation. 2 3 4 5 6

  8. Android Developers. "Share and access files in shared storage." https://developer.android.com/training/data-storage/shared — last updated 2026-03-05 UTC, accessed 2026-08-15. Source of the media-versus-documents routing and the shared-storage purpose statement. 2 3 4 5

  9. Weissthaner, C. "Nextcloud Android file upload issue with Google." Nextcloud, published 2025-05-13, updated 2025-06-25. https://nextcloud.com/blog/nextcloud-android-file-upload-issue-google/ — accessed 2026-08-15. Cited for its timeline and its technical finding on the MediaStore API only. 2 3

  10. Google Play Console Help. "Use of All files access (MANAGE_EXTERNAL_STORAGE) permission." https://support.google.com/googleplay/android-developer/answer/10467955 — accessed 2026-08-15. The page carries no publication or last-updated date; its May 2021 effective date is taken from the developer documentation at 3. 2 3 4 5 6 7 8 9

  11. Android Developers. Behaviour-changes pages for Android 13, 14, 15, 16, and 17. https://developer.android.com/about/versions/13/behavior-changes-13 · /14/behavior-changes-14 · /14/behavior-changes-all · /15/behavior-changes-all · /16/behavior-changes-16 · /16/behavior-changes-all · /17/behavior-changes-17 · /17/behavior-changes-all — all eight accessed 2026-08-15, each stamped Last updated 2026-08-13 UTC. Source of the Selected Photos Access and MediaStore#getVersion() quotations. "Android 17 (API level 37)" appears verbatim on the Android 17 page, which describes the release as in beta. 2 3

  12. Murphy, M. (CommonsWare). "The Storage Access Framework: Counterpoints." commonsware.com, 2019-06-05. https://commonsware.com/blog/2019/06/05/storage-access-framework-counterpoints.html — accessed 2026-08-15. Every Murphy quotation here is taken from his own prose; the post also contains eleven block quotations from the article he is answering, including the "~25 to 50 times slower" benchmark, which is not his. 2 3 4 5 6 7

  13. Murphy, M. (CommonsWare). "Scoped Storage Stories: Problems with SAF." commonsware.com, 2019-12-01. https://commonsware.com/blog/2019/12/01/scoped-storage-stories-problems-saf.html — accessed 2026-08-15. 2 3