diff --git a/common/src/main/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReader.java b/common/src/main/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReader.java index b205c7e48052942ce401c52565c628857383977b..8f060cb8fa68e7045e788920dc9d5e6364fed2c1 100644 --- a/common/src/main/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReader.java +++ b/common/src/main/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReader.java @@ -25,6 +25,7 @@ package de.ozgcloud.eingang.common.zip; import java.io.File; import java.io.FileInputStream; +import java.io.FileNotFoundException; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; @@ -42,6 +43,7 @@ import java.util.zip.ZipInputStream; import org.springframework.util.MimeTypeUtils; import de.ozgcloud.eingang.common.errorhandling.TechnicalException; +import de.ozgcloud.eingang.common.formdata.DeleteOnCloseInputStream; import de.ozgcloud.eingang.common.formdata.IncomingFile; import lombok.Getter; import lombok.extern.log4j.Log4j2; @@ -212,10 +214,27 @@ public class ZipAttachmentReader { .build(); } + @Deprecated + public InputStream getSourceZipAsStream() { + try { + return new DeleteOnCloseInputStream(sourceZipFile); + } catch (FileNotFoundException e) { + throw new TechnicalException("Original ZIP was deleted", e); + } + } + public File getSourceZip() { return sourceZipFile; } + public long getSourceFileSize() { + try { + return Files.size(sourceZipFile.toPath()); + } catch (IOException e) { + throw new TechnicalException("Cannot get size of source ZIP.", e); + } + } + String getContentType(String name) { Objects.requireNonNull(name); return Objects.requireNonNullElse(URLConnection.guessContentTypeFromName(name), MimeTypeUtils.APPLICATION_OCTET_STREAM_VALUE); diff --git a/common/src/test/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReaderTest.java b/common/src/test/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReaderTest.java index a8bdbe27d084c75abd689628a79e46350c91766b..8cd2ad76c5b602b4b4e9096211afca5621c8569b 100644 --- a/common/src/test/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReaderTest.java +++ b/common/src/test/java/de/ozgcloud/eingang/common/zip/ZipAttachmentReaderTest.java @@ -33,7 +33,6 @@ import java.nio.file.Files; import java.nio.file.Path; import java.util.List; import java.util.function.Predicate; -import java.util.stream.Stream; import java.util.zip.ZipException; import java.util.zip.ZipInputStream; @@ -47,7 +46,6 @@ import org.mockito.Spy; import org.springframework.util.MimeTypeUtils; import de.ozgcloud.common.test.TestUtils; -import de.ozgcloud.eingang.common.formdata.DeleteOnCloseInputStream; import de.ozgcloud.eingang.common.formdata.IncomingFile; import lombok.SneakyThrows; @@ -75,11 +73,20 @@ class ZipAttachmentReaderTest { @SneakyThrows private void verifySourceFileSavedInTmpDirectory() { - try (Stream<Path> paths = Files.find(Path.of(getTmpDirectoryPath()), 1, - ((path, basicFileAttributes) -> path.getFileName().toString().startsWith(ZipAttachmentReader.SOURCE_ZIP_PREFIX)))) { - List<Path> foundFiles = paths.toList(); - assertThat(foundFiles).hasSize(1); - } + List<Path> foundFiles = Files.find(Path.of(getTmpDirectoryPath()), 1, + ((path, basicFileAttributes) -> path.getFileName().toString().startsWith(ZipAttachmentReader.SOURCE_ZIP_PREFIX))) + .toList(); + assertThat(foundFiles).hasSize(1).first(); + } + + @Test + @DisplayName("should return readable input stream for source zip file") + void shouldReturnSourceStream() { + var expectedContent = TestUtils.loadFile(ZIP_1_FILE_NAME); + + var sourceZipAsStream = createZipAttachment(ZIP_1_FILE_NAME).getSourceZipAsStream(); + + assertThat(sourceZipAsStream).hasSameContentAs(expectedContent); } @Test @@ -128,7 +135,7 @@ class ZipAttachmentReaderTest { var attachmentContentList = new ZipAttachmentReader().readContent(loadZip(ZIP_1_FILE_NAME)); assertThat(attachmentContentList).hasSize(1); - var contentEntry = attachmentContentList.getFirst(); + var contentEntry = attachmentContentList.get(0); assertThat(contentEntry.getName()).isEqualTo(content_file_0_name); assertThat(contentEntry.getSize()).isEqualTo(content_file_0_size); assertThat(contentEntry.getContentStream()).hasSameContentAs(TestUtils.loadFile(content_file_0_name)); @@ -162,7 +169,6 @@ class ZipAttachmentReaderTest { entry.getContentStreamForFinalRead().close(); } - @SneakyThrows @Test @DisplayName("should return readable input stream for source zip if cannot extract content") void shouldReturnSourceStreamByError() { @@ -171,7 +177,7 @@ class ZipAttachmentReaderTest { assertThrows(ReadZipException.class, attachment::readContent); - assertThat(new DeleteOnCloseInputStream(attachment.getSourceZip())).hasSameContentAs(new ByteArrayInputStream(attachmentContent)); + assertThat(attachment.getSourceZipAsStream()).hasSameContentAs(new ByteArrayInputStream(attachmentContent)); } @Test @@ -204,35 +210,30 @@ class ZipAttachmentReaderTest { private static final String ZIP_BOMB_WITH_MANY_FILES = "zipbombs/filewithmanyfiles.dat.zip"; @Test - @SneakyThrows void shouldFailOnExtremCompressionRatio() { - try (var zip = loadZip(ZIP_BOMB_WITH_BIG_NULL_FILE_CONTENT)) { + var zip = loadZip(ZIP_BOMB_WITH_BIG_NULL_FILE_CONTENT); - ReadZipException exception = assertThrows(ReadZipException.class, () -> reader.readContent(zip)); + ReadZipException exception = assertThrows(ReadZipException.class, () -> reader.readContent(zip)); - assertThat(exception.getMessage()).contains("Ratio between compressed and uncompressed data is highly suspicious"); - } + assertThat(exception.getMessage()).contains("Ratio between compressed and uncompressed data is highly suspicious"); } @Test @SneakyThrows void shouldFailOnTotalExtractedSize() { - try (var zip = loadZip(ZIP_1_FILE_NAME)) { - reader.readContent(zip); + var zip = loadZip(ZIP_1_FILE_NAME); + reader.readContent(zip); - verify(reader).checkTotalExtractedSize(157); - } + verify(reader).checkTotalExtractedSize(157); } @Test - @SneakyThrows void shouldFailOnTotalZipEntries() { - try (var zip = loadZip(ZIP_BOMB_WITH_MANY_FILES)) { + var zip = loadZip(ZIP_BOMB_WITH_MANY_FILES); - ReadZipException exception = assertThrows(ReadZipException.class, () -> reader.readContent(zip)); + ReadZipException exception = assertThrows(ReadZipException.class, () -> reader.readContent(zip)); - assertThat(exception.getMessage()).contains("Total entries in zip file exceeded"); - } + assertThat(exception.getMessage()).contains("Total entries in zip file exceeded"); } } @@ -299,16 +300,12 @@ class ZipAttachmentReaderTest { @SneakyThrows private static void cleanupTempFiles() { - try (Stream<Path> paths = Files.walk(Path.of(TMP_DIRECTORY_PATH), 1)) { - paths.filter(hasNameSuffix).map(Path::toFile).forEach(File::delete); - } + Files.walk(Path.of(TMP_DIRECTORY_PATH), 1).filter(hasNameSuffix).map(Path::toFile).forEach(File::delete); } @SneakyThrows private static boolean noFilesWithSuffixInTempDirectory() { - try (Stream<Path> paths = Files.walk(Path.of(TMP_DIRECTORY_PATH), 1)) { - return paths.noneMatch(hasNameSuffix); - } + return Files.walk(Path.of(TMP_DIRECTORY_PATH), 1).noneMatch(hasNameSuffix); } @SneakyThrows @@ -320,4 +317,4 @@ class ZipAttachmentReaderTest { private static String getTmpDirectoryPath() { return TMP_DIRECTORY_PATH.endsWith("/") ? TMP_DIRECTORY_PATH.substring(0, TMP_DIRECTORY_PATH.length() - 1) : TMP_DIRECTORY_PATH; } -} +} \ No newline at end of file