如何在Java中完全从内存中的对象(无文件)创建tar或tar.gz存档文件

问题描述:

如何在Java中创建tar或gzipped tar存档,但不支持File和实际文件?如何在Java中完全从内存中的对象(无文件)创建tar或tar.gz存档文件

我找到了commons-compress,但是这些示例和大多数文档都依赖于使用已存在的文件,这些文件可以被Java File对象引用。如果我不想使用File对象并想从byte[]构建我的tar档案,该怎么办?

TarArchiveEntry的唯一构造函数提供了一种方法来设置内容接受File并且没有内容的设置器。

documentation为TarArchiveEntry:

TarArchiveEntry(File file) 
    Construct an entry for a file. 
TarArchiveEntry(File file, String fileName) 
    Construct an entry for a file. 

使用commons-compress,它不是立即清除或文档中例举,但这里是你要它

//Get the content you want to lay down into a byte[] 
byte content[] = "I am some simple content that should be written".getBytes(); 

//Name your entry with the complete path relative to the base directory 
//of your archive. Any directories that don't exist (e.g. "testDir") will 
//be created for you 
TarArchiveEntry textFile = new TarArchiveEntry("testDir/hello.txt"); 

//Make sure to set the size of the entry. If you don't you will not be able 
//to write to it 
textFile.setSize(content.length); 


TarArchiveOutputStream gzOut = null; 
try { 

    /*In this case I chose to show how to lay down a gzipped archive. 
     You could just as easily remove the GZIPOutputStream to lay down a plain tar. 
     You also should be able to replace the FileOutputStream with 
     a ByteArrayOutputStream to lay nothing down on disk if you wanted 
     to do something else with your newly created archive 
    */ 
    gzOut = new TarArchiveOutputStream(
       new GZIPOutputStream(
       new BufferedOutputStream(
       new FileOutputStream("/tmp/mytest.tar.gz") 
      ))); 

    //When you put an ArchiveEntry into the archive output stream, 
    //it sets it as the current entry 
    gzOut.putArchiveEntry(textFile); 

    //The write command allows you to write bytes to the current entry 
    //on the output stream, which was set by the above command. 
    //It will not allow you to write any more than the size 
    //that you specified when you created the archive entry above 
    gzOut.write(content); 

    //You must close the current entry when you are done with it. 
    //If you are appending multiple archive entries, you only need 
    //to close the last one. The putArchiveEntry automatically closes 
    //the previous "current entry" if there was one 
    gzOut.closeArchiveEntry(); 

} catch (Exception ex) { 
    System.err.println("ERROR: " + ex.getMessage()); 
} finally { 
    if (gzOut != null) { 
     try { 
      gzOut.close(); 
     } catch (IOException e) { 
      e.printStackTrace(); 
     } 
    } 
} 
+0

要点如果可以的话,接受你的答案。 – 2015-01-09 21:05:28

+0

啊,好的。我对*还很缺乏经验。 – 2015-01-09 21:32:02