Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Copy file from the internal to the external storage in Android

My app (Android API 15) makes a picture and stores it in the internal memory's folder. Now, I want to copy this file to another folder inside of the external storage, e.g. /sdcard/myapp. I tried the following approaches:

Approach #1:

private void copyFile(File src, File dst) throws IOException {

    File from = new File(src.getPath());
    File to = new File(dst.getPath());
    from.renameTo(to);
}

Approach #2:

private void copyFile(File src, File dst) throws IOException {

    FileChannel inChannel = null;
    FileChannel outChannel = null;

    try {
        inChannel = new FileInputStream(src).getChannel();
        outChannel = new FileOutputStream(dst).getChannel();
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    }

    try {
        inChannel.transferTo(0, inChannel.size(), outChannel);
    } finally {
        if (inChannel != null)
            inChannel.close();
        if (outChannel != null)
            outChannel.close();
    }
}

Approach #3:

private void copyFile(File src, File dst) throws IOException {

    FileInputStream inStream = new FileInputStream(src);

    if (!dst.exists()) {
        dst.mkdir();
    }

    if (!dst.canWrite()) {
        System.out.print("CAN'T WRITE");
        return;
    }

    FileOutputStream outStream = new FileOutputStream(dst);
    FileChannel inChannel = inStream.getChannel();
    FileChannel outChannel = outStream.getChannel();
    inChannel.transferTo(0, inChannel.size(), outChannel);
    inStream.close();
    outStream.close();
}

None of these methods doesn't solve my task. In checked a number of related topics, and the only suggestion I found is to verify the persistence of

<uses-permission android:name="android.permission.WRITE_EXTERNAL_STORAGE" />

in AndroidManifest.xml and it does persist.

The approach #1 finishes the execution, but no folder and files are copied.

In the approach #2, the app fails with the exception java.lang.NullPointerException at outChannel = new FileOutputStream(dst).getChannel();, but the object dst is not a null.

In the approach #3, I decided to verify if the destination object exists and it creates a folder if needed, but when I check if I can write, the check returns false.

I tried a couple of additional approaches, which succeeded to create an empty folder, but no files are really copied.

Since this is my very first step towards Android, I feel I miss some small thing. Please, point me, how to copy a file from one folder to another folder in Android, including file moving from internal to external memory.

like image 678
Mike Avatar asked Jun 27 '15 22:06

Mike


People also ask

Why can't I move files to my SD card android?

Check If the SD card Has Read or Write Error One of the reasons why you can't move files to SD card is a read and write error. One way to check if this error is the reason behind you being unable to move files to SD card is to set your phone camera to store the images and videos taken from it directly to the SD card.

What is internal and external storage in Android?

In short, Internal Storage is for apps to save sensitive data to which other apps and users cannot access. However, Primary External Storage is part of built-in storage which can be accessed (for read-write) by the user and other apps but with permissions.


1 Answers

I solved my issue. The problem was in the destination path, in the original code:

File dst = new File(dstPath);

the variable dstPath had the full destination path, including the name of the file, which is wrong. Here is the correct code fragment:

String dstPath = Environment.getExternalStorageDirectory() + File.separator + "myApp" + File.separator;
File dst = new File(dstPath);

exportFile(pictureFile, dst);

private File exportFile(File src, File dst) throws IOException {

    //if folder does not exist
    if (!dst.exists()) {
        if (!dst.mkdir()) {
            return null;
        }
    }

    String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
    File expFile = new File(dst.getPath() + File.separator + "IMG_" + timeStamp + ".jpg");
    FileChannel inChannel = null;
    FileChannel outChannel = null;

    try {
        inChannel = new FileInputStream(src).getChannel();
        outChannel = new FileOutputStream(expFile).getChannel();
    } catch (FileNotFoundException e) {
        e.printStackTrace();
    }

    try {
        inChannel.transferTo(0, inChannel.size(), outChannel);
    } finally {
        if (inChannel != null)
            inChannel.close();
        if (outChannel != null)
            outChannel.close();
    }

    return expFile;
}

Thanks for the tips.

like image 108
Mike Avatar answered Oct 28 '22 05:10

Mike