Reputation: 25797
I deployed a Grails 3.2.0 WAR on Tomcat 8.5.6 and JDK 1.8.0_91 with a simple controller having following code:
package com.test
class MailController {
static responseFormats = ['json']
def index() {
Map headers = (request.headerNames as List).collectEntries { // It fails on this line
return [(it): request.getHeader(it)]
}
println "Incoming email $headers"
render status: 200
}
}
This code fails with the following exception:
Caused by: java.lang.NoClassDefFoundError: groovy/lang/GroovyObject
at java.lang.ClassLoader.defineClass(ClassLoader.java:763)
at java.lang.ClassLoader.defineClass(ClassLoader.java:642)
at groovy.util.ProxyGenerator.instantiateDelegateWithBaseClass(ProxyGenerator.java:225)
at groovy.util.ProxyGenerator.instantiateDelegateWithBaseClass(ProxyGenerator.java:193)
at groovy.util.ProxyGenerator.instantiateDelegate(ProxyGenerator.java:185)
at groovy.util.ProxyGenerator.instantiateDelegate(ProxyGenerator.java:181)
at org.grails.web.converters.ConverterUtil.invokeOriginalAsTypeMethod(ConverterUtil.java:161)
at org.grails.web.converters.ConvertersExtension.asType(ConvertersExtension.groovy:56)
at com.test.MailController.index(MailController.groovy:7)
at org.grails.core.DefaultGrailsControllerClass$MethodHandleInvoker.invoke(DefaultGrailsControllerClass.java:222)
at org.grails.core.DefaultGrailsControllerClass.invoke(DefaultGrailsControllerClass.java:187)
at org.grails.web.mapping.mvc.UrlMappingsInfoHandlerAdapter.handle(UrlMappingsInfoHandlerAdapter.groovy:90)
at org.springframework.web.servlet.DispatcherServlet.doDispatch(DispatcherServlet.java:963)
... 14 common frames omitted
Caused by: java.lang.ClassNotFoundException: groovy.lang.GroovyObject
at java.net.URLClassLoader.findClass(URLClassLoader.java:381)
at java.lang.ClassLoader.loadClass(ClassLoader.java:424)
... 27 common frames omitted
Before building the WAR file, I've changed the embedded tomcat to provided
in build.gradle
and also commented the groovy-ant
dependency related to grails-core#10196
I see a answer here but that didn't worked and the above code is working fine when we run via grails run-app
.
Update
I shorted down the issue. It is failing on this part only request.headerNames as List
Upvotes: 1
Views: 209
Reputation: 9
I am pretty sure the problem is with the use of "as List". Mostly because Grails will overwrite Groovy's asType implementation which makes the "as X" coercion syntax work.
Grails does this to add support for things like JSON for marshalling known Grails types to web transport formats. Unfortunately, in doing so Grails also breaks any asType function you might have declared yourself. Or in this case Groovy itself already declared for converting an Enumeration into a List.
It's quite annoying as Grails is effectively breaking existing contracts here and forcing you to modify upstream code to allow it to run on Grails. That or dump Grails because it doesn't play nice with perfectly valid Groovy code.
I believe replacing "as List" with .asType(List)
won't even fix the issue as you're still invoking the same code. At best you could try .collect([]) {it}
instead. It may not be necessary to add the empty array as the first argument to collect.
Upvotes: 1