androidmediastore

How to write a JSON file to a specific location using the Media Store API in Android


Having invoked a directory selector on Android with:

val intent = Intent(Intent.ACTION_OPEN_DOCUMENT_TREE)
intent.addFlags(
     Intent.FLAG_GRANT_READ_URI_PERMISSION
             or Intent.FLAG_GRANT_WRITE_URI_PERMISSION
             or Intent.FLAG_GRANT_PERSISTABLE_URI_PERMISSION
             or Intent.FLAG_GRANT_PREFIX_URI_PERMISSION
)

activity?.startActivityForResult(intent, REQUEST_CODE_FOLDER_PERMISSION)

And having obtained the URI of said route in onActivityResult(), being the URI of the form (example in case of having chosen a folder named backup in the root of the external storage):

content://com.android.externalstorage.documents/tree/primary:backup

At this point, how do you write a file to that location? After researching various answers on how to write files using the Media Store API, all the examples I've seen use constants to refer to already existing media directories, but in my case I want to create a new document (which is a JSON file) in the directory chosen by the user.


Solution

  • Thanks to @CommonsWare for pointing me in the right direction:

    var outputStream: OutputStream? = null
    
    try {
        val uri = Uri.parse(path)
        val document = DocumentFile.fromTreeUri(context, uri)
        val file = document?.createFile(mimeType, filename)
            ?: throw Exception("Created file is null, cannot continue")
        val fileUri = file.uri
    
        val contentResolver = context.contentResolver
        outputStream = contentResolver.openOutputStream(fileUri)
    
        val bytes = content.toByteArray()
        outputStream?.write(bytes)
        outputStream?.flush()
    
    } catch (e: Exception) {
        // Handle error
    } finally {
        outputStream?.close()
    }