3 ways to Copy a File From One Directory to Another in Java

Even though Java is considered one of the best feature-rich programming language, until Java 7, It didn't have any method to copy a file from one directory to another directory. It did have the java.io.File class, which provides a method to check if a file exists or not and methods for several other file operations but it lacks support for copying file from one folder to another. It was easy to write your own routine to copy a file using FileInputStream or FileChannel, most developers prefer to use Apache Commons IO library; which is not a bad idea at all. Even Joshua Bloch (author of several Java classes in JDK, including Java Collection Framework) advise using libraries instead of reinventing wheels in must read Effective Java book. The Apache Commons IO library provides a class called FileUtils, which contains several file utility methods including one for copying file from one directory to another.

Btw, Java has addressed the issue of a simpler, powerful, and feature rich file and directory library by introducing NIO 2.0 in JDK. In short, from Java 7 onwards, you don't need to include Apache Commons IO just for copying file, you can instead use Files.copy(source, destination) method to copy files from one folder to another in Java. This method takes Path of source and destination folder and copies the file (see Core Java Volume 2 - Advanced features to learn more about other useful files and directories related features added as part of NIO 2.0)

You can still use Apache commons IO for any missing functionality, but I doubt you would need it post JDK 7 new File IO package. Also if you are running on Java 5 or 6, you can take a look at FileChannel because it operates on buffer level, you can use it to copy large files from one location to another very efficiently.




3 examples to copy a file from one location to another

In this article, I'll show you three simple ways to copy a file from one folder to another using Java program. These three approaches shows how to copy a file in Java 6 or lower version by using fundamental FileInputStream class without using a third-party library, Apache Commons IO way for those who like to use a third-party library, and finally the standard way of copying file post-Java 7 using NIO 2.0 classes.


1) Copy file using FileInputStream

This is the simplest solution to copy a file in Java and the best part of this code is that it will work in all version of Java, starting from Java 1 to Java 8.  This method expects to source and destination file, which also encapsulate the path in the file system and then uses FileInputStream to read from source file and FileOutputStream to write to the destination file using a buffer (byte array) of 1KB.

private static void copy(File src, File dest) throws IOException {
        InputStream is = null;
        OutputStream os = null;
        try {
            is = new FileInputStream(src);
            os = new FileOutputStream(dest);

            // buffer size 1K
            byte[] buf = new byte[1024];

            int bytesRead;
            while ((bytesRead = is.read(buf)) > 0) {
                os.write(buf, 0, bytesRead);
            }
        } finally {
            is.close();
            os.close();
        }
    }

You can use this Java code to copy a file from one location to other in your project but I would strongly suggest using either Apache Commons IO or Files.copy() if you are running in Java 7. This example is good for learning but you need more feature rich method for production use


2) Using Apache Commons IO (Only for Java 5 and 6)

Even though the previous example of copying file was simple to code it wasn't thought to handle all scenarios and may fail while copying large files. This is where third -party library score well because they get the huge testing exposure with their large user base around the world and across the domain.

public static void copyFileUsingApache(File from, File to) throws IOException{
        FileUtils.copyFile(from, to);
    }

Another advantage of using a third-party library like Apache Commons and Google Guava is that you need to write less code. Here we are just calling the FileUtils.copyFile() method, nothing else. Though, you may notice we have encapsulated the call to a third-party library in our own method. This is to protect every part of our code from directly dependent on this library. Tomorrow if you decide to use Google Guava or switch to Java 7 standard way of copying, you only need change this method and not every part of your code which using this method for copying.


3) Files.copy() from (Java 7 onwards)

This is the best and right way to copy a file from one folder to another in Java. The only caveat is that this requires JRE 7 and compiled using Java 1.7 compiler.

 public static void copyFile(String from, String to) throws IOException{
        Path src = Paths.get(from);
        Path dest = Paths.get(to);
        Files.copy(src.toFile(), dest.toFile());
    }

It's as simple as the second example but it doesn't require any third-party library in your classpath.  You can further specify copy options to replace existing file or use standard options. You can further read, The Well-Grounded Java Developer: Vital techniques of Java 7 and polyglot programming, it nicely covers important features of NIO 2.0 e.g. copying and moving files, watching a directory for change and other essential features for Java programmers.

How to Copy a File From One folder to Another in Java



Java Program to copy files from one directory to another

Here is our complete Java program to copy a file or a set of files from one directory to another.  It includes all three examples for copying a file in Java.

import java.io.File;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.io.OutputStream;
import java.nio.file.Path;
import java.nio.file.Paths;

import org.apache.commons.io.FileUtils;

import com.google.common.io.Files;

/**
 * How to write to a file using try-with-resource statement in Java.
 *
 * @author java67
 */

public class FileCopyDemo {

    public static void main(String args[]) throws IOException {
             
        File from = new File("programming.txt");
        File to = new File("java6");
       
        System.out.println("Copying file in same location using FileInputStream");
        copy(from, to);
       
        System.out.println("Copying file into another location using Java 7 Files.copy");
        copyFile("programming.txt", "java7.txt");
       
        System.out.println("Copying file to another directory using Apache commons IO");
        copyFileUsingApache(from, new File("apache.txt"));
       
       
    }

    /**
     * This method copy a file from one directory to another. src is path of the
     * file to copy dest is the path where to copy the file.
     *
     * @param src
     * @param dest
     * @throws IOException
     */
    public static void copy(File src, File dest) throws IOException {
        InputStream is = null;
        OutputStream os = null;
        try {
            is = new FileInputStream(src);
            os = new FileOutputStream(dest);

            // buffer size 1K
            byte[] buf = new byte[1024];

            int bytesRead;
            while ((bytesRead = is.read(buf)) > 0) {
                os.write(buf, 0, bytesRead);
            }
        } finally {
            is.close();
            os.close();
        }
    }
   
   
    /**
     * Java 7 way to copy a file from one location to another
     * @param from
     * @param to
     * @throws IOException
     */
    public static void copyFile(String from, String to) throws IOException{
        Path src = Paths.get(from);
        Path dest = Paths.get(to);
        Files.copy(src.toFile(), dest.toFile());
    }
   
    /**
     * Apache commons IO FileUtils provides easy way to copy files in Java
     * It internally uses File
     * @param from
     * @param string
     * @throws IOException
     */
    public static void copyFileUsingApache(File from, File to) throws IOException{
        FileUtils.copyFile(from, to);
    }
}

Output :
Copying file in the same location using FileInputStream
Copying file into another location using Java 7 Files.copy
Copying file to another directory using Apache commons IO

You can see that all three approach works for a small file but it's the full regression test. You can try more by copying large file and checking which example copy the file faster.

Here is nice summary of Java NIO.2 Features for copying and moving files and watching directories:

3 ways to Copy a File From One Directory to Another in Java


Important Points about Copying File in Java

1) The Files.copy() should be a standard way to copy a file from one folder to another, if you are working in Java 7 and Java 8.


2) For copying file in Java 6, you can either write your own code using FileChannel, FileInputStream or can leverage Apache Commons IO. I would suggest use Apache Commons IO as its tried and tested library and its best practice to use the library instead of writing your own code. Of course, this rule doesn't apply to a rockstar developers who are keen to optimize everything as per their application need.


3) Use FileChannel to write a file copy method in Java 5 and 6. It's very efficient and should be used to copy large files from one place to other.


4) If source file does not exist or you have made spelling mistake our first solution will throw :

the first solution will throw :
Exception in thread "main" java.lang.NullPointerException
at dto.FileCopyDemo.copy(FileCopyDemo.java:65)
at dto.FileCopyDemo.main(FileCopyDemo.java:31)


Second solution will throw :
Exception in thread "main" java.nio.file.NoSuchFileException: programming1.txt
at sun.nio.fs.WindowsException.translateToIOException(Unknown Source)
at sun.nio.fs.WindowsException.rethrowAsIOException(Unknown Source)
at sun.nio.fs.WindowsException.rethrowAsIOException(Unknown Source)
at sun.nio.fs.WindowsFileCopy.copy(Unknown Source)
at sun.nio.fs.WindowsFileSystemProvider.copy(Unknown Source)
at java.nio.file.Files.copy(Unknown Source)
at dto.FileCopyDemo.copyFile(FileCopyDemo.java:80)
at dto.FileCopyDemo.main(FileCopyDemo.java:34)


and third solution will throw :
Exception in thread "main" java.io.FileNotFoundException: Source 'programming1.txt' does not exist
at org.apache.commons.io.FileUtils.copyFile(FileUtils.java:1074)
at org.apache.commons.io.FileUtils.copyFile(FileUtils.java:1038)
at dto.FileCopyDemo.copyFileUsingApache(FileCopyDemo.java:91)
at dto.FileCopyDemo.main(FileCopyDemo.java:37)


4) If the target file already exists then the first solution will silently overwrite it.

Second solution will throw below exception:

Exception in thread "main" java.nio.file.FileAlreadyExistsException: target\java7.txt
at sun.nio.fs.WindowsFileCopy.copy(Unknown Source)
at sun.nio.fs.WindowsFileSystemProvider.copy(Unknown Source)
at java.nio.file.Files.copy(Unknown Source)
at dto.FileCopyDemo.copyFile(FileCopyDemo.java:80)
at dto.FileCopyDemo.main(FileCopyDemo.java:34)

you can take care of it by supplying the file copy option REPLACE_EXISTING in Java 7 thought.


5) If target path doesn't exist e.g. you want to copy in a directory which is not yet created then our first solution will throw

Exception in thread "main" java.lang.NullPointerException
at dto.FileCopyDemo.copy(Helloworld.java:66)

Second solution will throw :
Exception in thread "main" java.nio.file.NoSuchFileException: programming.txt -> targetrr\java7.txt
at sun.nio.fs.WindowsException.translateToIOException(Unknown Source)
at sun.nio.fs.WindowsException.rethrowAsIOException(Unknown Source)
at sun.nio.fs.WindowsFileCopy.copy(Unknown Source)
at sun.nio.fs.WindowsFileSystemProvider.copy(Unknown Source)
at java.nio.file.Files.copy(Unknown Source)
at dto.FileCopyDemo.copyFile(FileCopyDemo.java:80)
at dto.FileCopyDemo.main(FileCopyDemo.java:34)


and the third solution will create the directory and copy the file there, one of the best solutions.


That's all about how to copy a file in Java. If you are on Java 7, use Files.copy() method, its simple and easy and you don't need to include any third party library, but if you are running on Java 6, then you can either use Apache commons IO library and FileUtils.copy() method or you can write your own routing using FileChannel to copy file from one folder to another in Java.


Other Java File and directory tutorials you may like
  • How to delete a directory with files in Java? (example)
  • How to copy a non-empty directory in Java? (example)
  • How to create file and directory in Java? (solution)
  • How to read a ZIP archive in Java? (solution)
  • 2 ways to read a text file in Java? (example)
  • How to append text to existing file in Java (solution)
  • How to write to file using BufferedWriter in Java? (example)

References:
JDK 7 Files documentation
Apache Commons IO FileUtils documentation


No comments:

Post a Comment