diff --git a/spring-boot-project/spring-boot-tools/spring-boot-loader/src/test/java/org/springframework/boot/loader/jar/JarFileWrapperTests.java b/spring-boot-project/spring-boot-tools/spring-boot-loader/src/test/java/org/springframework/boot/loader/jar/JarFileWrapperTests.java index aa7dd0be42..83482dbcd3 100644 --- a/spring-boot-project/spring-boot-tools/spring-boot-loader/src/test/java/org/springframework/boot/loader/jar/JarFileWrapperTests.java +++ b/spring-boot-project/spring-boot-tools/spring-boot-loader/src/test/java/org/springframework/boot/loader/jar/JarFileWrapperTests.java @@ -19,18 +19,25 @@ package org.springframework.boot.loader.jar; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; +import java.io.InputStream; import java.net.MalformedURLException; +import java.net.URL; +import java.security.Permission; +import java.util.EnumSet; +import java.util.Enumeration; +import java.util.Set; import java.util.jar.JarOutputStream; +import java.util.jar.Manifest; import java.util.zip.ZipEntry; import org.junit.jupiter.api.BeforeEach; import org.junit.jupiter.api.Test; import org.junit.jupiter.api.io.TempDir; +import org.springframework.boot.loader.jar.JarFileWrapperTests.SpyJarFile.Call; + import static org.assertj.core.api.Assertions.assertThat; import static org.assertj.core.api.Assertions.assertThatExceptionOfType; -import static org.mockito.Mockito.spy; -import static org.mockito.Mockito.verify; /** * Tests for {@link JarFileWrapper}. @@ -39,13 +46,13 @@ import static org.mockito.Mockito.verify; */ class JarFileWrapperTests { - private JarFile parent; + private SpyJarFile parent; private JarFileWrapper wrapper; @BeforeEach void setup(@TempDir File temp) throws IOException { - this.parent = spy(new JarFile(createTempJar(temp))); + this.parent = new SpyJarFile(createTempJar(temp)); this.wrapper = new JarFileWrapper(this.parent); } @@ -58,68 +65,68 @@ class JarFileWrapperTests { @Test void getUrlDelegatesToParent() throws MalformedURLException { this.wrapper.getUrl(); - verify(this.parent).getUrl(); + this.parent.verify(Call.GET_URL); } @Test void getTypeDelegatesToParent() { this.wrapper.getType(); - verify(this.parent).getType(); + this.parent.verify(Call.GET_TYPE); } @Test void getPermissionDelegatesToParent() { this.wrapper.getPermission(); - verify(this.parent).getPermission(); + this.parent.verify(Call.GET_PERMISSION); } @Test void getManifestDelegatesToParent() throws IOException { this.wrapper.getManifest(); - verify(this.parent).getManifest(); + this.parent.verify(Call.GET_MANIFEST); } @Test void entriesDelegatesToParent() { this.wrapper.entries(); - verify(this.parent).entries(); + this.parent.verify(Call.ENTRIES); } @Test void getJarEntryDelegatesToParent() { this.wrapper.getJarEntry("test"); - verify(this.parent).getJarEntry("test"); + this.parent.verify(Call.GET_JAR_ENTRY); } @Test void getEntryDelegatesToParent() { this.wrapper.getEntry("test"); - verify(this.parent).getEntry("test"); + this.parent.verify(Call.GET_ENTRY); } @Test void getInputStreamDelegatesToParent() throws IOException { this.wrapper.getInputStream(); - verify(this.parent).getInputStream(); + this.parent.verify(Call.GET_INPUT_STREAM); } @Test void getEntryInputStreamDelegatesToParent() throws IOException { ZipEntry entry = new ZipEntry("test"); this.wrapper.getInputStream(entry); - verify(this.parent).getInputStream(entry); + this.parent.verify(Call.GET_ENTRY_INPUT_STREAM); } @Test void getCommentDelegatesToParent() { this.wrapper.getComment(); - verify(this.parent).getComment(); + this.parent.verify(Call.GET_COMMENT); } @Test void sizeDelegatesToParent() { this.wrapper.size(); - verify(this.parent).size(); + this.parent.verify(Call.SIZE); } @Test @@ -137,4 +144,117 @@ class JarFileWrapperTests { .isThrownBy(() -> JarFileWrapper.class.getDeclaredMethod("close")); } + /** + * {@link JarFile} that we can spy (even on Java 11+) + */ + static class SpyJarFile extends JarFile { + + private final Set calls = EnumSet.noneOf(Call.class); + + SpyJarFile(File file) throws IOException { + super(file); + } + + @Override + Permission getPermission() { + mark(Call.GET_PERMISSION); + return super.getPermission(); + } + + @Override + public Manifest getManifest() throws IOException { + mark(Call.GET_MANIFEST); + return super.getManifest(); + } + + @Override + public Enumeration entries() { + mark(Call.ENTRIES); + return super.entries(); + } + + @Override + public JarEntry getJarEntry(String name) { + mark(Call.GET_JAR_ENTRY); + return super.getJarEntry(name); + } + + @Override + public ZipEntry getEntry(String name) { + mark(Call.GET_ENTRY); + return super.getEntry(name); + } + + @Override + InputStream getInputStream() throws IOException { + mark(Call.GET_INPUT_STREAM); + return super.getInputStream(); + } + + @Override + InputStream getInputStream(String name) throws IOException { + mark(Call.GET_ENTRY_INPUT_STREAM); + return super.getInputStream(name); + } + + @Override + public String getComment() { + mark(Call.GET_COMMENT); + return super.getComment(); + } + + @Override + public int size() { + mark(Call.SIZE); + return super.size(); + } + + @Override + public URL getUrl() throws MalformedURLException { + mark(Call.GET_URL); + return super.getUrl(); + } + + @Override + JarFileType getType() { + mark(Call.GET_TYPE); + return super.getType(); + } + + private void mark(Call call) { + this.calls.add(call); + } + + void verify(Call call) { + assertThat(call).matches(this.calls::contains); + } + + enum Call { + + GET_URL, + + GET_TYPE, + + GET_PERMISSION, + + GET_MANIFEST, + + ENTRIES, + + GET_JAR_ENTRY, + + GET_ENTRY, + + GET_INPUT_STREAM, + + GET_ENTRY_INPUT_STREAM, + + GET_COMMENT, + + SIZE + + } + + } + }