Skip to content

Commit

Permalink
Added example how to write structures
Browse files Browse the repository at this point in the history
  • Loading branch information
marc-christian-schulze committed Nov 28, 2024
1 parent 3b5c94b commit 7d52f89
Show file tree
Hide file tree
Showing 2 changed files with 72 additions and 0 deletions.
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
package examples.zip;

import org.junit.Test;
import static org.junit.Assert.assertEquals;

import java.io.ByteArrayInputStream;
import java.io.IOException;
import java.nio.ByteBuffer;
import java.nio.ByteOrder;
import java.util.zip.CRC32;
import java.util.zip.Checksum;
import java.util.zip.ZipEntry;
import java.util.zip.ZipInputStream;

public class ZipFileWritingTest {

@Test
public void testWritingZipFile() throws IOException {
ByteBuffer buffer = ByteBuffer.allocate(4096);
buffer.order(ByteOrder.LITTLE_ENDIAN);

// our file content to store
byte[] fileData = "example file content".getBytes("UTF-8");

// compute the CRC32 checksum of the file content
Checksum checksum = new CRC32();
checksum.update(fileData, 0, fileData.length);
long crc32 = checksum.getValue();

// first we create and write the local file header
long positionOfLocalFileHeader = buffer.position();
LocalFileHeader fhFile = new LocalFileHeader();
fhFile.setSignature(ByteBuffer.wrap(new byte[]{ 0x50, 0x4b, 0x03, 0x04 }));
fhFile.setFileName("example.txt");
fhFile.setCompressedSizeInBytes(fileData.length);
fhFile.setUncompressedSizeInBytes(fileData.length);
fhFile.setCrc32OfUncompressedData(crc32);
fhFile.write(buffer);
// right after the local file header, the actual file content needs to be stored
buffer.put(fileData);

// now we need to create the central directory header
long positionOfFirstCentralDirectoryHeader = buffer.position();
CentralDirectoryFileHeader cdfh = new CentralDirectoryFileHeader();
cdfh.setSignature(ByteBuffer.wrap(new byte[]{ 0x50, 0x4b, 0x01, 0x02 }));
cdfh.setFileName("example.txt");
cdfh.setCrc32OfUncompressedData(crc32);
cdfh.setCompressedSizeInBytes(fileData.length);
cdfh.setUncompressedSizeInBytes(fileData.length);
cdfh.setRelativeOffsetOfLocalFileHeader(positionOfLocalFileHeader);
cdfh.write(buffer);

// finally, we need to write the closing end of central directory header
EndOfCentralDirectoryRecord eocdr = new EndOfCentralDirectoryRecord();
eocdr.setSignature(ByteBuffer.wrap(new byte[]{ 0x50, 0x4b, 0x05, 0x06 }));
eocdr.setOffsetOfStartOfCentralDirectory(positionOfFirstCentralDirectoryHeader);
eocdr.setNumberOfCentralDirectoryRecordsOnThisDisk(1);
eocdr.setTotalNumberOfCentralDirectoryRecords(1);
eocdr.write(buffer);

// now we read the ZIP file using Java on-board classes and verify
ZipInputStream zis = new ZipInputStream(new ByteArrayInputStream(buffer.array()));
ZipEntry fileEntry = zis.getNextEntry();
assertEquals("example.txt", fileEntry.getName());
byte[] fileContentRead = zis.readAllBytes();
assertEquals("example file content", new String(fileContentRead, "UTF-8"));
}
}
4 changes: 4 additions & 0 deletions examples/zip-file-format/src/test/resources/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
The `example.zip` file was created without compression using
```
zip -0 -r example.zip zip-content/
```

0 comments on commit 7d52f89

Please sign in to comment.