1

I'm trying to open a file from a URL, copy it to a temporary file, and then delete the temporary file when processing work is done. However, I am unable to delete the file. I have tried closing all streams, I have tried deleting with both deleteOnExit() method and the Delete() method. This is an excel file which I am working with. When I am not using an excel file, or more particularly the Workbook object as shown in my code below, the file deletes just fine. As soon as I pass my file to the workbookFactory.create() method, my file cannot be deleted by the code.

Here's the code below:

public class URLtoFileWriting {

/**
 * @param args the command line arguments
 * @throws java.io.IOException
 */

static File destinationFile;
public static void getFile() throws IOException {

    try {
        // TODO code application logic here

        URL fileURL = new URL("http://www.testURL.com/testfile.xlsx");
        URLtoFileWriting.destinationFile = File.createTempFile("remotefile",".xlsx");

        try {
            URLConnection URLconnection = fileURL.openConnection();
            InputStream inputStream = URLconnection.getInputStream();
            FileOutputStream fileoutputStream = new FileOutputStream(URLtoFileWriting.destinationFile);
            IOUtils.copy(inputStream, fileoutputStream);

            Workbook wb = WorkbookFactory.create(URLtoFileWriting.destinationFile);

            System.out.println(URLtoFileWriting.destinationFile.getAbsolutePath());
            inputStream.close();
            fileoutputStream.close();
            System.out.println("Deleted testWB?!" + URLtoFileWriting.destinationFile.delete());



        } catch (IOException ex) {
            Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
        } catch (InvalidFormatException ex) {
            Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
        }


    } catch (MalformedURLException ex) {
        Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
    }


}

}

All the imports I am using:

import java.io.File;
import java.io.FileOutputStream;
import java.io.IOException;
import java.io.InputStream;
import java.net.MalformedURLException;
import java.net.URL;
import java.net.URLConnection;
import java.util.logging.Level;
import java.util.logging.Logger;
import org.apache.commons.io.IOUtils;
import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
import org.apache.poi.ss.usermodel.Workbook;
import org.apache.poi.ss.usermodel.WorkbookFactory;

I suspect it has something to do with the workbookFactory.create() method, as deletion becomes impossible once I have passed the file to this method.

What am I doing wrong here?

UPDATE. I have come across a fix: You can pass the File to a FileInputStream, and then pass this stream to the WorkbookFactory.Create() method.

Updated code below to reflect this:

  import java.io.File;
  import java.io.FileInputStream;
  import java.io.FileOutputStream;
  import java.io.IOException;
  import java.io.InputStream;
  import java.net.MalformedURLException;
  import java.net.URL;
  import java.net.URLConnection;
  import java.util.logging.Level;
  import java.util.logging.Logger;
  import org.apache.commons.io.IOUtils;
  import org.apache.poi.openxml4j.exceptions.InvalidFormatException;
  import org.apache.poi.ss.usermodel.Workbook;
  import org.apache.poi.ss.usermodel.WorkbookFactory;


 public class URLtoFileWriting {

/**
 * @param args the command line arguments
 * @throws java.io.IOException
 */

static File destinationFile;
public static void getFile() throws IOException {

    try {
        // TODO code application logic here

        URL fileURL = new URL("http://www.testURL.com/testfile.xlsx");
        URLtoFileWriting.destinationFile = File.createTempFile("remotefile",".xlsx");

        try {
            URLConnection URLconnection = fileURL.openConnection();
            InputStream inputStream = URLconnection.getInputStream();
            FileOutputStream fileoutputStream = new FileOutputStream(URLtoFileWriting.destinationFile);
            IOUtils.copy(inputStream, fileoutputStream);

            FileInputStream FIS = new FileInputStream(URLtoFileWriting.destinationFile);
            Workbook wb = WorkbookFactory.create(FIS);
            FIS.close();
            inputStream.close();
            fileoutputStream.close();
            System.out.println(URLtoFileWriting.destinationFile);
            System.out.println(URLtoFileWriting.destinationFile.delete());



        } catch (IOException ex) {
            Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
        } catch (InvalidFormatException ex) {
            Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
        }


    } catch (MalformedURLException ex) {
        Logger.getLogger(URLtoFileWriting.class.getName()).log(Level.SEVERE, null, ex);
    }


}

}

I hope this helps.

4
  • Just guessing: close the streams before passing the file object to WorkbookFactory.create method. I assume the factory will create the needed input streams by itself, and you have an output stream blocking the input file
    – dimoniy
    Commented Apr 18, 2014 at 20:46
  • @dimoniy, I've just tried this. I am afraid it didn't work.
    – fuyawaka
    Commented Apr 18, 2014 at 20:51
  • I have found a work around. Apparently, you can pass the File to a FileInputStream, and then pass that FileInputStream to the WorkbookFactory.Create() method. I will update the code above to reflect this. Thanks for helping.
    – fuyawaka
    Commented Apr 18, 2014 at 21:42
  • I looked at your updated code. I gives me java.lang.IllegalArgumentException: Your InputStream was neither an OLE2 stream, nor an OOXML stream
    – Braj
    Commented Apr 18, 2014 at 21:51

1 Answer 1

1

Find the solution here Close Filehandle for Workbook (apache poi).

Use NPOIFSFileSystem#close() or OPCPackage#close().

For more info have a look at the overloaded constructors of WorkbookFactory class.

4
  • I wish I could upvote but I am not allowed yet. So I'll just say thank you for your help!
    – fuyawaka
    Commented Apr 18, 2014 at 21:46
  • No worries. I am here just to help you.
    – Braj
    Commented Apr 18, 2014 at 21:48
  • I looked at your updated code. I gives me java.lang.IllegalArgumentException: Your InputStream was neither an OLE2 stream, nor an OOXML stream
    – Braj
    Commented Apr 18, 2014 at 21:50
  • I've updated the code again. This time with the entire class. Try copy pasting that and see what happens. Edit: I've had this problem before as well, I had to import all the libraries for Apache poi.
    – fuyawaka
    Commented Apr 18, 2014 at 21:53

Not the answer you're looking for? Browse other questions tagged or ask your own question.