The Grails depedency injection inheritance pitfall
This blog post is about a small pitfall you should be aware of when combining dependency injection in Grails with inheritance.
I think the problem is best explained with a piece of example code. So let’s look at the following two definitions of Grails controllers.
class FooController { TestService testService def foo() { // do something with testService } }
class BarController extends FooController { TestService testService def bar() { // do something with testService } }
Both controllers look nearly identical. The only difference is that BarController extends FooController. Now assume we have an instance of BarController and we want to call the methods bar() and foo() on it. Guess what happens?
The call of bar() works fine while the call of foo() throws a NullPointerException because testService is null.
testService is a standard Groovy property. This means that the testService fields will become private and getter / setter methods are generated for both controllers. The getter / setter of BarController override the getter / setter of FooController. So whenever the dependency is injected using setTestService() only BarController retrieves the TestService instance. This is nothing special about Grails controllers, it works the same for services and other Groovy classes.
The solution is easy: Remove the testService dependency from BarController. Whenever testService is accessed in BarController, it will use the appropriate getter of FooController and everything works.
In this simple example the problem is quite obvious and can be easily solved. However, if your classes become larger this can be a bit tricky to debug. Assume you have a base class with multiple sub classes. Whenever you want to add a new dependency to your base class, you have to check all the subclasses. If one of the sub classes already defines the same dependency you have to remove it or it will not be available in your base class.
Reference: | The Grails depedency injection inheritance pitfall from our JCG partner Michael Scharhag at the mscharhag, Programming and Stuff blog. |