From ac1ee4dbcd165aafbe5746aa4dee0be4344918c3 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 14 Dec 2025 11:25:25 +0000 Subject: [PATCH 1/4] Initial plan From e17f5892922d3bb886894a1911ec60937b96d841 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 14 Dec 2025 11:36:44 +0000 Subject: [PATCH 2/4] Add NullAway support via Error Prone - Added Error Prone 2.45.0 as compiler plugin - Added NullAway 0.12.14 for null-safety checking - Added JSpecify 1.0.0 for nullability annotations - Configured Error Prone with Java 21 compatibility flags - Fixed nullability issues in PrintAll.java - Added @SuppressWarnings for test helper classes - All tests passing Co-authored-by: Garciat <118277+Garciat@users.noreply.github.com> --- pom.xml | 40 +++++++++++++++++++ .../garciat/typeclasses/classes/PrintAll.java | 4 +- .../garciat/typeclasses/TypeClassesTest.java | 2 + .../typeclasses/impl/ParsedTypeTest.java | 2 + 4 files changed, 47 insertions(+), 1 deletion(-) diff --git a/pom.xml b/pom.xml index 6aed270..e9c6aa6 100644 --- a/pom.xml +++ b/pom.xml @@ -19,6 +19,11 @@ + + org.jspecify + jspecify + 1.0.0 + org.junit.jupiter junit-jupiter @@ -47,6 +52,38 @@ maven-compiler-plugin 3.14.1 + + true + 128m + 2048m + + -XDcompilePolicy=simple + --should-stop=ifError=FLOW + -Xplugin:ErrorProne -Xep:NullAway:ERROR -XepOpt:NullAway:AnnotatedPackages=com.garciat.typeclasses + -J--add-exports=jdk.compiler/com.sun.tools.javac.api=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.file=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.main=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.model=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.parser=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.processing=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.tree=ALL-UNNAMED + -J--add-exports=jdk.compiler/com.sun.tools.javac.util=ALL-UNNAMED + -J--add-opens=jdk.compiler/com.sun.tools.javac.code=ALL-UNNAMED + -J--add-opens=jdk.compiler/com.sun.tools.javac.comp=ALL-UNNAMED + + + + com.google.errorprone + error_prone_core + 2.45.0 + + + com.uber.nullaway + nullaway + 0.12.14 + + + maven-surefire-plugin @@ -86,6 +123,9 @@ com.spotify.fmt fmt-maven-plugin + + maven-compiler-plugin + \ No newline at end of file diff --git a/src/main/java/com/garciat/typeclasses/classes/PrintAll.java b/src/main/java/com/garciat/typeclasses/classes/PrintAll.java index 919be1f..2bee204 100644 --- a/src/main/java/com/garciat/typeclasses/classes/PrintAll.java +++ b/src/main/java/com/garciat/typeclasses/classes/PrintAll.java @@ -8,6 +8,7 @@ import com.garciat.typeclasses.types.F3; import java.util.List; import java.util.function.Function; +import org.jspecify.annotations.Nullable; /** * @implNote Source @@ -21,7 +22,8 @@ static T of(PrintAll printAll) { } @Witness - static PrintAll base() { + @SuppressWarnings("NullAway") + static PrintAll<@Nullable Void> base() { return strings -> { for (String s : strings) { System.out.println(s); diff --git a/src/test/java/com/garciat/typeclasses/TypeClassesTest.java b/src/test/java/com/garciat/typeclasses/TypeClassesTest.java index ae9070a..703ba1f 100644 --- a/src/test/java/com/garciat/typeclasses/TypeClassesTest.java +++ b/src/test/java/com/garciat/typeclasses/TypeClassesTest.java @@ -216,10 +216,12 @@ void witnessMapWithDependencies() { // Test helper classes // ============================================ + @SuppressWarnings("NullAway") static class NoWitnessType { String value; } + @SuppressWarnings("NullAway") static class CustomType { String value; diff --git a/src/test/java/com/garciat/typeclasses/impl/ParsedTypeTest.java b/src/test/java/com/garciat/typeclasses/impl/ParsedTypeTest.java index 66f12fe..0b77ac6 100644 --- a/src/test/java/com/garciat/typeclasses/impl/ParsedTypeTest.java +++ b/src/test/java/com/garciat/typeclasses/impl/ParsedTypeTest.java @@ -77,6 +77,7 @@ class TestClass {} @Test void parseTypeVariableInParameterizedType() throws Exception { + @SuppressWarnings("NullAway") class TestClass { List field; } @@ -88,6 +89,7 @@ class TestClass { @Test void parseWildcardTypeThrows() throws Exception { + @SuppressWarnings("NullAway") class TestClass { List field; } From 9543257d209cf728f6b4308782f6712642db9c48 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 14 Dec 2025 11:46:17 +0000 Subject: [PATCH 3/4] Replace Void with Unit type in PrintAll - Created new Unit record type in types package - Updated PrintAll to use Unit instead of Void with @Nullable - Removed @SuppressWarnings annotation as it's no longer needed - Updated test to use Unit type - All tests passing Co-authored-by: Garciat <118277+Garciat@users.noreply.github.com> --- .../java/com/garciat/typeclasses/classes/PrintAll.java | 9 +++++---- src/main/java/com/garciat/typeclasses/types/Unit.java | 7 +++++++ src/test/java/com/garciat/typeclasses/ExamplesTest.java | 3 ++- 3 files changed, 14 insertions(+), 5 deletions(-) create mode 100644 src/main/java/com/garciat/typeclasses/types/Unit.java diff --git a/src/main/java/com/garciat/typeclasses/classes/PrintAll.java b/src/main/java/com/garciat/typeclasses/classes/PrintAll.java index 2bee204..1d3948d 100644 --- a/src/main/java/com/garciat/typeclasses/classes/PrintAll.java +++ b/src/main/java/com/garciat/typeclasses/classes/PrintAll.java @@ -1,14 +1,16 @@ package com.garciat.typeclasses.classes; +import static com.garciat.typeclasses.types.Unit.unit; + import com.garciat.typeclasses.api.TypeClass; import com.garciat.typeclasses.api.TypeClass.Witness; import com.garciat.typeclasses.impl.utils.Lists; import com.garciat.typeclasses.types.F1; import com.garciat.typeclasses.types.F2; import com.garciat.typeclasses.types.F3; +import com.garciat.typeclasses.types.Unit; import java.util.List; import java.util.function.Function; -import org.jspecify.annotations.Nullable; /** * @implNote Source @@ -22,13 +24,12 @@ static T of(PrintAll printAll) { } @Witness - @SuppressWarnings("NullAway") - static PrintAll<@Nullable Void> base() { + static PrintAll base() { return strings -> { for (String s : strings) { System.out.println(s); } - return null; + return unit(); }; } diff --git a/src/main/java/com/garciat/typeclasses/types/Unit.java b/src/main/java/com/garciat/typeclasses/types/Unit.java new file mode 100644 index 0000000..95d2324 --- /dev/null +++ b/src/main/java/com/garciat/typeclasses/types/Unit.java @@ -0,0 +1,7 @@ +package com.garciat.typeclasses.types; + +public record Unit() { + public static Unit unit() { + return new Unit(); + } +} diff --git a/src/test/java/com/garciat/typeclasses/ExamplesTest.java b/src/test/java/com/garciat/typeclasses/ExamplesTest.java index 706de4e..0dc6444 100644 --- a/src/test/java/com/garciat/typeclasses/ExamplesTest.java +++ b/src/test/java/com/garciat/typeclasses/ExamplesTest.java @@ -18,6 +18,7 @@ import com.garciat.typeclasses.types.JavaList; import com.garciat.typeclasses.types.Maybe; import com.garciat.typeclasses.types.Sum; +import com.garciat.typeclasses.types.Unit; import java.util.List; import java.util.Map; import java.util.Optional; @@ -70,7 +71,7 @@ void example() { F3 sum = SumAllInt.of(witness(new Ty<>() {})); System.out.println(sum.apply(1, 2, 3)); - F3, Integer, Void> printer = PrintAll.of(witness(new Ty<>() {})); + F3, Integer, Unit> printer = PrintAll.of(witness(new Ty<>() {})); printer.apply("Items:", JavaList.of("apple", "banana", "cherry"), 0); Foldable foldableFwdList = witness(new Ty<>() {}); From 6eafa1f6b9b7a57c598bd4b931d32bff941f9452 Mon Sep 17 00:00:00 2001 From: "copilot-swe-agent[bot]" <198982749+Copilot@users.noreply.github.com> Date: Sun, 14 Dec 2025 12:09:51 +0000 Subject: [PATCH 4/4] Replace Void with Unit in FwdList#forEach - Updated FwdList#forEach to use Unit instead of Void - Replaced null returns with unit() calls - Added static import for Unit.unit() - Eliminates all null usage from FwdList#forEach - All tests passing Co-authored-by: Garciat <118277+Garciat@users.noreply.github.com> --- src/main/java/com/garciat/typeclasses/types/FwdList.java | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/main/java/com/garciat/typeclasses/types/FwdList.java b/src/main/java/com/garciat/typeclasses/types/FwdList.java index ccd5c48..44d667d 100644 --- a/src/main/java/com/garciat/typeclasses/types/FwdList.java +++ b/src/main/java/com/garciat/typeclasses/types/FwdList.java @@ -1,6 +1,7 @@ package com.garciat.typeclasses.types; import static com.garciat.typeclasses.api.TypeClass.Witness.Overlap.OVERLAPPING; +import static com.garciat.typeclasses.types.Unit.unit; import com.garciat.typeclasses.api.hkt.Kind; import com.garciat.typeclasses.api.hkt.Kind.KArr; @@ -47,12 +48,12 @@ default B foldl(B identity, BiFunction f) { } default void forEach(Consumer action) { - this.match( - () -> null, + this.match( + () -> unit(), (head, tail) -> { action.accept(head); tail.forEach(action); - return null; + return unit(); }); }