2010-01-14 9 views
1

J'ai du mal à essayer de goudronner certains fichiers en utilisant la bibliothèque de compression.Problème de goudron avec la compression d'apache commons

Code Mon est le suivant, et est pris des exemples wiki commons.compress:

private static File createTarFile(String[] filePaths, String saveAs) throws Exception{ 

    File tarFile = new File(saveAs); 
    OutputStream out = new FileOutputStream(tarFile); 

    TarArchiveOutputStream aos = (TarArchiveOutputStream) new ArchiveStreamFactory().createArchiveOutputStream("tar", out); 

    for(String filePath : filePaths){ 
     File file = new File(filePath); 
     TarArchiveEntry entry = new TarArchiveEntry(file); 
     entry.setSize(file.length()); 
     aos.putArchiveEntry(entry); 
     IOUtils.copy(new FileInputStream(file), aos); 
     aos.closeArchiveEntry(); 
    } 
    aos.finish(); 
    out.close(); 


    return tarFile; 
} 

Il n'y a pas d'erreur au cours du processus, mais lorsque je tente de décompresser le fichier, je me suis ce qui suit:

XXXX:XXXX /home/XXXX$ tar -xf typeCommandes.tar 
tar: Unexpected EOF in archive 
tar: Unexpected EOF in archive 
tar: Error is not recoverable: exiting now 

en outre, l'archive est slighty plus petite taille que le fichier d'origine, ce qui nest pas normal pour un goudron, donc il faire est un problème ...

-rw-r--r-- 1 XXXX nobody 12902400 Jan 14 17:11 typeCommandes.tar 
-rw-r--r-- 1 XXXX nobody 12901888 Jan 14 17:16 typeCommandes.csv 

Tout le monde peut me dire ce que je fais mal? Merci

Répondre

3

Vous ne fermez pas le TarArchiveOutputStream. Ajouter aos.close() après aos.finish()

+0

Oui qui était ... Merci –

1

Petite correction du code ci-dessus. Il ne ferme pas le flux d'entrée, alors que Apache lib suppose que le flux est géré par le client appelant. Voir le correctif ci-dessous (mettre ce code après la ligne 'aos.putArchiveEntry (entrée)):

FileInputStream fis = new FileInputStream(fileForPuttingIntoTar); 
IOUtils.copy(fis, aos); 
fis.close(); 
aos.closeArchiveEntry(); 
0

Voir aussi ma réponse here

import org.apache.commons.compress.archivers.ArchiveEntry; 
import org.apache.commons.compress.archivers.tar.TarArchiveEntry; 
import org.apache.commons.compress.archivers.tar.TarArchiveInputStream; 
import org.apache.commons.compress.archivers.tar.TarArchiveOutputStream; 

public class TarUpdater { 

     private static final int buffersize = 8048; 

     public static void updateFile(File tarFile, File[] flist) throws IOException { 
      // get a temp file 
      File tempFile = File.createTempFile(tarFile.getName(), null); 
      // delete it, otherwise you cannot rename your existing tar to it. 
      if (tempFile.exists()) { 
       tempFile.delete(); 
      } 

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

      boolean renameOk = tarFile.renameTo(tempFile); 
      if (!renameOk) { 
       throw new RuntimeException(
         "could not rename the file " + tarFile.getAbsolutePath() + " to " + tempFile.getAbsolutePath()); 
      } 
      byte[] buf = new byte[buffersize]; 

      TarArchiveInputStream tin = new TarArchiveInputStream(new FileInputStream(tempFile)); 

      OutputStream outputStream = new BufferedOutputStream(Files.newOutputStream(tarFile.toPath())); 
      TarArchiveOutputStream tos = new TarArchiveOutputStream(outputStream); 
      tos.setLongFileMode(TarArchiveOutputStream.LONGFILE_POSIX); 

      //read from previous version of tar file 
      ArchiveEntry entry = tin.getNextEntry(); 
      while (entry != null) {//previous file have entries 
       String name = entry.getName(); 
       boolean notInFiles = true; 
       for (File f : flist) { 
        if (f.getName().equals(name)) { 
         notInFiles = false; 
         break; 
        } 
       } 
       if (notInFiles) { 
        // Add TAR entry to output stream. 
        if (!entry.isDirectory()) { 
         tos.putArchiveEntry(new TarArchiveEntry(name)); 
         // Transfer bytes from the TAR file to the output file 
         int len; 
         while ((len = tin.read(buf)) > 0) { 
          tos.write(buf, 0, len); 
         } 
        } 
       } 
       entry = tin.getNextEntry(); 
      } 
      // Close the streams 
      tin.close();//finished reading existing entries 
      // Compress new files 

      for (int i = 0; i < flist.length; i++) { 
       if (flist[i].isDirectory()) { 
        continue; 
       } 
       InputStream fis = new FileInputStream(flist[i]); 
       TarArchiveEntry te = new TarArchiveEntry(flist[i],flist[i].getName()); 
       //te.setSize(flist[i].length()); 
       tos.setLongFileMode(TarArchiveOutputStream.LONGFILE_GNU); 
       tos.setBigNumberMode(2); 
       tos.putArchiveEntry(te); // Add TAR entry to output stream. 

       // Transfer bytes from the file to the TAR file 
       int count = 0; 
       while ((count = fis.read(buf, 0, buffersize)) != -1) { 
        tos.write(buf, 0, count); 
       } 
       tos.closeArchiveEntry(); 
       fis.close(); 
      } 
      // Complete the TAR file 
      tos.close(); 
      tempFile.delete(); 
     } 
    }