Home > other >  Unable to read an apk file from an internal directory
Unable to read an apk file from an internal directory

Time:03-02

I'm downloading an apk from s3 and storing it in a directory named SAMPLE_APK. When I try to execute the apk present in the directory, I get an error.

2022-03-01 15:44:20.773 21867-21867/com.test.digitaloceanspaces D/Main Activity -: File 
path  - /data/user/0/com.test.digitaloceanspaces/app_SAMPLE_APK/debug.apk
2022-03-01 15:44:20.774 21867-21867/com.test.digitaloceanspaces D/AndroidRuntime: 
Shutting down VM  

--------- beginning of crash
2022-03-01 15:44:20.779 21867-21867/com.test.digitaloceanspaces E/AndroidRuntime: FATAL 
EXCEPTION: main
    Process: com.test.digitaloceanspaces, PID: 21867
    java.lang.IllegalArgumentException: Failed to find configured root that contains 
/data/data/com.test.digitaloceanspaces/app_SAMPLE_APK/debug.apk
    at  
androidx.core.content.FileProvider$SimplePathStrategy
.getUriForFile(FileProvider.java:800)
    at androidx.core.content.FileProvider.getUriForFile(FileProvider.java:442)

But If I read the apk from filesDir, I'm able to execute it.

Below the two different directory structure

Unable to read the apk present in the file parameter of the callback method.

fun downloadLatestApk(callback: (File?, Exception?) -> Unit) {

//using a custom directory named sample apk
 val directoryName = "SAMPLE_APK"

    val directory = if (appContext.getDir(directoryName, Context.MODE_PRIVATE).exists()) 
    {
        Log.d("Local directory", "APK directory Already exists")
        appContext.getDir(directoryName, Context.MODE_PRIVATE)
    } else {
        Log.d("Local directory", "New Directory")
        File(appContext.filesDir, directoryName).apply {
            this.mkdir()
        }
    }

    val file = File(**directory**, "debug.apk")
    val listener = transferUtility.download(spacename, "debug.apk", file)

    listener.setTransferListener(object : TransferListener {

        override fun onStateChanged(id: Int, state: TransferState?) {
            if (state == TransferState.COMPLETED) {
                callback(file, null)
            }
        }
 }

Able to execute the apk present in the file parameter of the callback method. Here I'm reading the apk present in the filesDir.

fun downloadLatestAPk(callback: (File?, Exception?) -> Unit) {
//using files dir
val file = File(**appContext.filesDir**, "debug.apk")
    val listener = transferUtility.download(spacename, "debug.apk", file)

    listener.setTransferListener(object : TransferListener {

        override fun onStateChanged(id: Int, state: TransferState?) {
            if (state == TransferState.COMPLETED) {
                callback(file, null)
            }
        }
}

This happens only for apk. I'm able to read image files from either of the directories. Unable to fathom this behavior.

Folder structure - Folder Structure

The file provider has the following paths.

<paths>
<external-path
    name="external"
    path="." />

<external-files-path
    name="external_files"
    path="." />

<cache-path
    name="cache"
    path="." />

<external-cache-path
    name="external_cache"
    path="." />

<files-path
    name="files"
    path="." />
</paths>

File from the callback method is sent to the below method for execution.

private fun handleInstallation(file: File) {

    Log.d("Main Activity - ", "File path  - ${file.path}")

    val contentUri =
        FileProvider.getUriForFile(
            this,
            "com.test.digitaloceanspaces"   ".provider", file
        )

    val intent = Intent()
    intent.action = Intent.ACTION_VIEW
    intent.putExtra(Intent.EXTRA_NOT_UNKNOWN_SOURCE, true)
    intent.flags = Intent.FLAG_ACTIVITY_NEW_TASK or Intent.FLAG_GRANT_READ_URI_PERMISSION
    intent.setDataAndType(contentUri, "application/vnd.android.package-archive")
    startActivity(intent)
}

App crashes after printing the log statement. Any help is deeply appreciated.

CodePudding user response:

path - /data/user/0/com.test.digitaloceanspaces/app_SAMPLE_APK/debug.apk

That is a path not covered by FileProvider.

From getFilesDir() is covered by entry <files-path.

You could make it:

/data/user/0/com.test.digitaloceanspaces/files/app_SAMPLE_APK/debug.apk

Not covered by FileProvider: java.lang.IllegalArgumentException: Failed to find configured root that contains /data/data/com.test.digitaloceanspaces/app_SAMPLE_APK/debug.apk

Unable to read an apk file from an internal directory

No. Unable to use FileProvider for not allowed path.

  • Related