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 2022/09/03 23:54:53 UTC

[groovy] branch GROOVY_2_5_X updated: GROOVY-10114: STC: diamond inference: handle ternary without target type

This is an automated email from the ASF dual-hosted git repository.

emilles pushed a commit to branch GROOVY_2_5_X
in repository https://gitbox.apache.org/repos/asf/groovy.git


The following commit(s) were added to refs/heads/GROOVY_2_5_X by this push:
     new 5d60429a28 GROOVY-10114: STC: diamond inference: handle ternary without target type
5d60429a28 is described below

commit 5d60429a28f59eabf73986c3a919f8861dc1a0fc
Author: Eric Milles <er...@thomsonreuters.com>
AuthorDate: Tue Mar 15 15:33:04 2022 -0500

    GROOVY-10114: STC: diamond inference: handle ternary without target type
---
 .../transform/stc/StaticTypeCheckingVisitor.java   |  13 +-
 .../groovy/transform/stc/GenericsSTCTest.groovy    | 551 +++++++++++++++++----
 2 files changed, 464 insertions(+), 100 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 38c4bbadbe..67bb6291b4 100644
--- a/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java
+++ b/src/main/java/org/codehaus/groovy/transform/stc/StaticTypeCheckingVisitor.java
@@ -4182,12 +4182,17 @@ public class StaticTypeCheckingVisitor extends ClassCodeVisitorSupport {
             sourceType = getInferredReturnType(expr);
         }
 
+        if (expr instanceof ConstructorCallExpression) { // GROOVY-9972, GROOVY-9983
+            // GROOVY-10114: type parameter(s) could be inferred from call arguments
+            if (targetType == null) targetType = sourceType.getPlainNodeReference();
+            inferDiamondType((ConstructorCallExpression) expr, targetType);
+            return sourceType;
+        }
+
         if (targetType == null) return sourceType;
 
-        if (expr instanceof ConstructorCallExpression) {
-            inferDiamondType((ConstructorCallExpression) expr, targetType);
-        } else if (!isPrimitiveType(getUnwrapper(targetType)) && !OBJECT_TYPE.equals(targetType)
-                    && !sourceType.isGenericsPlaceHolder() && missesGenericsTypes(sourceType)) {
+        if (!isPrimitiveType(getUnwrapper(targetType)) && !OBJECT_TYPE.equals(targetType)
+                && !sourceType.isGenericsPlaceHolder() && missesGenericsTypes(sourceType)){
             // unchecked assignment with ternary/elvis, like "List<T> list = listOfT ?: []"
             // the inferred type is the RHS type "completed" with generics information from LHS
             return GenericsUtils.parameterizeType(targetType, sourceType.getPlainNodeReference());
diff --git a/src/test/groovy/transform/stc/GenericsSTCTest.groovy b/src/test/groovy/transform/stc/GenericsSTCTest.groovy
index 7ef859a5a5..62d6415254 100644
--- a/src/test/groovy/transform/stc/GenericsSTCTest.groovy
+++ b/src/test/groovy/transform/stc/GenericsSTCTest.groovy
@@ -152,7 +152,7 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         '''
     }
 
-    void testReturnTypeInference() {
+    void testReturnTypeInference1() {
         assertScript '''
             class Foo<U> {
                 U method() { }
@@ -162,13 +162,12 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         '''
     }
 
-    void testReturnTypeInferenceWithDiamond() {
+    void testReturnTypeInference2() {
         assertScript '''
-            class Foo<U> {
-                U method() { }
-            }
-            Foo<Integer> foo = new Foo<>()
-            Integer result = foo.method()
+        Object m() {
+          def s = '1234'
+          println 'Hello'
+        }
         '''
     }
 
@@ -291,7 +290,7 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
                 U method() { }
             }
             Foo<Integer> foo = new Foo<>()
-            Integer result = foo.method()
+            Integer integer = foo.method()
         '''
     }
 
@@ -333,6 +332,60 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         '''
     }
 
+    // GROOVY-6232
+    void testDiamondInferrenceFromConstructor5() {
+        ['"a",new Object()', 'new Object(),"b"', '"a","b"'].each { args ->
+            assertScript """
+                class C<T> {
+                    C(T x, T y) {
+                    }
+                }
+                C<Object> c = new C<>($args)
+            """
+        }
+    }
+
+    // GROOVY-9948
+    void testDiamondInferrenceFromConstructor6() {
+        assertScript '''
+            class C<T> {
+                T p
+                C(T p) {
+                    this.p = p
+                }
+            }
+
+            C<Integer> c = new C<>(1)
+            assert c.p < 10
+        '''
+    }
+
+    // GROOVY-9948
+    void testDiamondInferrenceFromConstructor7() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+
+            C<Integer> c = new C<>(1)
+            assert c.p < 10
+        '''
+    }
+
+    @NotYetImplemented // GROOVY-9984
+    void testDiamondInferrenceFromConstructor7a() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+
+            C<Integer> c = new C<>(null)
+            assert c.p === null
+        '''
+    }
+
     // GROOVY-9956
     void testDiamondInferrenceFromConstructor8() {
         assertScript '''
@@ -348,6 +401,42 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         '''
     }
 
+    // GROOVY-9996
+    void testDiamondInferrenceFromConstructor8a() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            interface I { }
+            class D implements I { }
+            void test(C<I> c) { assert c.p instanceof D }
+
+            I i = new D() // infers D for "i"
+            def ci = new C<>(i) // infers C<D> for "ci"
+            test(ci)
+        '''
+    }
+
+    // GROOVY-10011
+    void testDiamondInferrenceFromConstructor8b() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            interface I { }
+            class D implements I { }
+
+            void test(I i) {
+                if (i instanceof D) {
+                    C<D> cd = new C<>(i)
+                }
+            }
+            test(new D())
+        '''
+    }
+
     void testDiamondInferrenceFromConstructor9() {
         assertScript '''
             abstract class A<X> { }
@@ -380,6 +469,131 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         'Incompatible generic argument types. Cannot assign java.util.HashSet <java.util.ArrayList> to: java.util.Set <List>'
     }
 
+    // GROOVY-9972
+    void testDiamondInferrenceFromConstructor9a() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                public String f = 'D#f'
+            }
+            C<D> cd = true ? new C<>(new D()) : new C<>(new D())
+            assert cd.p.f.toLowerCase() == 'd#f'
+        '''
+
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                public String f = 'D#f'
+            }
+            boolean b = false
+            C<D> cd = b ? new C<>(new D()) : (b ? new C<>((D) null) : new C<>(new D()))
+            assert cd.p.f.toLowerCase() == 'd#f'
+        '''
+
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                public String f = 'D#f'
+            }
+            def cd
+            if (true) {
+                cd = new C<>(new D())
+            } else {
+                cd = new C<>((D) null)
+            }
+            assert cd.p.f.toLowerCase() == 'd#f'
+        '''
+
+        assertScript '''
+            @groovy.transform.TupleConstructor
+            class C {
+                List<D> list
+            }
+            class D {
+            }
+            List test(C... array) {
+                // old code used "List<D> many" as target for guts of closure
+                List<D> many = array.collectMany { it.list ?: [] }
+            }
+            def result = test(new C(), new C(list:[new D()]))
+            assert result.size() == 1
+        '''
+    }
+
+    @NotYetImplemented
+    void testDiamondInferrenceFromConstructor9b() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                public String f = 'D#f'
+            }
+            def foo = { flag, C<D> cd = (flag ? new C<>(new D()) : new C<>(new D())) ->
+                cd.p.f.toLowerCase()
+            }
+            assert foo.call(true) == 'd#f'
+        '''
+
+        shouldFailWithMessages '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                public String f = 'D#f'
+            }
+            def foo = { flag, C<D> cd = (flag ? new C<>(new D()) : new C<>(new Object())) ->
+                cd.p.f.toLowerCase()
+            }
+        ''',
+        'Incompatible generic argument types. Cannot assign C<? extends java.lang.Object> to: C<D>'
+    }
+
+    @NotYetImplemented // GROOVY-9963
+    void testDiamondInferrenceFromConstructor10() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            static void m(String s) {
+                assert s.isEmpty()
+            }
+            m(new C<>("").p)
+        '''
+    }
+
+    @NotYetImplemented // GROOVY-10080
+    void testDiamondInferrenceFromConstructor11() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            class D {
+                int m(Object[] objects) {
+                    42
+                }
+            }
+            def closure = { ->
+                new C<>(new D())
+            }
+            def result = closure().p.m(new BigDecimal[0]) // Cannot find matching method Object#m(...)
+            assert result == 42
+        '''
+    }
+
     // GROOVY-10086
     void testDiamondInferrenceFromConstructor12() {
         shouldFailWithMessages '''
@@ -397,6 +611,180 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         'Cannot call', 'm(int, C <D>[]) with arguments [int, C <java.lang.Integer>]'
     }
 
+    // GROOVY-9970
+    void testDiamondInferrenceFromConstructor13() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class A<T extends B> {
+                T p
+            }
+            class B {
+            }
+            class C<T extends Number> {
+                void test(T n) {
+                    A<B> x = new A<>(new B())
+                    def closure = { ->
+                        A<B> y = new A<>(new B())
+                    }
+                    closure.call()
+                }
+            }
+            new C<Long>().test(42L)
+        '''
+    }
+
+    // GROOVY-9983
+    void testDiamondInferrenceFromConstructor14() {
+        String types = '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class A<T> {
+                T p
+            }
+            class B {
+            }
+            class C {
+                static m(A<B> a_of_b) {
+                }
+            }
+        '''
+
+        assertScript types + '''
+            class E extends B {
+            }
+            boolean flag = true
+
+            A<B> v = new A<>(null)
+            A<B> w = new A<>(new B())
+            A<B> x = new A<>(new E())
+            A<B> y = flag ? new A<>(new B()) : new A<>(new B())
+            A<B> z = flag ? new A<>(new B()) : new A<>(new E())
+
+            C.m(new A<>(null))
+            C.m(new A<>(new B()))
+            C.m(new A<>(new E()))
+            C.m(flag ? new A<>(new B()) : new A<>(new B()))
+            C.m(flag ? new A<>(new B()) : new A<>((B)null))
+            C.m(flag ? new A<>(new B()) : new A<>((B)new E())) // Cannot call m(A<B>) with arguments [A<? extends B>]
+        '''
+
+        shouldFailWithMessages types + '''
+            A<B> x = new A<>(new Object())
+            A<B> y = true ? new A<>(new B()) : new A<>(new Object())
+
+            C.m(new A<>(new Object()))
+            C.m(true ? new A<>(new B()) : new A<>(new Object()))
+        ''',
+        'Cannot assign A <java.lang.Object> to: A <B>',
+        'Cannot assign A <? extends java.lang.Object> to: A <B>',
+        'Cannot call C#m(A <B>) with arguments [A <java.lang.Object>]',
+        'Cannot call C#m(A <B>) with arguments [A <? extends java.lang.Object>]'
+    }
+
+    // GROOVY-10114
+    void testDiamondInferrenceFromConstructor14a() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class A<T> {
+              T p
+            }
+            class B {
+                Character m() {
+                    (Character) '!'
+                }
+            }
+            (false ? new A<B>(new B()) : new A<>(new B())).p.m()
+            (false ? new A< >(new B()) : new A<>(new B())).p.m()
+            def a = (true ? new A<>(new B()) : new A<>(new B()))
+            assert a.p.m() == (char)'!'
+        '''
+    }
+
+    @NotYetImplemented // GROOVY-9995
+    void testDiamondInferrenceFromConstructor15() {
+        [
+            ['Closure<A<Long>>', 'java.util.concurrent.Callable<A<Long>>'],
+            ['new A<>(42L)', 'return new A<>(42L)']
+        ].combinations { functionalType, returnStmt ->
+            assertScript """
+                @groovy.transform.TupleConstructor(defaults=false)
+                class A<T extends Number> {
+                    T p
+                }
+                $functionalType callable = { ->
+                    $returnStmt
+                }
+                Long n = callable.call().p
+                assert n == 42L
+            """
+        }
+    }
+
+    // GROOVY-10283
+    void testDiamondInferrenceFromConstructor16() {
+        assertScript '''
+            class A<T1, T2> {
+            }
+            class B<T1 extends Number, T2 extends A<C, ? extends T1>> {
+                T2 t
+                B(T2 t) {
+                    this.t  = t
+                }
+            }
+            class C {
+            }
+
+            new B<Integer,A<C,Integer>>(new A<>())
+        '''
+    }
+
+    // GROOVY-10291
+    void testDiamondInferrenceFromConstructor17() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class A<X> {
+                X x
+            }
+            class B<Y> {
+                def m(Y y) { null }
+                def test() {
+                    def c = { Y yy -> null }
+
+                    Y y = null
+                    m(new A<>(y).x) // works
+                    c(new A<>(y).x) // fails
+                }
+            }
+            new B().test()
+        '''
+    }
+
+    @NotYetImplemented // GROOVY-10228
+    void testDiamondInferrenceFromConstructor18() {
+        assertScript '''
+            @groovy.transform.TupleConstructor(defaults=false)
+            class C<T> {
+                T p
+            }
+            def m(Number n) {
+                'works'
+            }
+            def x = 12345
+            x = m(new C<>(x).getP()) // Cannot find matching method
+            assert x == 'works'
+        '''
+    }
+
+    // GROOVY-10323
+    void testDiamondInferrenceFromConstructor19() {
+        assertScript '''
+            class C<T> {
+            }
+            def <T,T> T m(C<T> c) {
+            }
+            Number n = m(new C<>())
+        '''
+    }
+
     // GROOVY-10324
     void testDiamondInferrenceFromConstructor20() {
         assertScript '''
@@ -547,93 +935,64 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
         '''
     }
 
-    // GROOVY-9972
-    void testDiamondInferrenceFromConstructor10() {
+    // GROOVY-10266
+    void testDiamondInferrenceFromConstructor30() {
         assertScript '''
-            @groovy.transform.TupleConstructor
-            class C<T> {
-                T p
-            }
-            class D {
-                public String f = 'D#f'
+            @groovy.transform.TupleConstructor(defaults=false)
+            class A<T> {
+                T t
             }
-            C<D> cd = true ? new C<>(new D()) : new C<>(new D())
-            assert cd.p.f.toLowerCase() == 'd#f'
-        '''
+            class B<U> {
+                def m() {
+                    U v = null
+                    U w = new A<>(v).t
 
-        assertScript '''
-            @groovy.transform.TupleConstructor
-            class C<T> {
-                T p
-            }
-            class D {
-                public String f = 'D#f'
+                    String x = ""
+                    String y = new A<>(x).t
+                }
             }
-            boolean b = false
-            C<D> cd = b ? new C<>(new D()) : (b ? new C<>((D) null) : new C<>(new D()))
-            assert cd.p.f.toLowerCase() == 'd#f'
+            new B<String>().m()
         '''
+    }
 
+    // GROOVY-10662
+    void testDiamondInferrenceFromConstructor31() {
         assertScript '''
-            @groovy.transform.TupleConstructor
-            class C {
-                List<D> list
-            }
-            class D {
+            class A<X, T> {
+                A(T t, X x) {}
+                void m(X x) {}
             }
-            List test(C... array) {
-                // old code used "List<D> many" as target for guts of closure
-                List<D> many = array.collectMany { it.list ?: [] }
+            class B<T extends Number> {
+                void test() {
+                    T t = (T) null
+                    Character c = 'c'
+                    def a = new A<>(c, t)
+                    a.m((T) null) // Cannot find matching method A#m(T)
+                }
             }
-            def result = test(new C(), new C(list:[new D()]))
-            assert result.size() == 1
+            new B<Integer>().test()
         '''
     }
 
-    // GROOVY-9983
-    void testDiamondInferrenceFromConstructor11() {
-        String types = '''
-            @groovy.transform.TupleConstructor(defaults=false)
-            class A<T> {
-                T p
-            }
-            class B {
+    @NotYetImplemented // GROOVY-10633
+    void testDiamondInferrenceFromConstructor32() {
+        assertScript '''
+            class A<T, Y> {
+                public B<Y> f
+                A(B<Y> b_of_y, T t) {
+                    this.f = b_of_y
+                }
             }
-            class C {
-                static m(A<B> a_of_b) {
+            class B<T> {
+                void m(T t) {
                 }
             }
-        '''
-
-        assertScript types + '''
-            class E extends B {
+            <T extends Number> void test() {
+                def x = new B<T>()
+                new A<>(x, '').f.m((T) null)
             }
-            boolean flag = true
-
-            A<B> v = new A<>(null)
-            A<B> w = new A<>(new B())
-            A<B> x = new A<>(new E())
-            A<B> y = flag ? new A<>(new B()) : new A<>(new B())
-            A<B> z = flag ? new A<>(new B()) : new A<>(new E())
-
-            C.m(new A<>(null))
-            C.m(new A<>(new B()))
-            C.m(new A<>(new E()))
-            C.m(flag ? new A<>(new B()) : new A<>(new B()))
-            C.m(flag ? new A<>(new B()) : new A<>(new E())) // Cannot call m(A<B>) with arguments [A<? extends B>]
+            test()
         '''
-
-        /*shouldFailWithMessages types + '''
-            A<B> x = new A<>(new Object())
-            A<B> y = true ? new A<>(new B()) : new A<>(new Object())
-
-            C.m(new A<>(new Object()))
-            C.m(true ? new A<>(new B()) : new A<>(new Object()))
-        ''',
-        'Cannot assign A<java.lang.Object> to: A<B>',
-        'Cannot assign A<? extends java.lang.Object> to: A<B>',
-        'Cannot call C#m(A<B>) with arguments [A<java.lang.Object>]',
-        'Cannot call C#m(A<B>) with arguments [A<? extends java.lang.Object>]'*/
     }
 
     // GROOVY-10280
@@ -688,13 +1047,15 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
     void testLinkedListWithListArgumentAndWrongElementTypes() {
         shouldFailWithMessages '''
             List<String> list = new LinkedList<String>([1,2,3])
-        ''', 'Cannot call java.util.LinkedList <String>#<init>(java.util.Collection <java.lang.Object extends java.lang.String>) with arguments [java.util.List <java.lang.Integer>]'
+        ''',
+        'Cannot call java.util.LinkedList <String>#<init>(java.util.Collection <java.lang.Object extends java.lang.String>) with arguments [java.util.List <java.lang.Integer>]'
     }
 
     void testCompatibleGenericAssignmentWithInference() {
         shouldFailWithMessages '''
             List<String> elements = ['a','b', 1]
-        ''', 'Incompatible generic argument types. Cannot assign java.util.List <java.io.Serializable> to: java.util.List <String>'
+        ''',
+        'Cannot assign java.util.List <java.io.Serializable> to: java.util.List <String>'
     }
 
     void testGenericAssignmentWithSubClass() {
@@ -706,7 +1067,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
     void testGenericAssignmentWithSubClassAndWrongGenericType() {
         shouldFailWithMessages '''
             List<Integer> list = new groovy.transform.stc.GenericsSTCTest.MyList()
-        ''', 'Incompatible generic argument types'
+        ''',
+        'Incompatible generic argument types'
     }
 
     void testAddShouldBeAllowedOnUncheckedGenerics() {
@@ -722,7 +1084,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
     void testAssignmentShouldFailBecauseOfLowerBound() {
         shouldFailWithMessages '''
             List<? super Number> list = ['string']
-        ''', 'Number'
+        ''',
+        'Cannot assign java.util.List <java.lang.String> to: java.util.List <? super java.lang.Number>'
     }
 
     void testGroovy5154() {
@@ -783,16 +1146,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
             class FooBound {
             }
             new Foo()
-        ''', 'Cannot find matching method FooWithGenerics#say(java.lang.Object)'
-    }
-
-    void testVoidReturnTypeInferrence() {
-        assertScript '''
-        Object m() {
-          def s = '1234'
-          println 'Hello'
-        }
-        '''
+        ''',
+        'Cannot find matching method FooWithGenerics#say(java.lang.Object)'
     }
 
     // GROOVY-5237
@@ -901,7 +1256,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
 
             A<String, Integer> a = new B()
             a.test()
-        ''', 'Cannot call A <String, Integer>#<init>(java.lang.Class <String>, java.lang.Class <Integer>) with arguments [java.lang.Class <java.lang.Integer>, java.lang.Class <java.lang.String>]'
+        ''',
+        'Cannot call A <String, Integer>#<init>(java.lang.Class <String>, java.lang.Class <Integer>) with arguments [java.lang.Class <java.lang.Integer>, java.lang.Class <java.lang.String>]'
     }
 
     void testPutWithPrimitiveValue() {
@@ -1124,7 +1480,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
                 }
             }
             new Test()
-        ''', 'Cannot find matching method java.lang.Object#getAt(int)'
+        ''',
+        'Cannot find matching method java.lang.Object#getAt(int)'
     }
 
     void testAssignmentOfNewInstance() {
@@ -1164,7 +1521,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
             }
         }
         new ClassB()
-        ''', 'Cannot call <X> groovy.transform.stc.GenericsSTCTest$ClassA <Long>#bar(java.lang.Class <Long>) with arguments [java.lang.Class <? extends java.lang.Object>]'
+        ''',
+        'Cannot call <X> groovy.transform.stc.GenericsSTCTest$ClassA <Long>#bar(java.lang.Class <Long>) with arguments [java.lang.Class <? extends java.lang.Object>]'
     }
 
     // GROOVY-8961
@@ -1200,7 +1558,8 @@ class GenericsSTCTest extends StaticTypeCheckingTestCase {
             void test() {
               m = Collections.<Integer>emptyList()
             }
-        ''', '[Static type checking] - Cannot assign value of type java.util.List <Integer> to variable of type java.util.List <String>'
+        ''',
+        'Cannot assign value of type java.util.List <Integer> to variable of type java.util.List <String>'
     }
 
     // GROOVY-9734