2

I have the following Groovy script as test.groovy:

import test.Vehicle

def ok=new Vehicle();
def test=new Vehicle.Deserializer();

println "Hello, world!"

And, I have code/test/Vehicle.groovy, with the following class definition:

package test;

public class Vehicle {
  public static class Deserializer {
  }
}

However, the following command fails:

groovy -cp code/ test.groovy

(groovy -v reports 2.4.7)

I would expect it to succeed and print "Hello, world". Instead, I get:

org.codehaus.groovy.control.MultipleCompilationErrorsException: startup failed:
/tmp/test.groovy: 4: unable to resolve class Vehicle.Deserializer 
 @ line 4, column 10.
   def test=new Vehicle.Deserializer();
            ^

1 error

Since the script is not failing on the prior line, Groovy is finding the Vehicle class without issue. It is just not finding the Deserializer static class.

However, this script works just fine:

public class Vehicle {
  public static class Deserializer {
  }
}

def ok=new Vehicle();
def test=new Vehicle.Deserializer();

println "Hello, world!"

Is there something that I need to be doing to allow Groovy to work with static classes, when the static class (and its outer class) are defined in a separate Groovy file?


UPDATE: I found this issue and can confirm that Groovy can at least sort of see the Deserializer class:

import test.Vehicle;
import static test.Vehicle.Deserializer;

println Deserializer.class.name

def ok=new Vehicle();
// def test=new Vehicle.Deserializer();

println "Hello, world!"

This works as expected:

test.Vehicle$Deserializer
Hello, world!

However, uncommenting the def test=new Vehicle.Deserializer(); still gives me the error, as does changing that to def test=new Deserializer(); (given the import static).

CommonsWare
  • 986,068
  • 189
  • 2,389
  • 2,491
  • I have not tested myself but have you tried importing the static class explicitly as well in `test.groovy` as `import static test.Vehicle.Deserializer` ? – dmahapatro Nov 29 '16 at 19:21
  • @dmahapatro: `import test.Vehicle.Deserializer` results in a second "unable to resolve class" error, pointing at that line. `import static test.Vehicle.Deserializer`, strangely, does *not* cause a second error, but it does not clear up the first one. – CommonsWare Nov 29 '16 at 19:27
  • Yes, witnessed the same. I was also trying to compile `Vehicle.groovy` by `groovyc` before executing `test.groovy`, but I still see it complaining. It may be an issue. – dmahapatro Nov 29 '16 at 19:34
  • Having `test.groovy` in the same package as `Vehicle.groovy`, compiling `Vehicle.groovy` and then running `groovy test.groovy` works!! – dmahapatro Nov 29 '16 at 19:42
  • 1
    @dmahapatro: I am not sure what "alongside" means. If you mean "not in a package, like the `test` that I am using", that is not an option in my case, and that resembles my working script (last code snippet in the question). – CommonsWare Nov 29 '16 at 19:45
  • Updated above comment to say "in the same package as" – dmahapatro Nov 29 '16 at 19:46
  • @dmahapatro: I just added a `package test` line to the top of the first script from my question. I still get the same error message. Is there something more to putting a non-class Groovy script in a package? – CommonsWare Nov 29 '16 at 19:51
  • You need to compile `Vehicle.groovy` by using `groovyc Vehicle.groovy`, after which it should work. It worked for me. – dmahapatro Nov 29 '16 at 19:58
  • @dmahapatro: I am trying to use Groovy in interpreted mode, not compiled mode. But, thanks! – CommonsWare Nov 29 '16 at 20:00

1 Answers1

1

It looks like this is a known Groovy bug. If your static class has a zero-arguments constructor, you can work around this via newInstance():

import test.Vehicle;
import static test.Vehicle.Deserializer;

def ok=new Vehicle();
def test=Deserializer.class.newInstance();

println "Hello, world!"
CommonsWare
  • 986,068
  • 189
  • 2,389
  • 2,491