aboutsummaryrefslogtreecommitdiff
path: root/jgvariant-core/src/test
diff options
context:
space:
mode:
authorMatthias Andreas Benkard <code@mail.matthias.benkard.de>2023-12-10 20:29:35 +0100
committerMatthias Andreas Benkard <code@mail.matthias.benkard.de>2023-12-10 20:32:21 +0100
commitdf853ef46a9c12d319bf824ac106a411f5eddabd (patch)
treef7e0112d7ff160c12186ba7d7ec4671a6487aeeb /jgvariant-core/src/test
parent3ad12086acde4cfa9d346938e876947bde6305dc (diff)
Add property-based tests and fix the bugs discovered.
Change-Id: I8deb1a7d75078c037714541d8f6f656052c2476c
Diffstat (limited to 'jgvariant-core/src/test')
-rw-r--r--jgvariant-core/src/test/java/eu/mulk/jgvariant/core/DecoderPropertyTest.java89
1 files changed, 89 insertions, 0 deletions
diff --git a/jgvariant-core/src/test/java/eu/mulk/jgvariant/core/DecoderPropertyTest.java b/jgvariant-core/src/test/java/eu/mulk/jgvariant/core/DecoderPropertyTest.java
new file mode 100644
index 0000000..5e07ea0
--- /dev/null
+++ b/jgvariant-core/src/test/java/eu/mulk/jgvariant/core/DecoderPropertyTest.java
@@ -0,0 +1,89 @@
+package eu.mulk.jgvariant.core;
+
+import java.text.ParseException;
+import java.util.Optional;
+import net.jqwik.api.*;
+
+@SuppressWarnings("java:S2187")
+class DecoderPropertyTest {
+
+ @Group
+ class VariantRoundtripLaw implements RoundtripLaw<Variant> {
+
+ @Override
+ public Decoder<Variant> decoder() {
+ return Decoder.ofVariant();
+ }
+
+ @Override
+ public Arbitrary<Variant> anyT() {
+ return anyVariant();
+ }
+ }
+
+ interface RoundtripLaw<T> {
+
+ @Property
+ default boolean roundtripsWell(@ForAll(value = "anyT") T entityLeft) {
+ var decoder = decoder();
+ var bytes = decoder.encode(entityLeft);
+ var entityRight = decoder.decode(bytes);
+ return entityLeft.equals(entityRight);
+ }
+
+ Decoder<T> decoder();
+
+ @Provide
+ Arbitrary<T> anyT();
+ }
+
+ @Provide
+ Arbitrary<Variant> anyVariant() {
+ var anyString = Arbitraries.strings().map(s -> new Variant(parseSignature("s"), s));
+ var anyInt = Arbitraries.integers().map(i -> new Variant(parseSignature("i"), i));
+ var anyLong = Arbitraries.longs().map(l -> new Variant(parseSignature("x"), l));
+ var anyDouble = Arbitraries.doubles().map(d -> new Variant(parseSignature("d"), d));
+ var anyBoolean =
+ Arbitraries.of(Boolean.TRUE, Boolean.FALSE).map(b -> new Variant(parseSignature("b"), b));
+ var anyByte = Arbitraries.bytes().map(b -> new Variant(parseSignature("y"), b));
+ var anyShort = Arbitraries.shorts().map(s -> new Variant(parseSignature("n"), s));
+ var anyByteArray = Arbitraries.bytes().list().map(b -> new Variant(parseSignature("ay"), b));
+ var anySome =
+ Arbitraries.lazyOf(
+ () ->
+ anyVariant()
+ .map(
+ x ->
+ new Variant(
+ parseSignature("m" + x.signature().toString()),
+ Optional.of(x.value()))));
+ var anyNone =
+ Arbitraries.lazyOf(
+ () ->
+ anyVariant()
+ .map(
+ x ->
+ new Variant(
+ parseSignature("m" + x.signature().toString()), Optional.empty())));
+ // FIXME missing: list, tuple, dictionary, variant
+ return Arbitraries.oneOf(
+ anyString,
+ anyInt,
+ anyLong,
+ anyDouble,
+ anyBoolean,
+ anyByte,
+ anyShort,
+ anyByteArray,
+ anySome,
+ anyNone);
+ }
+
+ private Signature parseSignature(String s) {
+ try {
+ return Signature.parse(s);
+ } catch (ParseException e) {
+ throw new AssertionError(e);
+ }
+ }
+}