Spring – How to PROPERLY inject Grails services using Spring resource.groovy

dependency-injectiongrailsjavabeansresourcesspring

Using Grails 2.2.1

I have the following Grails services defined:

package poc

class TestService {
    def helperService
}

class HelperService {
}

I have used the TestService as follow (resources.groovy):

test(poc.TestService) {
    
}

jmsContainer(org.springframework.jms.listener.DefaultMessageListenerContainer) {
    connectionFactory = jmsConnectionFactory
    destinationName = "Test"
    messageListener = test
    autoStartup = true
}

Everything works except for automatic injection of the helperService, as it is expected when the service create by Grails. The only way I can get it to work is to manually inject it as follow:

//added 
helper(poc.HelperService) {
}

//changed
test(poc.TestService) {
    helperSerivce = helper
}

The problem is that it is not injecting the same way as Grails does. My actual service is quite complex, and if I will have to inject everything manually, including all the dependencies.

Best Solution

Beans declared in resources.groovy are normal Spring beans and do not by default participate in autowiring. You can do so by setting the autowire property on them explicitly:

aBean(BeanClass) { bean ->
    bean.autowire = 'byName'
}

In your specific case, you don't need to define the testService bean in your resources.groovy, merely set up a reference to it from your jmsContainer bean like so:

jmsContainer(org.springframework.jms.listener.DefaultMessageListenerContainer) {
    connectionFactory = jmsConnectionFactory
    destinationName = "Test"
    messageListener = ref('testService') // <- runtime reference to Grails artefact
    autoStartup = true
}

This is documented in the "Grails and Spring" section of the Grails Documentation under "Referencing Existing Beans".