diff --git a/.drone.yml b/.drone.yml index e4c41bc..02147aa 100644 --- a/.drone.yml +++ b/.drone.yml @@ -1,12 +1,20 @@ kind: pipeline type: docker name: default - steps: - - name: test - image: maven:3.6-jdk-11 + - name: build + image: maven:3.8-openjdk-18-slim commands: - mvn clean install -DskipTests=true -Dmaven.javadoc.skip=true -B -V + when: + ref: + include: + - refs/head/master + - refs/head/feature/** + - refs/tags/** + - name: test + image: maven:3.8-openjdk-18-slim + commands: - mvn test -B when: branch: @@ -14,15 +22,15 @@ steps: - master - feature/* - name: deploy - image: maven:3.6-jdk-11 + image: maven:3.8-openjdk-18-slim environment: REPO_TOKEN: from_secret: repo-token commands: - mvn -s maven-settings.xml deploy -DskipTests=true - trigger: + when: branch: - master event: exclude: - - pull_request + - pull_request diff --git a/labyrinth-generator.iml b/labyrinth-generator.iml deleted file mode 100644 index 815f5ae..0000000 --- a/labyrinth-generator.iml +++ /dev/null @@ -1,27 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - \ No newline at end of file diff --git a/maven-settings.xml b/maven-settings.xml index adce7ab..18a15cb 100644 --- a/maven-settings.xml +++ b/maven-settings.xml @@ -1,12 +1,12 @@ - - - - repo.gittr.ch - ci - ${env.REPO_TOKEN} - - + + + + repo.gittr.ch + ci + ${env.REPO_TOKEN} + + diff --git a/pom.xml b/pom.xml index 468ec50..b89e9a3 100644 --- a/pom.xml +++ b/pom.xml @@ -1,124 +1,172 @@ - - 4.0.0 + + 4.0.0 - - ch.fritteli - fritteli-build-parent - 2.0.4 - + + ch.fritteli + fritteli-build-parent + 2.0.4 + - ch.fritteli.labyrinth - labyrinth-generator - 0.0.3-SNAPSHOT + ch.fritteli.labyrinth + labyrinth-generator + 0.0.3-SNAPSHOT + The Labyrinth generator, a library for generating Labyrinths in various output formats. + https://manuel.friedli.info/labyrinth.html - - 1.2.10 - 2.0.25 - 1.7.35 - + + 17 + 17 + 24.0.1 + 5.9.2 + 1.4.6 + 1.18.26 + 2.0.27 + 2.0.7 + 0.10.4 + - - - org.projectlombok - lombok - - - org.jetbrains - annotations - - - io.vavr - vavr - - - org.apache.pdfbox - pdfbox - ${pdfbox.version} - - - org.slf4j - slf4j-api - ${slf4j.version} - - - ch.qos.logback - logback-classic - ${logback.version} - - - org.junit.jupiter - junit-jupiter-api - - - - - - maven-assembly-plugin - - - - ch.fritteli.labyrinth.generator.Main - - - - jar-with-dependencies - - - - - make-assembly - package - - single - - - - - - - - scm:git:git://gittr.ch/java/labyrinth-generator.git - scm:git:ssh://git@gittr.ch/java/labyrinth-generator.git - https://gittr.ch/java/labyrinth-generator - HEAD - - - - repo.gittr.ch - gittr.ch - https://repo.gittr.ch/releases/ - - - repo.gittr.ch - gittr.ch - https://repo.gittr.ch/snapshots/ - - - - - repo.gittr.ch.releases - https://repo.gittr.ch/releases/ - - true - never - - - false - never - - - - repo.gittr.ch.snapshots - https://repo.gittr.ch/snapshots/ - - false - never - - - true - always - - - + + + Manuel Friedli + manuel + https://www.fritteli.ch/ + manuel@fritteli.ch + Europe/Zurich + + Project Lead + Software Architect + Software Engineer + + + + + + + org.projectlombok + lombok + + + org.jetbrains + annotations + + + io.vavr + vavr + + + org.apache.pdfbox + pdfbox + ${pdfbox.version} + + + org.slf4j + slf4j-api + ${slf4j.version} + + + ch.qos.logback + logback-classic + ${logback.version} + + + org.junit.jupiter + junit-jupiter-api + + + org.assertj + assertj-core + 3.24.2 + test + + + + + + maven-assembly-plugin + + + + ch.fritteli.labyrinth.generator.Main + + + + jar-with-dependencies + + + + + make-assembly + package + + single + + + + + + org.apache.maven.plugins + maven-source-plugin + + + attach-sources + verify + + jar-no-fork + + + + + + org.apache.maven.plugins + maven-site-plugin + 4.0.0-M6 + + + + + scm:git:https://gittr.ch/java/labyrinth-generator.git + scm:git:ssh://git@gittr.ch/java/labyrinth-generator.git + https://gittr.ch/java/labyrinth-generator + HEAD + + + + repo.gittr.ch + gittr.ch + https://repo.gittr.ch/releases/ + + + repo.gittr.ch + gittr.ch + https://repo.gittr.ch/snapshots/ + + + + + repo.gittr.ch.releases + https://repo.gittr.ch/releases/ + + true + never + + + false + never + + + + repo.gittr.ch.snapshots + https://repo.gittr.ch/snapshots/ + + false + never + + + true + always + + + diff --git a/src/main/java/ch/fritteli/labyrinth/generator/Main.java b/src/main/java/ch/fritteli/labyrinth/generator/Main.java index df3ebef..9c16e66 100644 --- a/src/main/java/ch/fritteli/labyrinth/generator/Main.java +++ b/src/main/java/ch/fritteli/labyrinth/generator/Main.java @@ -15,8 +15,8 @@ import java.nio.file.Paths; @Slf4j public class Main { public static void main(@NonNull final String[] args) { - int width = 100; - int height = 100; + final int width = 20; + final int height = 30; final Labyrinth labyrinth = new Labyrinth(width, height/*, 0*/); final TextRenderer textRenderer = TextRenderer.newInstance(); final HTMLRenderer htmlRenderer = HTMLRenderer.newInstance(); diff --git a/src/main/java/ch/fritteli/labyrinth/generator/renderer/pdf/Generator.java b/src/main/java/ch/fritteli/labyrinth/generator/renderer/pdf/Generator.java index 971fed2..d683241 100644 --- a/src/main/java/ch/fritteli/labyrinth/generator/renderer/pdf/Generator.java +++ b/src/main/java/ch/fritteli/labyrinth/generator/renderer/pdf/Generator.java @@ -33,14 +33,13 @@ class Generator { final PDDocument pdDocument = new PDDocument(); final PDDocumentInformation info = new PDDocumentInformation(); - info.setTitle("Labyrinth " + this.labyrinth.getWidth() + "x" + this.labyrinth.getHeight() + ", ID " + this.labyrinth.getRandomSeed()); + info.setTitle("Labyrinth %sx%s, ID %s".formatted(this.labyrinth.getWidth(), this.labyrinth.getHeight(), this.labyrinth.getRandomSeed())); pdDocument.setDocumentInformation(info); final PDPage puzzlePage = new PDPage(new PDRectangle(pageWidth, pageHeight)); final PDPage solutionPage = new PDPage(new PDRectangle(pageWidth, pageHeight)); pdDocument.addPage(puzzlePage); pdDocument.addPage(solutionPage); - try (final PDPageContentStream puzzlePageContentStream = new PDPageContentStream(pdDocument, puzzlePage); - final PDPageContentStream solutionPageContentStream = new PDPageContentStream(pdDocument, solutionPage)) { + try (final PDPageContentStream puzzlePageContentStream = new PDPageContentStream(pdDocument, puzzlePage); final PDPageContentStream solutionPageContentStream = new PDPageContentStream(pdDocument, solutionPage)) { setUpPageContentStream(puzzlePageContentStream); setUpPageContentStream(solutionPageContentStream); this.drawHorizontalLines(puzzlePageContentStream, solutionPageContentStream); @@ -250,21 +249,21 @@ class Generator { this.y = y; } - private float calcX(final int x) { - return x * PDFRenderer.SCALE + PDFRenderer.MARGIN; - } - - private float calcY(final int y) { - return (Generator.this.labyrinth.getHeight() - y) * PDFRenderer.SCALE + PDFRenderer.MARGIN; - } - public Coordinate withX(final int x) { return new Coordinate(calcX(x), this.y); } + private float calcX(final int x) { + return x * PDFRenderer.SCALE + PDFRenderer.MARGIN; + } + public Coordinate withY(final int y) { return new Coordinate(this.x, calcY(y)); } + + private float calcY(final int y) { + return (Generator.this.labyrinth.getHeight() - y) * PDFRenderer.SCALE + PDFRenderer.MARGIN; + } } @Value diff --git a/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthInputStream.java b/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthInputStream.java index 1d13101..cf619c8 100644 --- a/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthInputStream.java +++ b/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthInputStream.java @@ -1,5 +1,7 @@ package ch.fritteli.labyrinth.generator.serialization; +import ch.fritteli.labyrinth.generator.model.Labyrinth; +import ch.fritteli.labyrinth.generator.model.Tile; import lombok.NonNull; import java.io.ByteArrayInputStream; @@ -9,13 +11,11 @@ public class LabyrinthInputStream extends ByteArrayInputStream { super(buf); } - public byte readByte() { - final int read = this.read(); - if (read == -1) { - // end of stream reached - throw new ArrayIndexOutOfBoundsException("End of stream reached. Cannot read more bytes."); - } - return (byte) read; + public long readLong() { + long result = 0; + result |= ((long) this.readInt()) << 32; + result |= 0xffffffffL & this.readInt(); + return result; } public int readInt() { @@ -27,10 +27,48 @@ public class LabyrinthInputStream extends ByteArrayInputStream { return result; } - public long readLong() { - long result = 0; - result |= ((long) this.readInt()) << 32; - result |= 0xffffffffL & this.readInt(); - return result; + public void checkHeader() { + final byte magic1 = this.readByte(); + if (magic1 != SerializerDeserializer.MAGIC_BYTE_1) { + throw new IllegalArgumentException("Invalid labyrinth data."); + } + final byte magic2 = this.readByte(); + if (magic2 != SerializerDeserializer.MAGIC_BYTE_2) { + throw new IllegalArgumentException("Invalid labyrinth data."); + } + final int version = this.readByte(); + if (version != SerializerDeserializer.VERSION_BYTE) { + throw new IllegalArgumentException("Unknown Labyrinth data version: " + version); + } + } + + public byte readByte() { + final int read = this.read(); + if (read == -1) { + // end of stream reached + throw new ArrayIndexOutOfBoundsException("End of stream reached. Cannot read more bytes."); + } + return (byte) read; + } + + @NonNull + public Labyrinth readLabyrinthData() { + final long randomSeed = this.readLong(); + final int width = this.readInt(); + final int height = this.readInt(); + + final Tile[][] tiles = new Tile[width][height]; + for (int x = 0; x < width; x++) { + tiles[x] = new Tile[height]; + } + + for (int y = 0; y < height; y++) { + for (int x = 0; x < width; x++) { + final byte bitmask = this.readByte(); + tiles[x][y] = SerializerDeserializer.getTileForBitmask(bitmask); + } + } + + return SerializerDeserializer.createLabyrinth(tiles, width, height, randomSeed); } } diff --git a/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthOutputStream.java b/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthOutputStream.java index 6d2327f..363a52b 100644 --- a/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthOutputStream.java +++ b/src/main/java/ch/fritteli/labyrinth/generator/serialization/LabyrinthOutputStream.java @@ -1,21 +1,50 @@ package ch.fritteli.labyrinth.generator.serialization; +import ch.fritteli.labyrinth.generator.model.Labyrinth; +import ch.fritteli.labyrinth.generator.model.Tile; +import lombok.NonNull; + import java.io.ByteArrayOutputStream; + public class LabyrinthOutputStream extends ByteArrayOutputStream { + public void writeHeader() { + this.writeByte(SerializerDeserializer.MAGIC_BYTE_1); + this.writeByte(SerializerDeserializer.MAGIC_BYTE_2); + this.writeByte(SerializerDeserializer.VERSION_BYTE); + } + public void writeByte(final byte value) { this.write(value); } + public void writeLabyrinthData(@NonNull final Labyrinth labyrinth) { + final long randomSeed = labyrinth.getRandomSeed(); + final int width = labyrinth.getWidth(); + final int height = labyrinth.getHeight(); + this.writeLong(randomSeed); + this.writeInt(width); + this.writeInt(height); + + for (int y = 0; y < height; y++) { + for (int x = 0; x < width; x++) { + // We .get() it, because we want to crash hard if it is not available. + final Tile tile = labyrinth.getTileAt(x, y).get(); + final byte bitmask = SerializerDeserializer.getBitmaskForTile(tile); + this.writeByte(bitmask); + } + } + } + + public void writeLong(final long value) { + this.writeInt((int) (value >> 32)); + this.writeInt((int) value); + } + public void writeInt(final int value) { this.write(value >> 24); this.write(value >> 16); this.write(value >> 8); this.write(value); } - - public void writeLong(final long value) { - this.writeInt((int) (value >> 32)); - this.writeInt((int) value); - } } diff --git a/src/main/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializer.java b/src/main/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializer.java index ae4df70..244c3f6 100644 --- a/src/main/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializer.java +++ b/src/main/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializer.java @@ -36,19 +36,19 @@ import java.util.EnumSet; * byte hex meaning * 00 0x1a magic * 01 0xb1 magic - * 02 0x00 version (0x00 -> dev / unstable; will be bumped to 0x01 once stabilized) + * 02 0x01 version (0x00 -> dev, 0x01 -> stable) * 03..06 width (int) * 07..10 height (int) * 11..18 random seed number (long) * 19.. tiles * - * exteaneous space (poss. last nibble) is ignored. + * Extraneous space (poss. last nibble) is ignored. */ @UtilityClass public class SerializerDeserializer { - private final byte MAGIC_BYTE_1 = 0x1a; - private final byte MAGIC_BYTE_2 = (byte) 0xb1; - private final byte VERSION_BYTE = 0x01; + final byte MAGIC_BYTE_1 = 0x1a; + final byte MAGIC_BYTE_2 = (byte) 0xb1; + final byte VERSION_BYTE = 0x01; private final byte TOP_BIT = 0b0000_0001; private final byte RIGHT_BIT = 0b0000_0010; @@ -65,8 +65,8 @@ public class SerializerDeserializer { @NonNull public byte[] serialize(@NonNull final Labyrinth labyrinth) { final LabyrinthOutputStream stream = new LabyrinthOutputStream(); - writeHeader(stream); - writeLabyrinthData(stream, labyrinth); + stream.writeHeader(); + stream.writeLabyrinthData(labyrinth); return stream.toByteArray(); } @@ -79,79 +79,17 @@ public class SerializerDeserializer { @NonNull public Labyrinth deserialize(@NonNull final byte[] bytes) { final LabyrinthInputStream stream = new LabyrinthInputStream(bytes); - checkHeader(stream); - return readLabyrinthData(stream); - } - - private static void writeHeader(@NonNull final LabyrinthOutputStream stream) { - stream.writeByte(MAGIC_BYTE_1); - stream.writeByte(MAGIC_BYTE_2); - stream.writeByte(VERSION_BYTE); - - } - - private static void checkHeader(@NonNull final LabyrinthInputStream stream) { - final byte magic1 = stream.readByte(); - if (magic1 != MAGIC_BYTE_1) { - throw new IllegalArgumentException("Invalid labyrinth data."); - } - final byte magic2 = stream.readByte(); - if (magic2 != MAGIC_BYTE_2) { - throw new IllegalArgumentException("Invalid labyrinth data."); - } - final int version = stream.readByte(); - if (version != VERSION_BYTE) { - throw new IllegalArgumentException("Unknown Labyrinth data version: " + version); - } - } - - private static void writeLabyrinthData(@NonNull final LabyrinthOutputStream stream, @NonNull final Labyrinth labyrinth) { - final long randomSeed = labyrinth.getRandomSeed(); - final int width = labyrinth.getWidth(); - final int height = labyrinth.getHeight(); - stream.writeLong(randomSeed); - stream.writeInt(width); - stream.writeInt(height); - - for (int y = 0; y < height; y++) { - for (int x = 0; x < width; x++) { - // We .get() it, because we want to crash hard if it is not available. - final Tile tile = labyrinth.getTileAt(x, y).get(); - final byte bitmask = getBitmaskForTile(tile); - stream.writeByte(bitmask); - } - } - + stream.checkHeader(); + return stream.readLabyrinthData(); } @NonNull - private static Labyrinth readLabyrinthData(@NonNull final LabyrinthInputStream stream) { - final long randomSeed = stream.readLong(); - final int width = stream.readInt(); - final int height = stream.readInt(); - - final Tile[][] tiles = new Tile[width][height]; - for (int x = 0; x < width; x++) { - tiles[x] = new Tile[height]; - } - - for (int y = 0; y < height; y++) { - for (int x = 0; x < width; x++) { - final byte bitmask = stream.readByte(); - tiles[x][y] = getTileForBitmask(bitmask); - } - } - - return createLabyrinth(tiles, width, height, randomSeed); - } - - @NonNull - private Labyrinth createLabyrinth(@NonNull final Tile[][] field, final int width, final int height, final long randomSeed) { + Labyrinth createLabyrinth(@NonNull final Tile[][] field, final int width, final int height, final long randomSeed) { try { - @NonNull final Constructor constructor = Labyrinth.class.getDeclaredConstructor(Tile[][].class, Integer.TYPE, Integer.TYPE, Long.TYPE); + final Constructor constructor = Labyrinth.class.getDeclaredConstructor(Tile[][].class, Integer.TYPE, Integer.TYPE, Long.TYPE); constructor.setAccessible(true); return constructor.newInstance(field, width, height, randomSeed); - } catch (final NoSuchMethodException | IllegalAccessException | InstantiationException | InvocationTargetException e) { + } catch (@NonNull final NoSuchMethodException | IllegalAccessException | InstantiationException | InvocationTargetException e) { throw new RuntimeException("Can not deserialize Labyrinth from labyrinth data.", e); } } @@ -159,15 +97,15 @@ public class SerializerDeserializer { @NonNull private Tile createTile(@NonNull final EnumSet walls, boolean solution) { try { - @NonNull final Constructor constructor = Tile.class.getDeclaredConstructor(EnumSet.class, Boolean.TYPE); + final Constructor constructor = Tile.class.getDeclaredConstructor(EnumSet.class, Boolean.TYPE); constructor.setAccessible(true); return constructor.newInstance(walls, solution); - } catch (final NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { + } catch (@NonNull final NoSuchMethodException | InstantiationException | IllegalAccessException | InvocationTargetException e) { throw new RuntimeException("Can not deserialize Tile from labyrinth data.", e); } } - private byte getBitmaskForTile(@NonNull final Tile tile) { + byte getBitmaskForTile(@NonNull final Tile tile) { byte bitmask = 0; if (tile.hasWallAt(Direction.TOP)) { bitmask |= TOP_BIT; @@ -188,7 +126,7 @@ public class SerializerDeserializer { } @NonNull - private Tile getTileForBitmask(final byte bitmask) { + Tile getTileForBitmask(final byte bitmask) { final EnumSet walls = EnumSet.noneOf(Direction.class); if ((bitmask & TOP_BIT) == TOP_BIT) { walls.add(Direction.TOP); diff --git a/src/main/resources/logback.xml b/src/main/resources/logback.xml index fd7cd55..d8eeeaf 100644 --- a/src/main/resources/logback.xml +++ b/src/main/resources/logback.xml @@ -1,12 +1,12 @@ - + - %d{HH:mm:ss.SSS} [%thread] %-5level %logger{36} - %msg%n + %d{HH:mm:ss.SSS} %-5level %X{correlationId} [%thread] %logger{36} - %msg%n diff --git a/src/test/java/ch/fritteli/labyrinth/generator/model/DirectionTest.java b/src/test/java/ch/fritteli/labyrinth/generator/model/DirectionTest.java index b94bbc3..03a3151 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/model/DirectionTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/model/DirectionTest.java @@ -2,14 +2,14 @@ package ch.fritteli.labyrinth.generator.model; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.*; +import static org.assertj.core.api.Assertions.assertThat; class DirectionTest { @Test void invert() { - assertEquals(Direction.BOTTOM, Direction.TOP.invert()); - assertEquals(Direction.LEFT, Direction.RIGHT.invert()); - assertEquals(Direction.TOP, Direction.BOTTOM.invert()); - assertEquals(Direction.RIGHT, Direction.LEFT.invert()); + assertThat(Direction.TOP.invert()).isEqualTo(Direction.BOTTOM); + assertThat(Direction.RIGHT.invert()).isEqualTo(Direction.LEFT); + assertThat(Direction.BOTTOM.invert()).isEqualTo(Direction.TOP); + assertThat(Direction.LEFT.invert()).isEqualTo(Direction.RIGHT); } } diff --git a/src/test/java/ch/fritteli/labyrinth/generator/model/LabyrinthTest.java b/src/test/java/ch/fritteli/labyrinth/generator/model/LabyrinthTest.java index 45ecc99..e3653ff 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/model/LabyrinthTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/model/LabyrinthTest.java @@ -2,25 +2,28 @@ package ch.fritteli.labyrinth.generator.model; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertThrows; +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatExceptionOfType; class LabyrinthTest { @Test void testConstruct() { // act / assert on simple cases - assertThrows(IllegalArgumentException.class, () -> new Labyrinth(0, 0)); - assertThrows(IllegalArgumentException.class, () -> new Labyrinth(0, 0, 0)); + assertThatExceptionOfType(IllegalArgumentException.class).isThrownBy(() -> new Labyrinth(0, 0)) + .withMessage("width and height must be >1"); + assertThatExceptionOfType(IllegalArgumentException.class).isThrownBy(() -> new Labyrinth(0, 0, 0)) + .withMessage("width and height must be >1"); // now for the real work: // arrange final Labyrinth sut = new Labyrinth(2, 3, 5); // assert - assertEquals(2, sut.getWidth()); - assertEquals(3, sut.getHeight()); - assertEquals(5, sut.getRandomSeed()); - assertEquals(new Position(0, 0), sut.getStart()); - assertEquals(new Position(1, 2), sut.getEnd()); + assertThat(sut) + .returns(2, Labyrinth::getWidth) + .returns(3, Labyrinth::getHeight) + .returns(5L, Labyrinth::getRandomSeed) + .returns(new Position(0, 0), Labyrinth::getStart) + .returns(new Position(1, 2), Labyrinth::getEnd); } } diff --git a/src/test/java/ch/fritteli/labyrinth/generator/model/PositionTest.java b/src/test/java/ch/fritteli/labyrinth/generator/model/PositionTest.java index f1494c9..307156b 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/model/PositionTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/model/PositionTest.java @@ -2,7 +2,7 @@ package ch.fritteli.labyrinth.generator.model; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.assertj.core.api.Assertions.assertThat; class PositionTest { @Test @@ -18,10 +18,10 @@ class PositionTest { // assert // Original is unchanged - assertEquals(new Position(0, 0), sut); - assertEquals(new Position(0, -1), resultTOP); - assertEquals(new Position(1, 0), resultRIGHT); - assertEquals(new Position(0, 1), resultBOTTOM); - assertEquals(new Position(-1, 0), resultLEFT); + assertThat(sut).isEqualTo(new Position(0, 0)); + assertThat(resultTOP).isEqualTo(new Position(0, -1)); + assertThat(resultRIGHT).isEqualTo(new Position(1, 0)); + assertThat(resultBOTTOM).isEqualTo(new Position(0, 1)); + assertThat(resultLEFT).isEqualTo(new Position(-1, 0)); } } diff --git a/src/test/java/ch/fritteli/labyrinth/generator/model/TileTest.java b/src/test/java/ch/fritteli/labyrinth/generator/model/TileTest.java index 6d8f5d0..11bacc6 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/model/TileTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/model/TileTest.java @@ -5,9 +5,7 @@ import org.junit.jupiter.api.Test; import java.util.Random; -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static org.junit.jupiter.api.Assertions.assertTrue; +import static org.assertj.core.api.Assertions.assertThat; class TileTest { @Test @@ -16,11 +14,12 @@ class TileTest { final Tile sut = new Tile(); //assert - assertTrue(sut.hasWallAt(Direction.TOP)); - assertTrue(sut.hasWallAt(Direction.RIGHT)); - assertTrue(sut.hasWallAt(Direction.BOTTOM)); - assertTrue(sut.hasWallAt(Direction.LEFT)); - assertFalse(sut.isSolution()); + assertThat(sut) + .returns(true, v -> v.hasWallAt(Direction.TOP)) + .returns(true, v -> v.hasWallAt(Direction.RIGHT)) + .returns(true, v -> v.hasWallAt(Direction.BOTTOM)) + .returns(true, v -> v.hasWallAt(Direction.LEFT)) + .returns(false, Tile::isSolution); } @Test @@ -32,15 +31,15 @@ class TileTest { boolean result = sut.digFrom(Direction.TOP); // assert - assertTrue(result); - assertFalse(sut.hasWallAt(Direction.TOP)); + assertThat(result).isTrue(); + assertThat(sut.hasWallAt(Direction.TOP)).isFalse(); // act: can not dig from when already dug result = sut.digFrom(Direction.BOTTOM); // assert - assertFalse(result); - assertTrue(sut.hasWallAt(Direction.BOTTOM)); + assertThat(result).isFalse(); + assertThat(sut.hasWallAt(Direction.BOTTOM)).isTrue(); } @Test @@ -49,18 +48,20 @@ class TileTest { final Tile sut = new Tile(); // act / assert - assertTrue(sut.digTo(Direction.TOP)); - assertTrue(sut.digTo(Direction.RIGHT)); - assertTrue(sut.digTo(Direction.BOTTOM)); - assertTrue(sut.digTo(Direction.LEFT)); - // digging a second time does not succeed - assertFalse(sut.digTo(Direction.LEFT)); + assertThat(sut) + .returns(true, v -> v.digTo(Direction.TOP)) + .returns(true, v -> v.digTo(Direction.RIGHT)) + .returns(true, v -> v.digTo(Direction.BOTTOM)) + .returns(true, v -> v.digTo(Direction.LEFT)) + // digging a second time does not succeed + .returns(false, v -> v.digTo(Direction.LEFT)); // assert - assertFalse(sut.hasWallAt(Direction.TOP)); - assertFalse(sut.hasWallAt(Direction.RIGHT)); - assertFalse(sut.hasWallAt(Direction.BOTTOM)); - assertFalse(sut.hasWallAt(Direction.LEFT)); + assertThat(sut) + .returns(false, v -> v.hasWallAt(Direction.TOP)) + .returns(false, v -> v.hasWallAt(Direction.RIGHT)) + .returns(false, v -> v.hasWallAt(Direction.BOTTOM)) + .returns(false, v -> v.hasWallAt(Direction.LEFT)); } @Test @@ -72,9 +73,10 @@ class TileTest { sut.preventDiggingToOrFrom(Direction.LEFT); // assert - assertFalse(sut.digTo(Direction.LEFT)); - assertFalse(sut.digFrom(Direction.LEFT)); - assertTrue(sut.hasWallAt(Direction.LEFT)); + assertThat(sut) + .returns(false, v -> v.digTo(Direction.LEFT)) + .returns(false, v -> v.digFrom(Direction.LEFT)) + .returns(true, v -> v.hasWallAt(Direction.LEFT)); } @Test @@ -87,11 +89,12 @@ class TileTest { // then, re-enable digging sut.enableDiggingToOrFrom(Direction.LEFT); // also, enable it from a previously non-disabled direction - sut.enableDiggingToOrFrom(Direction.BOTTOM); + // assert - assertTrue(sut.digTo(Direction.LEFT)); - assertFalse(sut.hasWallAt(Direction.LEFT)); + assertThat(sut) + .returns(true, v -> v.digTo(Direction.LEFT)) + .returns(false, v -> v.hasWallAt(Direction.LEFT)); } @Test @@ -104,7 +107,7 @@ class TileTest { sut.undigTo(Direction.BOTTOM); // assert - assertTrue(sut.hasWallAt(Direction.BOTTOM)); + assertThat(sut.hasWallAt(Direction.BOTTOM)).isTrue(); } @Test @@ -116,7 +119,7 @@ class TileTest { sut.setSolution(); // assert - assertTrue(sut.isSolution()); + assertThat(sut.isSolution()).isTrue(); } @Test @@ -130,8 +133,9 @@ class TileTest { Option result = sut.getRandomAvailableDirection(dummyRandom); // assert - assertTrue(result.isDefined()); - assertEquals(Direction.TOP, result.get()); + assertThat(result) + .singleElement() + .isEqualTo(Direction.TOP); // re-arrange sut.preventDiggingToOrFrom(Direction.TOP); @@ -140,8 +144,9 @@ class TileTest { result = sut.getRandomAvailableDirection(dummyRandom); // assert - assertTrue(result.isDefined()); - assertEquals(Direction.RIGHT, result.get()); + assertThat(result) + .singleElement() + .isEqualTo(Direction.RIGHT); // re-arrange sut.preventDiggingToOrFrom(Direction.RIGHT); @@ -150,8 +155,9 @@ class TileTest { result = sut.getRandomAvailableDirection(dummyRandom); // assert - assertTrue(result.isDefined()); - assertEquals(Direction.BOTTOM, result.get()); + assertThat(result) + .singleElement() + .isEqualTo(Direction.BOTTOM); // re-arrange sut.preventDiggingToOrFrom(Direction.BOTTOM); @@ -160,8 +166,9 @@ class TileTest { result = sut.getRandomAvailableDirection(dummyRandom); // assert - assertTrue(result.isDefined()); - assertEquals(Direction.LEFT, result.get()); + assertThat(result) + .singleElement() + .isEqualTo(Direction.LEFT); // re-arrange sut.preventDiggingToOrFrom(Direction.LEFT); @@ -170,7 +177,7 @@ class TileTest { result = sut.getRandomAvailableDirection(dummyRandom); // assert - assertFalse(result.isDefined()); + assertThat(result).isEmpty(); } private static class MyDummyRandom extends Random { diff --git a/src/test/java/ch/fritteli/labyrinth/generator/model/WallsTest.java b/src/test/java/ch/fritteli/labyrinth/generator/model/WallsTest.java index 78de732..8e87fca 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/model/WallsTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/model/WallsTest.java @@ -3,10 +3,8 @@ package ch.fritteli.labyrinth.generator.model; import io.vavr.collection.Stream; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.assertEquals; -import static org.junit.jupiter.api.Assertions.assertFalse; -import static org.junit.jupiter.api.Assertions.assertThrows; -import static org.junit.jupiter.api.Assertions.assertTrue; +import static org.assertj.core.api.Assertions.assertThat; +import static org.assertj.core.api.Assertions.assertThatExceptionOfType; class WallsTest { @Test @@ -15,10 +13,11 @@ class WallsTest { final Walls sut = new Walls(); // assert - assertFalse(sut.isSet(Direction.TOP)); - assertFalse(sut.isSet(Direction.RIGHT)); - assertFalse(sut.isSet(Direction.BOTTOM)); - assertFalse(sut.isSet(Direction.LEFT)); + assertThat(sut) + .returns(false, v -> v.isSet(Direction.TOP)) + .returns(false, v -> v.isSet(Direction.RIGHT)) + .returns(false, v -> v.isSet(Direction.BOTTOM)) + .returns(false, v -> v.isSet(Direction.LEFT)); } @Test @@ -30,19 +29,21 @@ class WallsTest { sut.set(Direction.RIGHT); // assert - assertFalse(sut.isSet(Direction.TOP)); - assertTrue(sut.isSet(Direction.RIGHT)); - assertFalse(sut.isSet(Direction.BOTTOM)); - assertFalse(sut.isSet(Direction.LEFT)); + assertThat(sut) + .returns(false, v -> v.isSet(Direction.TOP)) + .returns(true, v -> v.isSet(Direction.RIGHT)) + .returns(false, v -> v.isSet(Direction.BOTTOM)) + .returns(false, v -> v.isSet(Direction.LEFT)); //act: Setting twice has no effect sut.set(Direction.RIGHT); // assert - assertFalse(sut.isSet(Direction.TOP)); - assertTrue(sut.isSet(Direction.RIGHT)); - assertFalse(sut.isSet(Direction.BOTTOM)); - assertFalse(sut.isSet(Direction.LEFT)); + assertThat(sut) + .returns(false, v -> v.isSet(Direction.TOP)) + .returns(true, v -> v.isSet(Direction.RIGHT)) + .returns(false, v -> v.isSet(Direction.BOTTOM)) + .returns(false, v -> v.isSet(Direction.LEFT)); } @Test @@ -54,10 +55,11 @@ class WallsTest { sut.setAll(); // assert - assertTrue(sut.isSet(Direction.TOP)); - assertTrue(sut.isSet(Direction.RIGHT)); - assertTrue(sut.isSet(Direction.BOTTOM)); - assertTrue(sut.isSet(Direction.LEFT)); + assertThat(sut) + .returns(true, v -> v.isSet(Direction.TOP)) + .returns(true, v -> v.isSet(Direction.RIGHT)) + .returns(true, v -> v.isSet(Direction.BOTTOM)) + .returns(true, v -> v.isSet(Direction.LEFT)); } @Test @@ -71,20 +73,21 @@ class WallsTest { sut.harden(Direction.TOP); // assert - assertTrue(sut.isSet(Direction.TOP)); - assertTrue(sut.isSet(Direction.RIGHT)); - assertFalse(sut.isSet(Direction.BOTTOM)); - assertFalse(sut.isSet(Direction.LEFT)); + assertThat(sut) + .returns(true, v -> v.isSet(Direction.TOP)) + .returns(true, v -> v.isSet(Direction.RIGHT)) + .returns(false, v -> v.isSet(Direction.BOTTOM)) + .returns(false, v -> v.isSet(Direction.LEFT)); // act: try to clear hardened wall final boolean result = sut.clear(Direction.TOP); // assert: TOP wall is still set - assertFalse(result); - assertTrue(sut.isSet(Direction.TOP)); + assertThat(result).isFalse(); + assertThat(sut.isSet(Direction.TOP)).isTrue(); // act / assert: try to harden un-set wall - assertThrows(IllegalStateException.class, () -> sut.harden(Direction.LEFT)); + assertThatExceptionOfType(IllegalStateException.class).isThrownBy(() -> sut.harden(Direction.LEFT)); } @Test @@ -95,13 +98,13 @@ class WallsTest { sut.harden(Direction.TOP); // pre-assert: TOP can't be cleared while hardened - assertFalse(sut.clear(Direction.TOP)); + assertThat(sut.clear(Direction.TOP)).isFalse(); // act sut.unharden(Direction.TOP); // assert: TOP can be cleared - assertTrue(sut.clear(Direction.TOP)); + assertThat(sut.clear(Direction.TOP)).isTrue(); } @Test @@ -113,7 +116,7 @@ class WallsTest { Stream result = sut.getUnhardenedSet(); // assert - assertTrue(result.isEmpty()); + assertThat(result).isEmpty(); // arrange: set some directions sut.set(Direction.TOP); @@ -123,7 +126,7 @@ class WallsTest { result = sut.getUnhardenedSet(); // assert - assertEquals(Stream.of(Direction.TOP, Direction.LEFT), result); + assertThat(result).containsExactly(Direction.TOP, Direction.LEFT); // arrange: harden a direction sut.harden(Direction.TOP); @@ -132,6 +135,6 @@ class WallsTest { result = sut.getUnhardenedSet(); // assert - assertEquals(Stream.of(Direction.LEFT), result); + assertThat(result).containsExactly(Direction.LEFT); } } diff --git a/src/test/java/ch/fritteli/labyrinth/generator/renderer/text/CharDefinitionTest.java b/src/test/java/ch/fritteli/labyrinth/generator/renderer/text/CharDefinitionTest.java index eefc1a9..0fc9e0c 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/renderer/text/CharDefinitionTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/renderer/text/CharDefinitionTest.java @@ -2,58 +2,58 @@ package ch.fritteli.labyrinth.generator.renderer.text; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.assertj.core.api.Assertions.assertThat; class CharDefinitionTest { @Test void testRenderingWall() { - assertEquals(" ", new CharDefinition(false, false, false, false, false).toString()); - assertEquals("╶", new CharDefinition(false, false, false, true, false).toString()); - assertEquals("╴", new CharDefinition(false, false, true, false, false).toString()); - assertEquals("─", new CharDefinition(false, false, true, true, false).toString()); - assertEquals("╷", new CharDefinition(false, true, false, false, false).toString()); - assertEquals("┌", new CharDefinition(false, true, false, true, false).toString()); - assertEquals("┐", new CharDefinition(false, true, true, false, false).toString()); - assertEquals("┬", new CharDefinition(false, true, true, true, false).toString()); - assertEquals("╵", new CharDefinition(true, false, false, false, false).toString()); - assertEquals("└", new CharDefinition(true, false, false, true, false).toString()); - assertEquals("┘", new CharDefinition(true, false, true, false, false).toString()); - assertEquals("┴", new CharDefinition(true, false, true, true, false).toString()); - assertEquals("│", new CharDefinition(true, true, false, false, false).toString()); - assertEquals("├", new CharDefinition(true, true, false, true, false).toString()); - assertEquals("┤", new CharDefinition(true, true, true, false, false).toString()); - assertEquals("┼", new CharDefinition(true, true, true, true, false).toString()); + assertThat(new CharDefinition(false, false, false, false, false)).hasToString(" "); + assertThat(new CharDefinition(false, false, false, true, false)).hasToString("╶"); + assertThat(new CharDefinition(false, false, true, false, false)).hasToString("╴"); + assertThat(new CharDefinition(false, false, true, true, false)).hasToString("─"); + assertThat(new CharDefinition(false, true, false, false, false)).hasToString("╷"); + assertThat(new CharDefinition(false, true, false, true, false)).hasToString("┌"); + assertThat(new CharDefinition(false, true, true, false, false)).hasToString("┐"); + assertThat(new CharDefinition(false, true, true, true, false)).hasToString("┬"); + assertThat(new CharDefinition(true, false, false, false, false)).hasToString("╵"); + assertThat(new CharDefinition(true, false, false, true, false)).hasToString("└"); + assertThat(new CharDefinition(true, false, true, false, false)).hasToString("┘"); + assertThat(new CharDefinition(true, false, true, true, false)).hasToString("┴"); + assertThat(new CharDefinition(true, true, false, false, false)).hasToString("│"); + assertThat(new CharDefinition(true, true, false, true, false)).hasToString("├"); + assertThat(new CharDefinition(true, true, true, false, false)).hasToString("┤"); + assertThat(new CharDefinition(true, true, true, true, false)).hasToString("┼"); } @Test void testRenderingSolution() { - assertEquals(" ", new CharDefinition(false, false, false, false, true).toString()); - assertEquals("╶", new CharDefinition(false, false, false, true, true).toString()); - assertEquals("╴", new CharDefinition(false, false, true, false, true).toString()); - assertEquals("─", new CharDefinition(false, false, true, true, true).toString()); - assertEquals("╷", new CharDefinition(false, true, false, false, true).toString()); - assertEquals("╭", new CharDefinition(false, true, false, true, true).toString()); - assertEquals("╮", new CharDefinition(false, true, true, false, true).toString()); - assertEquals("┬", new CharDefinition(false, true, true, true, true).toString()); - assertEquals("╵", new CharDefinition(true, false, false, false, true).toString()); - assertEquals("╰", new CharDefinition(true, false, false, true, true).toString()); - assertEquals("╯", new CharDefinition(true, false, true, false, true).toString()); - assertEquals("┴", new CharDefinition(true, false, true, true, true).toString()); - assertEquals("│", new CharDefinition(true, true, false, false, true).toString()); - assertEquals("├", new CharDefinition(true, true, false, true, true).toString()); - assertEquals("┤", new CharDefinition(true, true, true, false, true).toString()); - assertEquals("┼", new CharDefinition(true, true, true, true, true).toString()); + assertThat(new CharDefinition(false, false, false, false, true)).hasToString(" "); + assertThat(new CharDefinition(false, false, false, true, true)).hasToString("╶"); + assertThat(new CharDefinition(false, false, true, false, true)).hasToString("╴"); + assertThat(new CharDefinition(false, false, true, true, true)).hasToString("─"); + assertThat(new CharDefinition(false, true, false, false, true)).hasToString("╷"); + assertThat(new CharDefinition(false, true, false, true, true)).hasToString("╭"); + assertThat(new CharDefinition(false, true, true, false, true)).hasToString("╮"); + assertThat(new CharDefinition(false, true, true, true, true)).hasToString("┬"); + assertThat(new CharDefinition(true, false, false, false, true)).hasToString("╵"); + assertThat(new CharDefinition(true, false, false, true, true)).hasToString("╰"); + assertThat(new CharDefinition(true, false, true, false, true)).hasToString("╯"); + assertThat(new CharDefinition(true, false, true, true, true)).hasToString("┴"); + assertThat(new CharDefinition(true, true, false, false, true)).hasToString("│"); + assertThat(new CharDefinition(true, true, false, true, true)).hasToString("├"); + assertThat(new CharDefinition(true, true, true, false, true)).hasToString("┤"); + assertThat(new CharDefinition(true, true, true, true, true)).hasToString("┼"); } @Test void testBuilderMethods() { - assertEquals(new CharDefinition(true, false, false, false, false), new CharDefinition().up()); - assertEquals(new CharDefinition(false, true, false, false, false), new CharDefinition().down()); - assertEquals(new CharDefinition(false, false, true, false, false), new CharDefinition().left()); - assertEquals(new CharDefinition(false, false, false, true, false), new CharDefinition().right()); - assertEquals(new CharDefinition(false, false, false, false, true), new CharDefinition().solution()); - assertEquals(new CharDefinition(true, true, false, false, false), new CharDefinition().vertical()); - assertEquals(new CharDefinition(false, false, true, true, false), new CharDefinition().horizontal()); - assertEquals(new CharDefinition(true, true, true, true, true), new CharDefinition().vertical().horizontal().solution()); + assertThat(new CharDefinition().up()).isEqualTo(new CharDefinition(true, false, false, false, false)); + assertThat(new CharDefinition().down()).isEqualTo(new CharDefinition(false, true, false, false, false)); + assertThat(new CharDefinition().left()).isEqualTo(new CharDefinition(false, false, true, false, false)); + assertThat(new CharDefinition().right()).isEqualTo(new CharDefinition(false, false, false, true, false)); + assertThat(new CharDefinition().solution()).isEqualTo(new CharDefinition(false, false, false, false, true)); + assertThat(new CharDefinition().vertical()).isEqualTo(new CharDefinition(true, true, false, false, false)); + assertThat(new CharDefinition().horizontal()).isEqualTo(new CharDefinition(false, false, true, true, false)); + assertThat(new CharDefinition().vertical().horizontal().solution()).isEqualTo(new CharDefinition(true, true, true, true, true)); } } diff --git a/src/test/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializerTest.java b/src/test/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializerTest.java index 4839e9b..ed7c85a 100644 --- a/src/test/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializerTest.java +++ b/src/test/java/ch/fritteli/labyrinth/generator/serialization/SerializerDeserializerTest.java @@ -1,33 +1,32 @@ package ch.fritteli.labyrinth.generator.serialization; import ch.fritteli.labyrinth.generator.model.Labyrinth; -import lombok.NonNull; import org.junit.jupiter.api.Test; -import static org.junit.jupiter.api.Assertions.assertEquals; +import static org.assertj.core.api.Assertions.assertThat; class SerializerDeserializerTest { @Test void testSerializeDeserializeTiny() { - @NonNull final Labyrinth expected = new Labyrinth(2, 2, 255); - @NonNull final byte[] bytes = SerializerDeserializer.serialize(expected); - @NonNull final Labyrinth result = SerializerDeserializer.deserialize(bytes); - assertEquals(expected, result); + final Labyrinth expected = new Labyrinth(2, 2, 255); + final byte[] bytes = SerializerDeserializer.serialize(expected); + final Labyrinth result = SerializerDeserializer.deserialize(bytes); + assertThat(result).isEqualTo(expected); } @Test void testSerializeDeserializeMedium() { - @NonNull final Labyrinth expected = new Labyrinth(20, 20, -271828182846L); - @NonNull final byte[] bytes = SerializerDeserializer.serialize(expected); - @NonNull final Labyrinth result = SerializerDeserializer.deserialize(bytes); - assertEquals(expected, result); + final Labyrinth expected = new Labyrinth(20, 20, -271828182846L); + final byte[] bytes = SerializerDeserializer.serialize(expected); + final Labyrinth result = SerializerDeserializer.deserialize(bytes); + assertThat(result).isEqualTo(expected); } @Test void testSerializeDeserializeLarge() { - @NonNull final Labyrinth expected = new Labyrinth(200, 320, 3141592653589793238L); - @NonNull final byte[] bytes = SerializerDeserializer.serialize(expected); - @NonNull final Labyrinth result = SerializerDeserializer.deserialize(bytes); - assertEquals(expected, result); + final Labyrinth expected = new Labyrinth(200, 320, 3141592653589793238L); + final byte[] bytes = SerializerDeserializer.serialize(expected); + final Labyrinth result = SerializerDeserializer.deserialize(bytes); + assertThat(result).isEqualTo(expected); } }