I have an application that has multiple screens and each screen is selected via a button. Each screen contains pretty heavy-weight components so it's important that only the activate screen is in memory - all others should be available for garbage collection.
The app uses Spring for the glue and currently it switches screens using getBean():
//event handler for a specific button
public void actionPerformed(Event e) {
setScreen( (Screen) applicationContext.getBean("screen1"));
}
"screen1" is a prototype bean so a new instance of the screen is created when the button is pressed. Also, setScreen() is the only place where a reference to Screen is maintained in the app so the previously active screen will be available for garbage collection. I haven't tested this yet but I expect it will work fine - no rocket science here!
The problem is - after reading this page about why getBean() is considered bad - I'm wondering whether there is a more idiomatic way to acheive the same results while removing the dependency on getBean().
I have looked at method injection and it looks to me to introduce complexity with little benefit. It's another concept to learn, more magic, adds dependency on CGLIB, etc. If I really want to remove the dependency on Spring, I can just introduce an interface that exposes the getBean() method.
Is getBean() and method injection the only options in my case or have I missed something?
And if so, is getBean() really so bad?
Conclusion. Constructor injection makes code more robust. It allows us to create immutable objects, preventing NullPointerException s and other errors.
getBean. Object getBean(String name) throws BeansException. Return an instance, which may be shared or independent, of the specified bean. This method allows a Spring BeanFactory to be used as a replacement for the Singleton or Prototype design pattern.
We can combine constructor-based and setter-based types of injection for the same bean. The Spring documentation recommends using constructor-based injection for mandatory dependencies, and setter-based injection for optional ones.
getBean() method. Simply put, as the name of the method also suggests, this is responsible for retrieving a bean instance from the Spring container.
Setter injection, property injection or constructor injection all create a loosely coupled application that is much easier to test through mocking. It also prevents any of your classes from having direct dependencies on Spring (or other IoC container) classes. It ends up just being a cleaner overall solution when you don't have to manually call getBean().
I think you should become comfortable with the notion of configuring dependencies. The "magic" is not really magic at all and is just something that you will become comfortable with as you use it.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With