Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Download a database file to the app directory

i want to update the sqlite database of the app when clicking on a button using the DownloadManager.

But it says "java.lang.IllegalArgumentException: Not a file URI: /data/user/0/com.example.laudien.listviewtesting/databases/Employees"

What do i make wrong? Do i need a permission for that? The internet permission is already in the manifest.

Here is the code of my updateDb() method:

private void updateDb() {
    DownloadManager downloadManager = (DownloadManager) getSystemService(DOWNLOAD_SERVICE); // create download manager
    DownloadFinishedReceiver receiver = new DownloadFinishedReceiver(); // create broadcast receiver
    registerReceiver(receiver, new IntentFilter(DownloadManager.ACTION_DOWNLOAD_COMPLETE)); // register the receiver
    DownloadManager.Request request = new DownloadManager.Request(Uri.parse(DATABASE_URL)); // create a download request

    // delete database file if it exists
    File databaseFile = new File(getDatabasePath(DATABASE_NAME).getAbsolutePath());
    if(databaseFile.exists())
        databaseFile.delete();

    request//.setNotificationVisibility(DownloadManager.Request.VISIBILITY_HIDDEN) // not visible
        .setAllowedNetworkTypes(DownloadManager.Request.NETWORK_WIFI) // only via wifi
        .setDestinationUri(Uri.parse("file:" + getDatabasePath(DATABASE_NAME).getAbsolutePath())); // set path in app dir
    downloadManager.enqueue(request); // enqueue the download request
}
like image 292
P1xelfehler Avatar asked Oct 07 '16 06:10

P1xelfehler


2 Answers

Your path /data/user/0/com.example.laudien.listviewtesting is private internal memory of your app. You obtained it using getFilesDir(). Other apps have no access. Including the download manager. Use external memory given by getExternalStorageDirectory() instead.

like image 157
greenapps Avatar answered Sep 19 '22 10:09

greenapps


For anyone who wants to download sensitive files to app's private folders, I have to say that download manager doesn't have access to these folders inside internal storage. But the solution is moving the downloaded file in broadcast receiver. For example putting such line in BroadcastReceiver:

String destinationFileName = "test.mp4";
String filePath = cursor.getString(cursor.getColumnIndex(DownloadManager.COLUMN_LOCAL_URI));
copyFile(Uri.parse(filePath).getPath(), context.getFilesDir() + "/" + destinationFileName);

and copyFile is a method like this:

private void copyFile(String inFileName, String outFileName) throws IOException {

    InputStream myInput = new FileInputStream(inFileName);

    OutputStream myOutput = new FileOutputStream(outFileName);

    // Transfer bytes from the input file to the output file
    byte[] myBuffer = new byte[1024];
    int length;
    while ((length = myInput.read(myBuffer)) > 0)
        myOutput.write(myBuffer, 0, length);

    // Close the streams
    myOutput.flush();
    myOutput.close();
    myInput.close();
}
like image 41
Ehsan Avatar answered Sep 21 '22 10:09

Ehsan