Java 为什么我的untar不包含最后的字节

Java 为什么我的untar不包含最后的字节,java,zip,gzip,tar,Java,Zip,Gzip,Tar,我已经编写了一个rest资源,它提供一个.tar.gz文件。工作正常。我尝试过请求它,保存数据,解包(使用tar xzvf[filename]),然后得到了正确的数据 然而,我正试图使用java.util.zip.GZIPInputStream和org.apache.tools.tar.TarInputStream解压和解压我在JUnit测试中服务的.tar.gz,以验证它是否自动工作。这是我单元测试中的代码,删除了一些详细信息: HttpResponse response = <

我已经编写了一个rest资源,它提供一个
.tar.gz
文件。工作正常。我尝试过请求它,保存数据,解包(使用
tar xzvf[filename]
),然后得到了正确的数据

然而,我正试图使用
java.util.zip.GZIPInputStream
org.apache.tools.tar.TarInputStream
解压和解压我在JUnit测试中服务的
.tar.gz
,以验证它是否自动工作。这是我单元测试中的代码,删除了一些详细信息:

    HttpResponse response = <make request code here>
    byte[] receivedBytes = FileHelper.copyInputStreamToByteArray(response.getEntity().getContent(), true);

    GZIPInputStream gzipInputStream = new GZIPInputStream(new ByteArrayInputStream(receivedBytes));
    TarInputStream tarInputStream = new TarInputStream(gzipInputStream);
    TarEntry tarEntry = tarInputStream.getNextEntry();
    ByteArrayOutputStream byteArrayOutputStream = null;
    System.out.println("Record size: " + tarInputStream.getRecordSize());
    while (tarEntry != null) // It only goes in here once
    {
        byteArrayOutputStream = new ByteArrayOutputStream();
        tarInputStream.copyEntryContents(byteArrayOutputStream);
        tarEntry = tarInputStream.getNextEntry();
    }
    byteArrayOutputStream.flush();
    byteArrayOutputStream.close();
    byte[] archivedBytes = byteArrayOutputStream.toByteArray();
    byte[] actualBytes = <get actual bytes>
    Assert.assertArrayEquals(actualBytes, archivedBytes);
numRead
是100,但是看看缓冲区,只有前512字节是非零的。也许我不应该使用该方法从
TarInputStream
中获取数据


如果有人知道它应该如何工作,我将非常感谢任何建议或帮助。

您可以指定创建tar存档时要使用的输出块大小。因此,归档文件的大小将是块大小的倍数。由于存档大小通常不适合整个数据块,因此最后一个数据块将添加零,以使其具有正确的大小。

您可以指定创建tar存档时要使用的输出块大小。因此,归档文件的大小将是块大小的倍数。由于存档大小通常不适合整个数据块,因此最后一个数据块中会添加0,以使其大小正确。

结果表明,我原来的问题是错的,错误出现在资源代码中。我在写TarOutputStream时没有关闭它。我猜当从服务器手动请求时,这并没有引起任何问题,可能是因为该条目是通过连接或其他方式关闭的,但是当从单元测试请求时,工作方式不同。。。尽管我必须承认,成为这样的人没有多大意义:P

查看下面我编写的代码片段,我遗漏了第3行

1: tarOutputStream.putNextEntry(tarEntry);
2: tarOutputStream.write(fileRawBytes);
3: tarOutputStream.closeEntry();
4: tarOutputStream.close();

我甚至不知道TarOutputStream上有“closeEntry”这样的东西。。。我现在知道了!:P

原来我的原始问题是错的,错误在资源代码中。我在写TarOutputStream时没有关闭它。我猜当从服务器手动请求时,这并没有引起任何问题,可能是因为该条目是通过连接或其他方式关闭的,但是当从单元测试请求时,工作方式不同。。。尽管我必须承认,成为这样的人没有多大意义:P

查看下面我编写的代码片段,我遗漏了第3行

1: tarOutputStream.putNextEntry(tarEntry);
2: tarOutputStream.write(fileRawBytes);
3: tarOutputStream.closeEntry();
4: tarOutputStream.close();

我甚至不知道TarOutputStream上有“closeEntry”这样的东西。。。我现在知道了!:P

如果我得到的数据数组是块大小的倍数(在本例中为512),并且最后一位被填充,那么这是有意义的。但实际上,数组是原始数据的长度(不是块大小的倍数),从最后一个完整块到数组结束都有零。这有意义吗?因此,数组不太长,零的填充。这是正确的长度(数据的预期长度),但错过了最后一个数据(全零)。如果我得到的数据数组是块大小的倍数(在本例中为512),并且最后一位被填充,这是有意义的。但实际上,数组是原始数据的长度(不是块大小的倍数),从最后一个完整块到数组结束都有零。这有意义吗?因此,数组不太长,零的填充。它是正确的长度(数据的预期长度),但错过了最后一个数据(全部为零)。