You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@groovy.apache.org by em...@apache.org on 2024/01/04 20:34:41 UTC
(groovy) branch GROOVY_3_0_X updated: GROOVY-11241: STC: first param is implicit receiver
This is an automated email from the ASF dual-hosted git repository.
emilles pushed a commit to branch GROOVY_3_0_X
in repository https://gitbox.apache.org/repos/asf/groovy.git
The following commit(s) were added to refs/heads/GROOVY_3_0_X by this push:
new 96f62e3068 GROOVY-11241: STC: first param is implicit receiver
96f62e3068 is described below
commit 96f62e3068cdacf5d7f5df10632fed48240e3dd8
Author: Eric Milles <er...@thomsonreuters.com>
AuthorDate: Thu Jan 4 14:20:27 2024 -0600
GROOVY-11241: STC: first param is implicit receiver
---
.../transform/stc/StaticTypeCheckingVisitor.java | 8 ++++
.../transform/stc/MethodReferenceTest.groovy | 51 +++++++++++++++++++++-
2 files changed, 57 insertions(+), 2 deletions(-)
diff --git a/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java b/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java
index 447daa360a..9cf9c36b86 100644
--- a/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java
+++ b/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java
@@ -5682,14 +5682,22 @@ public class StaticTypeCheckingVisitor extends ClassCodeVisitorSupport {
if (mn != null) {
ClassNode[] pTypes = collateMethodReferenceParameterTypes(mp, mn);
Map<GenericsTypeName, GenericsType> connections = new HashMap<>();
+ // GROOVY-11241: implicit receiver for "Optional::get" is resolved now
+ if (!mn.isStatic() && mp.getExpression() instanceof ClassExpression) {
+ ClassNode objectType = parameters[0].getType();
+ objectType = applyGenericsContext(placeholders, objectType);
+ extractGenericsConnections(connections, objectType, pTypes[0].redirect());
+ }
for (int i = 0, n = parameters.length; i < n; i += 1) {
// SAM parameters should align one-for-one with the referenced method's parameters
extractGenericsConnections(connections, parameters[i].getOriginType(), pTypes[i]);
}
// convert the method reference's generics into the SAM's generics domain
closureReturnType = applyGenericsContext(connections, closureReturnType);
+ pTypes = applyGenericsContext(connections, pTypes);
// apply known generics connections to the placeholders of the return type
closureReturnType = applyGenericsContext(placeholders, closureReturnType);
+ pTypes = applyGenericsContext(placeholders, pTypes); // and the parameters
expression = new ClosureExpression(Arrays.stream(pTypes).map(t -> new Parameter(t,"")).toArray(Parameter[]::new), null);
}
diff --git a/src/test/groovy/transform/stc/MethodReferenceTest.groovy b/src/test/groovy/transform/stc/MethodReferenceTest.groovy
index a35738ec23..f80c7c8be9 100644
--- a/src/test/groovy/transform/stc/MethodReferenceTest.groovy
+++ b/src/test/groovy/transform/stc/MethodReferenceTest.groovy
@@ -237,8 +237,35 @@ final class MethodReferenceTest {
'''
}
- @Test // class::instanceMethod -- GROOVY-11241
+ @Test // class::instanceMethod -- GROOVY-9803
void testFunctionCI9() {
+ assertScript imports + '''
+ class Try<X> { X x
+ static <Y> Try<Y> success(Y y) {
+ new Try<Y>(x: y)
+ }
+ def <Z> Try<Z> map(Function<? super X, ? extends Z> f) {
+ new Try<Z>(x: f.apply(x))
+ }
+ }
+
+ static <E> Set<E> asSet(E element) {
+ Collections.singleton(element)
+ }
+
+ @CompileStatic
+ Try<String> test() {
+ def try_of_str = Try.success('WORKS')
+ def try_of_opt = try_of_str.map(this::asSet)
+ try_of_str = try_of_opt.map{it.first().toLowerCase()}
+ }
+
+ assert test().x == 'works'
+ '''
+ }
+
+ @Test // class::instanceMethod -- GROOVY-11241
+ void testFunctionCI10() {
assertScript imports + '''
@Grab('io.vavr:vavr:0.10.4')
import io.vavr.control.*
@@ -254,6 +281,26 @@ final class MethodReferenceTest {
assert test().get() == 42
'''
+ assertScript imports + '''
+ class Try<X> { X x
+ static <Y> Try<Y> of(Supplier<? extends Y> s) {
+ new Try<Y>(x: s.get())
+ }
+ def <Z> Try<Z> mapTry(Function<? super X, ? extends Z> f) {
+ new Try<Z>(x: f.apply(x))
+ }
+ }
+
+ @CompileStatic
+ Try<String> test() {
+ def try_of = Try.of{Optional.of('works')}
+ def result = try_of.mapTry(Optional.&get) // Function<T,_> and Optional<T>
+ return result
+ }
+
+ assert test().x == 'works'
+ '''
+
assertScript imports + '''
@Grab('io.vavr:vavr:0.10.4')
import io.vavr.control.Try
@@ -280,7 +327,7 @@ final class MethodReferenceTest {
}
@Test // class::instanceMethod -- GROOVY-11259
- void testFunctionCI10() {
+ void testFunctionCI11() {
assertScript imports + '''
def consume(Set<String> keys){keys}
@CompileStatic