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 2021/11/30 17:13:26 UTC

[groovy] branch master updated: GROOVY-10396: StaticImportVisitor: static context skips instance methods

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

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


The following commit(s) were added to refs/heads/master by this push:
     new ff0f23d  GROOVY-10396: StaticImportVisitor: static context skips instance methods
ff0f23d is described below

commit ff0f23dad7011e8f006a666b5cf9bece538f689d
Author: Eric Milles <er...@thomsonreuters.com>
AuthorDate: Tue Nov 30 10:54:18 2021 -0600

    GROOVY-10396: StaticImportVisitor: static context skips instance methods
---
 .../groovy/control/StaticImportVisitor.java        | 11 ++--
 src/test/groovy/StaticImportTest.groovy            | 59 +++++++++++++++++++++-
 2 files changed, 65 insertions(+), 5 deletions(-)

diff --git a/src/main/java/org/codehaus/groovy/control/StaticImportVisitor.java b/src/main/java/org/codehaus/groovy/control/StaticImportVisitor.java
index fc4838c..0fad93f 100644
--- a/src/main/java/org/codehaus/groovy/control/StaticImportVisitor.java
+++ b/src/main/java/org/codehaus/groovy/control/StaticImportVisitor.java
@@ -245,17 +245,20 @@ public class StaticImportVisitor extends ClassCodeExpressionTransformer {
         Expression method = transform(mce.getMethod());
         Expression args = transform(mce.getArguments());
 
+        // GROOVY-10396: skip the instance method checks when the context is static with-respect-to current class
+        boolean staticWrtCurrent = inSpecialConstructorCall || currentMethod != null && currentMethod.isStatic();
+
         if (mce.isImplicitThis()) {
             String name = mce.getMethodAsString();
-            if (currentClass.tryFindPossibleMethod(name, args) == null
-                    && currentClass.getOuterClasses().stream().noneMatch(oc -> oc.tryFindPossibleMethod(name, args) != null)) {
+            boolean thisOrSuperMethod = staticWrtCurrent ? hasPossibleStaticMethod(currentClass, name, args, true) : currentClass.tryFindPossibleMethod(name, args) != null;
+            if (!thisOrSuperMethod && currentClass.getOuterClasses().stream().noneMatch(oc -> oc.tryFindPossibleMethod(name, args) != null)) {
                 Expression result = findStaticMethodImportFromModule(method, args);
                 if (result != null) {
                     setSourcePosition(result, mce);
                     return result;
                 }
             }
-        } else if (currentMethod != null && currentMethod.isStatic() && isSuperExpression(object)) {
+        } else if (staticWrtCurrent && isSuperExpression(object)) {
             Expression result = new MethodCallExpression(new ClassExpression(currentClass.getSuperClass()), method, args);
             result.setSourcePosition(mce);
             return result;
@@ -264,7 +267,7 @@ public class StaticImportVisitor extends ClassCodeExpressionTransformer {
         if (method instanceof ConstantExpression && ((ConstantExpression) method).getValue() instanceof String && (mce.isImplicitThis() || isThisOrSuper(object))) {
             String methodName = (String) ((ConstantExpression) method).getValue();
 
-            boolean foundInstanceMethod = (currentMethod != null && !currentMethod.isStatic() && currentClass.hasPossibleMethod(methodName, args));
+            boolean foundInstanceMethod = !staticWrtCurrent && currentClass.hasPossibleMethod(methodName, args);
 
             Predicate<ClassNode> hasPossibleStaticMember = cn -> {
                 if (hasPossibleStaticMethod(cn, methodName, args, true)) {
diff --git a/src/test/groovy/StaticImportTest.groovy b/src/test/groovy/StaticImportTest.groovy
index 6603772..5110c69 100644
--- a/src/test/groovy/StaticImportTest.groovy
+++ b/src/test/groovy/StaticImportTest.groovy
@@ -176,7 +176,7 @@ final class StaticImportTest extends groovy.test.GroovyTestCase {
                 class Foo {
                     static x = 'foo'
                     static getX() { x + '_get' }
-                    static void setX(newx) { x = newx + '_set' } 
+                    static void setX(newx) { x = newx + '_set' }
                 }
                 assert x == 'foo_get'
                 x = 'bar'
@@ -522,6 +522,56 @@ final class StaticImportTest extends groovy.test.GroovyTestCase {
         assert err =~ /Apparent variable 'c' was found in a static scope but doesn't refer to a local variable, static field or class/
     }
 
+    // GROOVY-10396
+    void testStaticImportVersusThisOrSuperMethod1() {
+        assertScript '''
+            import static groovy.Extension10396.*
+
+            static void test() {
+                println 'x'
+            }
+            strings.clear()
+            test()
+
+            assert 'x' in strings
+        '''
+    }
+
+    // GROOVY-10396
+    void testStaticImportVersusThisOrSuperMethod2() {
+        assertScript '''
+            import static groovy.Extension10396.*
+
+            def obj = new Object() { // outer class extends Script
+                String toString() {
+                    println 'AIC::x'
+                    super.toString()
+                }
+            }
+            strings.clear()
+            obj.toString()
+
+            assert 'x' !in strings
+        '''
+    }
+
+    // GROOVY-10396
+    void testStaticImportVersusThisOrSuperMethod3() {
+        assertScript '''
+            import static groovy.Extension10396.*
+
+            static void println(String s) { // static overload
+            }
+            static void test() {
+                println 'x'
+            }
+            strings.clear()
+            test()
+
+            assert 'x' !in strings
+        '''
+    }
+
     void testStaticStarImportOfStaticInnerClass() {
         assert Inner1.class.name == 'groovy.Outer1$Inner1'
     }
@@ -642,3 +692,10 @@ class HolderWrapper {
         holder[name] = value
     }
 }
+
+class Extension10396 {
+    static final List<String> strings = []
+    static void println(String s) {
+        strings << s
+    }
+}