Java web application developers often face the need to inject a regular Spring bean into a non-Spring-managed artifact like a Servlet or a JSP tag.. If you browse the web for you find various quite outdated solutions to it. No offense, by the time being these were quite appropriate solutions. One of them you’ll probably will find is the following:
public class MyServlet extends HttpServlet {
private MyService service;
@Override
public void init(ServletConfig config) {
ServletContext context =
config.getServletContext();
ApplicationContext ctx =
WebApplicationContextUtils.
getRequiredWebApplicationContext(context);
service = ctx.getBean(MyService.class);
}
}
Let’s recap what we just have done. First we need to get access to the ServletContext
of the web application. A Spring WebApplicationContext
that was registered by a ContextLoaderListener
will be registered in the ServletContext
under a special name the framework knows, so that WebApplicationContextUtils
can then look it up and hand it out to you to manually retrieve Spring beans from it.
Okay, that get’s the job done. But we can reduce the effort and go a much nicer way, that reduces the amount of boilerplate even more. Spring 2.5.1 introduced a tiny helperclass SpringBeanAutowiringSupport
which is residing in org.springframework.web.context.support
spending a rather unregarded life. It offers a method processInjectionBasedOnCurrentContext(Object target)
that automatically injects Spring beans to properties of the given target using the usual annotation driven suspects (@Autowired
, @Resource
, @Inject
). So our sample code turns into something like this:
public class MyServlet extends HttpServlet {
@Inject
private MyService service;
@Override
public void init() {
SpringBeanAutowiringSupport.
processInjectionBasedOnCurrentContext(this);
}
}
Done. Note, that we override the init method without the ServletConfig
parameter as the called method looks up the actual ApplicationContext
from a static map held in ContextLoader
which inherits from. If you need to lookup beans from an ApplicationContext
tied to a particular ServletContext
you can use processInjectionBasedOnServletContext(Object target, ServletContext servletContext)
and hand it the appropriate instances.
P.S.: Thanks to Eberhard Wolff for pointing me at this.