2013-06-07 3 views
5

Я столкнулся с проблемой unusal. Я создаю инструмент, который планируется запустить каждые 5 минут. Он подберет zip-файлы из определенного каталога и извлечет файлы (в зависимости от имени файла) в пункт назначения. Я использую zipentry, чтобы получить каждое имя файла в zip-файле, а затем извлечение по мере необходимости, после чего я возвращаю их (ZIP-файлы, как только закончу все файлы в zip-файле) в конкретный каталог, а затем удалю zip-файл. Но иногда (не всегда) zip-файлы не удаляются. Потому что я использую fileutils.forcedelete(). Я получаю исключение: не может удалить файл. Поэтому я изменил код на использование fileutils.forcedeleteonexit(), но некоторые файлы остались в источнике.Не удается удалить zip-файл после распаковки?

Вот пример моего кода:

sourceFile=new file(zipfile); 
zipFile = new ZipFile(sourceFile); 
zEnum = (Enumeration<ZipEntry>) zipFile.entries(); 
for (int a = 0; a < zipFile.size(); a++) 
{ 
    ZipEntry zE = zEnum.nextElement(); 
    //Function uses zip4j for extracting. No streams used. 
    extract(String sourceZipFile, String fileNameToExtract, String outputFolder); 
} 
//I tried it with finally either 
zipFile.close(); 

//Using fileutils to copy. No streams used. 
copyFile(sourceFile, backup); 

FileUtils.forceDeleteOnExit(sourceFile); 

Там нет потоков, используемых, но я получаю блокировку файлов иногда (не всегда). Что, кажется, ошибка здесь? Это проблема с zip4j, которая вызывает проблему или что-то еще? Я использую zip4j 1.3.1.

+3

Что OS? Windows имеет печально известные проблемы с файловыми дескрипторами и удалениями ... – fge

+0

@fge: Windows.tried в моем локальном и на сервере (Windows Server 2008 R2) –

+0

@fge Я не могу сказать, сколько раз Windows сообщила мне «файл в используйте "при попытке удалить архив после извлечения его данных, но это, безусловно, было больше, чем я могу рассчитывать на обе руки. Является ли это ошибкой программ, которые не закрывают свои файлы вручную, или Windows сохраняет определенные файлы даже после закрытия программ? – JAB

ответ

0

Использование apache-commons IO's FileDeleteStrategy. Что-то вроде:

FileDeleteStrategy.FORCE.delete(file); 

Update:

Это должно быть так, как IO обрабатывается в приложении. Я написал простой код, который копирует zip-файл во временный почтовый индекс, дефлирует временный почтовый индекс и через несколько секунд удаляет его. Здесь вы найдете:

public class ZipTest { 

private static String dirPath = "/home/ubuntuuser/Desktop/"; 

public static void main(String[] args) throws Exception { 

    File myzip = new File(dirPath + "content.zip"); 
    String tempFileStr = dirPath + "content_temp.zip"; 
    File tempFile = new File(tempFileStr); 
    String unzipFolderStr = dirPath + "unzip"; 


    copyUsingChannels(myzip, tempFile); 

    // copyUsingStreams(myzip, tempFile); 

    unZip(tempFileStr, unzipFolderStr); 

    Thread.sleep(3000); 

    tempFile.delete(); 


} 

private static void copyUsingStreams(File myzip, File tempFile) 
     throws IOException, FileNotFoundException { 
    byte[] barray = new byte[1024]; 

    if (!tempFile.exists()) 
    { 
     tempFile.createNewFile(); 
    } 

    FileOutputStream fos = new FileOutputStream(tempFile); 
    FileInputStream fis = new FileInputStream(myzip); 

    int length = 0; 

    while ((length = fis.read(barray)) != -1) 
    { 
     fos.write(barray, 0, length); 
    } 

    fis.close(); 
    fos.close(); 
} 

public static void copyUsingChannels(final File srcFile, final File destFile) throws Exception 
{ 
    if (!destFile.exists()) 
    { 
     destFile.createNewFile(); 
    } 

    FileChannel source = new FileInputStream(srcFile).getChannel(); 
    FileChannel destination = new FileOutputStream(destFile).getChannel(); 

    source.transferTo(0, source.size(), destination); 

    source.close(); 
    destination.close(); 
} 

private static void unZip(String zipFile, String outputFolder) throws Exception { 

    byte[] buffer = new byte[1024]; 

    File folder = new File(outputFolder); 
    if (!folder.exists()) { 
     folder.mkdir(); 
    } 

    ZipInputStream zis = new ZipInputStream(new FileInputStream(zipFile)); 
    ZipEntry ze = zis.getNextEntry(); 

    while (ze != null) { 

     String fileName = ze.getName(); 

     File newFile = new File(outputFolder + File.separator + fileName); 

     System.out.println("file unzip : " + newFile.getAbsoluteFile()); 

     new File(newFile.getParent()).mkdirs(); 

     if (ze.isDirectory()) 
     { 
      newFile.mkdir(); 
      ze = zis.getNextEntry(); 
      continue; 
     } 

     FileOutputStream fos = new FileOutputStream(newFile); 

     int len; 
     while ((len = zis.read(buffer)) > 0) { 
      fos.write(buffer, 0, len); 
     } 

     fos.close(); 
     ze = zis.getNextEntry(); 
    } 

    zis.closeEntry(); 
    zis.close(); 
} 

} 
+0

та же проблема: не удалось удалить файл! –

+0

Можете ли вы подтвердить, что это не потому, что «copy» выше delete все еще продолжается? – Chris

+0

@ Chris.how я могу проверить that.if я могу тогда я могу код, чтобы удалить, как только копирование будет сделано. –

0

Я думаю, что ваша проблема связана с буферами файлов ОС, которые иногда не сбрасываются при попытке удалить файл. Вы пытались использовать sourceFile.deleteOnExit() вместо FileUtils.forceDeleteOnExit (sourceFile)? Также вы можете попробовать проверить sourceFile.canWrite перед удалением (может быть, это может поможет) Вы также можете попробовать использовать FileInputStream() перед удалением:

FileInputStream fi = new FileInputStream(sourceFile); 
fi.getFD().sync(); 
+0

, я попробовал с deleteOnExit() также тот же выпуск exit.i didnt использовать какой-либо FileInputStream, потому что я думал, что это может быть куприт –

+0

sourFile.canwrite всегда возвращает true !! –

Смежные вопросы