From dc010a01f1580de551c875455e0b2dbfe687437e Mon Sep 17 00:00:00 2001 From: Alisson Lopes Date: Fri, 3 Nov 2023 19:13:03 -0300 Subject: [PATCH] Window Test Support (#25) * Windows Test Support - Add helper methods to convert the unix absolute path to the Jimfs's supported Windows path * Windows Test Support - Bump Jimfs version * Windows Test Support - Implement helper methods to the needed paths * Windows Test Support - Implement helper methods to the needed paths and remove the unsupported (on Windows) newline character in the filename * Windows Test Support - Statically importing the helper methods * Windows Test Support - Statically importing the helper methods and changing the constant field names to good practices --- .../src/main/kotlin/core-config.gradle.kts | 2 +- .../configlib/ExampleConfigurationTests.java | 3 +- .../de/exlll/configlib/SerializersTest.java | 49 +++++++++---------- .../java/de/exlll/configlib/TestUtils.java | 25 +++++++++- .../ExampleConfigurationsSerialized.java | 16 +++--- .../configurations/ExampleInitializer.java | 18 +++---- .../ExampleConfigurationYamlTests.java | 9 ++-- .../configlib/YamlConfigurationStoreTest.java | 26 +++++----- .../configlib/YamlConfigurationsTest.java | 3 +- .../exlll/configlib/YamlFileWriterTest.java | 3 +- 10 files changed, 91 insertions(+), 63 deletions(-) diff --git a/buildSrc/src/main/kotlin/core-config.gradle.kts b/buildSrc/src/main/kotlin/core-config.gradle.kts index a6ef1ce..8cb562e 100644 --- a/buildSrc/src/main/kotlin/core-config.gradle.kts +++ b/buildSrc/src/main/kotlin/core-config.gradle.kts @@ -31,7 +31,7 @@ dependencies { testFixturesApi("org.mockito:mockito-inline:4.7.0") testFixturesApi("org.mockito:mockito-junit-jupiter:4.7.0") testFixturesApi("org.hamcrest:hamcrest-all:1.3") - testFixturesApi("com.google.jimfs:jimfs:1.2") + testFixturesApi("com.google.jimfs:jimfs:1.3.0") } publishing { diff --git a/configlib-core/src/test/java/de/exlll/configlib/ExampleConfigurationTests.java b/configlib-core/src/test/java/de/exlll/configlib/ExampleConfigurationTests.java index 0ccfb85..8c48b47 100644 --- a/configlib-core/src/test/java/de/exlll/configlib/ExampleConfigurationTests.java +++ b/configlib-core/src/test/java/de/exlll/configlib/ExampleConfigurationTests.java @@ -13,6 +13,7 @@ import java.nio.file.Files; import java.nio.file.Path; import java.util.Map; +import static de.exlll.configlib.TestUtils.createPlatformSpecificFilePath; import static de.exlll.configlib.configurations.ExampleConfigurationsSerialized.*; import static de.exlll.configlib.configurations.ExampleEqualityAsserter.*; import static org.junit.jupiter.api.Assertions.assertEquals; @@ -30,7 +31,7 @@ class ExampleConfigurationTests { .build(); private final FileSystem fs = Jimfs.newFileSystem(); - private final Path yamlFile = fs.getPath("/tmp/config.yml"); + private final Path yamlFile = fs.getPath(createPlatformSpecificFilePath("/tmp/config.yml")); @BeforeEach void setUp() throws IOException { diff --git a/configlib-core/src/test/java/de/exlll/configlib/SerializersTest.java b/configlib-core/src/test/java/de/exlll/configlib/SerializersTest.java index 85eed7c..9fffa84 100644 --- a/configlib-core/src/test/java/de/exlll/configlib/SerializersTest.java +++ b/configlib-core/src/test/java/de/exlll/configlib/SerializersTest.java @@ -29,6 +29,11 @@ import static org.hamcrest.MatcherAssert.assertThat; import static org.hamcrest.Matchers.*; class SerializersTest { + + private final String TMP_CONFIG_PATH = createPlatformSpecificFilePath("/tmp/config.yml"); + private final String TMP_WITH_UNDERSCORE_PATH = createPlatformSpecificFilePath("/tmp/with_underscore.yml"); + private final String TMP_PATH = createPlatformSpecificFilePath("/tmp"); + @Test void booleanSerializer() { Serializer serializer = new Serializers.BooleanSerializer(); @@ -461,42 +466,34 @@ class SerializersTest { void fileSerializer() { Serializer serializer = new Serializers.FileSerializer(); - String path1 = "/tmp/config.yml"; - String path2 = "/tmp/with \n new \n lines.yml"; - String path3 = "/tmp"; + File file1 = new File(TMP_CONFIG_PATH); + File file2 = new File(TMP_WITH_UNDERSCORE_PATH); + File file3 = new File(TMP_PATH); - File file1 = new File(path1); - File file2 = new File(path2); - File file3 = new File(path3); + assertThat(serializer.serialize(file1), is(TMP_CONFIG_PATH)); + assertThat(serializer.serialize(file2), is(TMP_WITH_UNDERSCORE_PATH)); + assertThat(serializer.serialize(file3), is(TMP_PATH)); - assertThat(serializer.serialize(file1), is(path1)); - assertThat(serializer.serialize(file2), is(path2)); - assertThat(serializer.serialize(file3), is(path3)); - - assertThat(serializer.deserialize(path1), is(file1)); - assertThat(serializer.deserialize(path2), is(file2)); - assertThat(serializer.deserialize(path3), is(file3)); + assertThat(serializer.deserialize(TMP_CONFIG_PATH), is(file1)); + assertThat(serializer.deserialize(TMP_WITH_UNDERSCORE_PATH), is(file2)); + assertThat(serializer.deserialize(TMP_PATH), is(file3)); } @Test void pathSerializer() { Serializer serializer = new Serializers.PathSerializer(); - String path1 = "/tmp/config.yml"; - String path2 = "/tmp/with \n new \n lines.yml"; - String path3 = "/tmp"; - - Path file1 = Path.of(path1); - Path file2 = Path.of(path2); - Path file3 = Path.of(path3); + Path file1 = Path.of(TMP_CONFIG_PATH); + Path file2 = Path.of(TMP_WITH_UNDERSCORE_PATH); + Path file3 = Path.of(TMP_PATH); - assertThat(serializer.serialize(file1), is(path1)); - assertThat(serializer.serialize(file2), is(path2)); - assertThat(serializer.serialize(file3), is(path3)); + assertThat(serializer.serialize(file1), is(TMP_CONFIG_PATH)); + assertThat(serializer.serialize(file2), is(TMP_WITH_UNDERSCORE_PATH)); + assertThat(serializer.serialize(file3), is(TMP_PATH)); - assertThat(serializer.deserialize(path1), is(file1)); - assertThat(serializer.deserialize(path2), is(file2)); - assertThat(serializer.deserialize(path3), is(file3)); + assertThat(serializer.deserialize(TMP_CONFIG_PATH), is(file1)); + assertThat(serializer.deserialize(TMP_WITH_UNDERSCORE_PATH), is(file2)); + assertThat(serializer.deserialize(TMP_PATH), is(file3)); } @Test diff --git a/configlib-core/src/testFixtures/java/de/exlll/configlib/TestUtils.java b/configlib-core/src/testFixtures/java/de/exlll/configlib/TestUtils.java index 08c280b..77f7cad 100644 --- a/configlib-core/src/testFixtures/java/de/exlll/configlib/TestUtils.java +++ b/configlib-core/src/testFixtures/java/de/exlll/configlib/TestUtils.java @@ -4,6 +4,7 @@ import org.junit.jupiter.api.Assertions; import org.junit.jupiter.api.function.Executable; import java.awt.Point; +import java.io.File; import java.io.IOException; import java.lang.reflect.Field; import java.math.BigInteger; @@ -289,4 +290,26 @@ public final class TestUtils { Field field = getField(type, fieldName); return new ConfigurationElements.FieldElement(field); } -} + + /* + There were absolute path errors when trying to pass the unit tests + on different platforms like Windows. Currently, Jimfs(1.3.0) lacks support + for both absolutes paths and relative paths on Windows, see: + - https://github.com/google/jimfs/issues/69 + - https://github.com/google/jimfs/blob/master/jimfs/src/main/java/com/google/common/jimfs/WindowsPathType.java + + So, in order to run unit tests on Windows. We have to translate the current + path declarations to fulfill the non-unix system's needs. + */ + public static String createPlatformSpecificFilePath(String path) { + final String platform = System.getProperty("os.name"); + + if (!platform.contains("Windows")) return path; + + return String.format("C:%s", path.replace("/", File.separator)); + } + + public static List createListOfPlatformSpecificFilePaths(String... paths) { + return Stream.of(paths).map(TestUtils::createPlatformSpecificFilePath).toList(); + } +} \ No newline at end of file diff --git a/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleConfigurationsSerialized.java b/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleConfigurationsSerialized.java index c51c703..f8880ea 100644 --- a/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleConfigurationsSerialized.java +++ b/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleConfigurationsSerialized.java @@ -121,8 +121,8 @@ public final class ExampleConfigurationsSerialized { entry("a1_localDateTime", "2000-01-01T00:00"), entry("a1_instant", "0000-01-01T00:00:00Z"), entry("a1_uuid", "d50f3bdd-ac66-4b74-a01f-4617b24d68c0"), - entry("a1_file", "/tmp"), - entry("a1_path", "/tmp"), + entry("a1_file", createPlatformSpecificFilePath("/tmp")), + entry("a1_path", createPlatformSpecificFilePath("/tmp")), entry("a1_url", "https://example.com"), entry("a1_uri", "https://example.com"), entry("a1_Enm", "A"), @@ -146,8 +146,8 @@ public final class ExampleConfigurationsSerialized { entry("a1_listLocalDateTime", List.of("2000-01-01T00:00", "2000-01-02T00:00", "2000-01-03T00:00")), entry("a1_listInstant", List.of("0000-01-01T00:00:00Z", "0001-01-01T00:00:00Z", "-1000000000-01-01T00:00:00Z")), entry("a1_listUuid", List.of("d50f3bdd-ac66-4b74-a01f-4617b24d68c0", "d50f3bdd-ac66-4b74-a01f-4617b24d68c1", "d50f3bdd-ac66-4b74-a01f-4617b24d68c2")), - entry("a1_listFile", List.of("/tmp", "/tmp/config.yml", "/tmp/with \n new \n lines.yml")), - entry("a1_listPath", List.of("/tmp", "/tmp/config.yml", "/tmp/with \n new \n lines.yml")), + entry("a1_listFile", createListOfPlatformSpecificFilePaths("/tmp", "/tmp/config.yml", "/tmp/with_underscore.yml")), + entry("a1_listPath", createListOfPlatformSpecificFilePaths("/tmp", "/tmp/config.yml", "/tmp/with_underscore.yml")), entry("a1_listUrl", List.of("https://example.com", "https://example.com?query=yes", "https://example.com?query=yes#fragment=true")), entry("a1_listUri", List.of("https://example.com", "https://example.com?query=yes", "https://example.com?query=yes#fragment=true")), entry("a1_listEnm", List.of("A", "B", "C")), @@ -299,8 +299,8 @@ public final class ExampleConfigurationsSerialized { entry("a2_localDateTime", "2000-01-02T00:00"), entry("a2_instant", "0001-01-01T00:00:00Z"), entry("a2_uuid", "d50f3bdd-ac66-4b74-a01f-4617b24d68c1"), - entry("a2_file", "/tmp/config.yml"), - entry("a2_path", "/tmp/config.yml"), + entry("a2_file", createPlatformSpecificFilePath("/tmp/config.yml")), + entry("a2_path", createPlatformSpecificFilePath("/tmp/config.yml")), entry("a2_url", "https://example.com?query=yes"), entry("a2_uri", "https://example.com?query=yes"), entry("a2_Enm", "B"), @@ -324,8 +324,8 @@ public final class ExampleConfigurationsSerialized { entry("a2_listLocalDateTime", List.of("2000-01-02T00:00", "2000-01-03T00:00", "2000-01-04T00:00")), entry("a2_listInstant", List.of("0001-01-01T00:00:00Z", "-1000000000-01-01T00:00:00Z", "+1000000000-12-31T23:59:59.999999999Z")), entry("a2_listUuid", List.of("d50f3bdd-ac66-4b74-a01f-4617b24d68c1", "d50f3bdd-ac66-4b74-a01f-4617b24d68c2", "d50f3bdd-ac66-4b74-a01f-4617b24d68c3")), - entry("a2_listFile", List.of("/tmp/config.yml", "/tmp/with \n new \n lines.yml", "with \n new \n lines.yml")), - entry("a2_listPath", List.of("/tmp/config.yml", "/tmp/with \n new \n lines.yml", "with \n new \n lines.yml")), + entry("a2_listFile", createListOfPlatformSpecificFilePaths("/tmp/config.yml", "/tmp/with_underscore.yml", "with_underscore.yml")), + entry("a2_listPath", createListOfPlatformSpecificFilePaths("/tmp/config.yml", "/tmp/with_underscore.yml", "with_underscore.yml")), entry("a2_listUrl", List.of("https://example.com?query=yes", "https://example.com?query=yes#fragment=true", "https://example.com#fragment=true")), entry("a2_listUri", List.of("https://example.com?query=yes", "https://example.com?query=yes#fragment=true", "https://example.com#fragment=true")), entry("a2_listEnm", List.of("B", "C", "D")), diff --git a/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleInitializer.java b/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleInitializer.java index d509c99..1365776 100644 --- a/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleInitializer.java +++ b/configlib-core/src/testFixtures/java/de/exlll/configlib/configurations/ExampleInitializer.java @@ -59,15 +59,15 @@ public final class ExampleInitializer { private static final UUID UUID_4 = UUID.fromString("d50f3bdd-ac66-4b74-a01f-4617b24d68c3"); private static final UUID UUID_5 = UUID.fromString("d50f3bdd-ac66-4b74-a01f-4617b24d68c4"); - private static final File FILE_1 = new File("/tmp"); - private static final File FILE_2 = new File("/tmp/config.yml"); - private static final File FILE_3 = new File("/tmp/with \n new \n lines.yml"); - private static final File FILE_4 = new File("with \n new \n lines.yml"); - - private static final Path PATH_1 = Path.of("/tmp"); - private static final Path PATH_2 = Path.of("/tmp/config.yml"); - private static final Path PATH_3 = Path.of("/tmp/with \n new \n lines.yml"); - private static final Path PATH_4 = Path.of("with \n new \n lines.yml"); + private static final File FILE_1 = new File(createPlatformSpecificFilePath("/tmp")); + private static final File FILE_2 = new File(createPlatformSpecificFilePath("/tmp/config.yml")); + private static final File FILE_3 = new File(createPlatformSpecificFilePath("/tmp/with_underscore.yml")); + private static final File FILE_4 = new File(createPlatformSpecificFilePath("with_underscore.yml")); + + private static final Path PATH_1 = Path.of(createPlatformSpecificFilePath("/tmp")); + private static final Path PATH_2 = Path.of(createPlatformSpecificFilePath("/tmp/config.yml")); + private static final Path PATH_3 = Path.of(createPlatformSpecificFilePath("/tmp/with_underscore.yml")); + private static final Path PATH_4 = Path.of(createPlatformSpecificFilePath("with_underscore.yml")); private static final URL URL_1 = createUrl("https://example.com"); private static final URL URL_2 = createUrl("https://example.com?query=yes"); diff --git a/configlib-yaml/src/test/java/de/exlll/configlib/ExampleConfigurationYamlTests.java b/configlib-yaml/src/test/java/de/exlll/configlib/ExampleConfigurationYamlTests.java index 7a9cc36..b9cc517 100644 --- a/configlib-yaml/src/test/java/de/exlll/configlib/ExampleConfigurationYamlTests.java +++ b/configlib-yaml/src/test/java/de/exlll/configlib/ExampleConfigurationYamlTests.java @@ -15,11 +15,12 @@ import java.nio.file.FileSystem; import java.nio.file.Files; import java.nio.file.Path; +import static de.exlll.configlib.TestUtils.*; import static de.exlll.configlib.configurations.ExampleEqualityAsserter.*; final class ExampleConfigurationYamlTests { private final FileSystem fs = Jimfs.newFileSystem(); - private final Path yamlFile = fs.getPath("/tmp/config.yml"); + private final Path yamlFile = fs.getPath(createPlatformSpecificFilePath("/tmp/config.yml")); @BeforeEach void setUp() throws IOException { @@ -34,7 +35,7 @@ final class ExampleConfigurationYamlTests { @Test void yamlStoreSavesAndLoadsExampleConfigurationA2() { var properties = YamlConfigurationProperties.newBuilder() - .addSerializer(Point.class, TestUtils.POINT_SERIALIZER) + .addSerializer(Point.class, POINT_SERIALIZER) .build(); var store = new YamlConfigurationStore<>(ExampleConfigurationA2.class, properties); ExampleConfigurationA2 cfg1 = ExampleInitializer.newExampleConfigurationA2(); @@ -46,7 +47,7 @@ final class ExampleConfigurationYamlTests { @Test void yamlStoreSavesAndLoadsExampleConfigurationNullsWithNullCollectionElements1() { var properties = YamlConfigurationProperties.newBuilder() - .addSerializer(Point.class, TestUtils.POINT_SERIALIZER) + .addSerializer(Point.class, POINT_SERIALIZER) .outputNulls(true) .inputNulls(true) .build(); @@ -61,7 +62,7 @@ final class ExampleConfigurationYamlTests { @Test void yamlStoreSavesAndLoadsExampleConfigurationNullsWithoutNullCollectionElements1() { var properties = YamlConfigurationProperties.newBuilder() - .addSerializer(Point.class, TestUtils.POINT_SERIALIZER) + .addSerializer(Point.class, POINT_SERIALIZER) .build(); var store = new YamlConfigurationStore<>(ExampleConfigurationNulls.class, properties); ExampleConfigurationNulls cfg1 = ExampleInitializer diff --git a/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationStoreTest.java b/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationStoreTest.java index e8aa6bb..1c374b3 100644 --- a/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationStoreTest.java +++ b/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationStoreTest.java @@ -16,7 +16,11 @@ import static org.junit.jupiter.api.Assertions.*; class YamlConfigurationStoreTest { private final FileSystem fs = Jimfs.newFileSystem(); - private final Path yamlFile = fs.getPath("/tmp/config.yml"); + + private final String yamlFilePath = createPlatformSpecificFilePath("/tmp/config.yml"); + private final Path yamlFile = fs.getPath(yamlFilePath); + + private final String abcFilePath = createPlatformSpecificFilePath("/a/b/c.yml"); @BeforeEach void setUp() throws IOException { @@ -93,7 +97,7 @@ class YamlConfigurationStoreTest { # The # Footer\ """; - assertEquals(expected, TestUtils.readFile(yamlFile)); + assertEquals(expected, readFile(yamlFile)); } @Test @@ -120,7 +124,7 @@ class YamlConfigurationStoreTest { # The # Footer\ """; - assertEquals(expected, TestUtils.readFile(yamlFile)); + assertEquals(expected, readFile(yamlFile)); } @Configuration @@ -208,7 +212,7 @@ class YamlConfigurationStoreTest { assertThrowsConfigurationException( () -> store.load(yamlFile), - "The configuration file at /tmp/config.yml does not contain valid YAML." + String.format("The configuration file at %s does not contain valid YAML.", yamlFilePath) ); } @@ -220,7 +224,7 @@ class YamlConfigurationStoreTest { assertThrowsConfigurationException( () -> store.load(yamlFile), - "The configuration file at /tmp/config.yml is empty or only contains null." + String.format("The configuration file at %s is empty or only contains null.", yamlFilePath) ); } @@ -232,9 +236,9 @@ class YamlConfigurationStoreTest { assertThrowsConfigurationException( () -> store.load(yamlFile), - "The contents of the YAML file at /tmp/config.yml do not represent a " + + String.format("The contents of the YAML file at %s do not represent a " + "configuration. A valid configuration file contains a YAML map but instead a " + - "'class java.lang.String' was found." + "'class java.lang.String' was found.", yamlFilePath) ); } @@ -246,7 +250,7 @@ class YamlConfigurationStoreTest { @Test void saveConfigurationWithInvalidTargetType() { YamlConfigurationProperties properties = YamlConfigurationProperties.newBuilder() - .addSerializer(Point.class, TestUtils.POINT_IDENTITY_SERIALIZER) + .addSerializer(Point.class, POINT_IDENTITY_SERIALIZER) .build(); YamlConfigurationStore store = new YamlConfigurationStore<>(D.class, properties); @@ -261,7 +265,7 @@ class YamlConfigurationStoreTest { void saveCreatesParentDirectoriesIfPropertyTrue() { YamlConfigurationStore store = newDefaultStore(A.class); - Path file = fs.getPath("/a/b/c.yml"); + Path file = fs.getPath(abcFilePath); store.save(new A(), file); assertTrue(Files.exists(file.getParent())); @@ -275,10 +279,10 @@ class YamlConfigurationStoreTest { .build(); YamlConfigurationStore store = new YamlConfigurationStore<>(A.class, properties); - Path file = fs.getPath("/a/b/c.yml"); + Path file = fs.getPath(abcFilePath); assertThrowsRuntimeException( () -> store.save(new A(), file), - "java.nio.file.NoSuchFileException: /a/b/c.yml" + String.format("java.nio.file.NoSuchFileException: %s", abcFilePath) ); } diff --git a/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationsTest.java b/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationsTest.java index 93d6a39..9dd81ce 100644 --- a/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationsTest.java +++ b/configlib-yaml/src/test/java/de/exlll/configlib/YamlConfigurationsTest.java @@ -10,12 +10,13 @@ import java.nio.file.FileSystem; import java.nio.file.Files; import java.nio.file.Path; +import static de.exlll.configlib.TestUtils.createPlatformSpecificFilePath; import static org.junit.jupiter.api.Assertions.assertEquals; class YamlConfigurationsTest { private static final FieldFilter includeI = field -> field.getName().equals("i"); private final FileSystem fs = Jimfs.newFileSystem(); - private final Path yamlFile = fs.getPath("/tmp/config.yml"); + private final Path yamlFile = fs.getPath(createPlatformSpecificFilePath("/tmp/config.yml")); @BeforeEach void setUp() throws IOException { diff --git a/configlib-yaml/src/test/java/de/exlll/configlib/YamlFileWriterTest.java b/configlib-yaml/src/test/java/de/exlll/configlib/YamlFileWriterTest.java index 75c9fcc..3883905 100644 --- a/configlib-yaml/src/test/java/de/exlll/configlib/YamlFileWriterTest.java +++ b/configlib-yaml/src/test/java/de/exlll/configlib/YamlFileWriterTest.java @@ -16,12 +16,13 @@ import java.util.Map; import java.util.Queue; import java.util.function.Consumer; +import static de.exlll.configlib.TestUtils.createPlatformSpecificFilePath; import static org.junit.jupiter.api.Assertions.assertEquals; @SuppressWarnings("unused") class YamlFileWriterTest { private final FileSystem fs = Jimfs.newFileSystem(); - private final Path yamlFile = fs.getPath("/tmp/config.yml"); + private final Path yamlFile = fs.getPath(createPlatformSpecificFilePath("/tmp/config.yml")); @BeforeEach void setUp() throws IOException {