Uploaded image for project: 'Groovy'
  1. Groovy
  2. GROOVY-7149

@CompileStatic 'Access to <property> is forbidden' with abstract base class and interface

    XMLWordPrintableJSON

Details

    • Bug
    • Status: Closed
    • Major
    • Resolution: Fixed
    • 2.3.7
    • 2.3.8, 2.4.0-beta-4
    • Static compilation
    • None
    • Ubuntu Linux 14.04.1 - 3.13.0-39-generic
      Groovy Version: 2.3.7 JVM: 1.8.0_05 Vendor: Oracle Corporation OS: Linux

    Description

      The CompileStatic annotation incorrectly reports the following error:

      org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
      compile_static_failure.groovy: 11: Access to Abstract#name is forbidden @ line 11, column 25.
           println "Y is called $y.name"
                                 ^
      1 error
      

      when executing the following coce:

      import groovy.transform.*
      
      test() 
      
      @CompileStatic
      def test() {
        I x = new ConcreteA()
        I y = System.currentTimeMillis() % 2 ? new ConcreteA() : new ConcreteB()
      
        println "X is called $x.name"
        println "Y is called $y.name"
      }
      
      public class ConcreteA extends Abstract { 
        String name
      }
      
      public class ConcreteB extends Abstract { 
        String name
      }
      
      abstract class Abstract implements I { 
        //abstract String getName()
      }
      
      interface I { 
        String getName()
      }
      

      The same code (plus a few semicolons) compiles fine in Java and also runs fine without the CompileStatic annotation. I haven't analyzed this very deeply, but this feels like a bug in the CompileStatic implementation.

      An interesting note is that for the variable x in the above code, there are no issues when accessing x.name. It seems that the CompileStatic code does type analysis, comes to the conclusion that the concrete type of variable y is either ConcrecteA or ConcreteB, then proceeds to find the largest common deniminator for the two which is abstract class Abstract, and then proceeds to complain about the fact that Abstract does not have method/property 'name'.

      Commenting in the commented out 'abstract String getName()' method on class Abstract 'fixes' the error.

      Attachments

        Activity

          People

            melix Cédric Champeau
            mbjarland Matias Bjarland
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

            Dates

              Created:
              Updated:
              Resolved: