Java compiler rejects variable declaration with parameterized inner class

I have Groovy code that works fine in the Groovy bytecode compiler, but the piece of Java it generates causes an error in the Java compiler. I think this is probably another mistake in the stack Groovy generator, but I really cannot understand why the Java compiler does not like the generated code.

Here's a truncated version of the generated Java class (please excuse the ugly formatting):

@groovy.util.logging.Log4j() public abstract class AbstractProcessingQueue <T> extends nz.ac.auckland.digitizer.AbstractAgent implements groovy.lang.GroovyObject { protected int retryFrequency; protected java.util.Queue<nz.ac.auckland.digitizer.AbstractProcessingQueue.ProcessingQueueMember<T>> items; public AbstractProcessingQueue (int processFrequency, int timeout, int retryFrequency) { super ((int)0, (int)0); } private enum ProcessState implements groovy.lang.GroovyObject { NEW, FAILED, FINISHED; } private class ProcessingQueueMember<E> extends java.lang.Object implements groovy.lang.GroovyObject { public ProcessingQueueMember (E object) {} } } 

The insult line in the generated code is as follows:

 protected java.util.Queue<nz.ac.auckland.digitizer.AbstractProcessingQueue.ProcessingQueueMember<T>> items; 

which produces the following compilation error:

 [ERROR] C:\Documents and Settings\Administrator\digitizer\target\generated-sources\groovy-stubs\main\nz\ac\auckland\digitizer\AbstractProcessingQueue.java:[14,96] error: improperly formed type, type arguments given on a raw type 

The index of column 96 in the compilation error indicates a parameterization <T> type ProcessingQueueMember . But ProcessingQueueMember not a raw type, as the compiler claims, it is a generic type:

 private class ProcessingQueueMember <E> extends java.lang.Object implements groovy.lang.GroovyObject { ... 

I am very confused why the compiler considers the type Queue<ProcessingQueueMember<T>> invalid. The Groovy source compiles fine, and the generated Java code looks perfectly correct for me. What am I missing here? Is this because the type in question is a nested class?

(in case anyone is interested, I filed this error report related to the problem in this question)

Edit: It turns out that it was a stub compiler error - this problem is now fixed in versions 1.8.9, 2.0.4 and 2.1, so if you still have this problem, just upgrade it to one of these versions. :)

+4
source share
2 answers

Since the ProcessingQueueMember class is a non-stationary inner class of AbstractProcessingQueue , its body can refer to a parameter of type T AbstractProcessingQueue . Thus, an unhandled reference to ProcessingQueueMember should provide both type arguments. For instance,

 protected java.util.Queue<AbstractProcessingQueue<T>.ProcessingQueueMember<T>> items; 

will compile. This code is probably overly generic. I believe that you really need one of these two alternatives:

  • Make ProcessingQueueMember<E> static (i.e. a nested class, not an inner class)
  • Remove type parameter from ProcessingQueueMember

I don't know anything about the groovy stub generator, but maybe there is some way to annotate your groovy code to express this?

+8
source

Perhaps there is no general type type of the class that contains the variable declaration ( protected java.util.Queue<nz.ac.auckland.digitizer.AbstractProcessingQueue.ProcessingQueueMember<T>> items; )?

0
source

All Articles