1. Overview
In this tutorial, we’re going to learn different ways to use shutdown callbacks with Spring.
The main advantage of using a shutdown callback is that it gives us control over a graceful application exit.
2. Shutdown Callback Approaches
Spring supports both the component-level and the context-level shutdown callbacks. We can create these callbacks using:
- @PreDestroy
- DisposableBean interface
- Bean-destroy method
- Global ServletContextListener
Let’s see all of these approaches with examples.
2.1. Using @PreDestroy
Let’s create a bean that uses @PreDestroy:
@Component public class Bean1 { @PreDestroy public void destroy() { System.out.println( "Callback triggered - @PreDestroy."); } }
During the bean initialization, Spring will register all the bean methods that are annotated with @PreDestroy and invokes them when the application shuts down.
2.2. Using the DisposableBean Interface
Our second bean will implement the DisposableBean interface to register the shutdown callback:
@Component public class Bean2 implements DisposableBean { @Override public void destroy() throws Exception { System.out.println( "Callback triggered - DisposableBean."); } }
2.3. Declaring a Bean Destroy Method
For this approach, firstly we’ll create a class with a custom destroy method:
public class Bean3 { public void destroy() { System.out.println( "Callback triggered - bean destroy method."); } }
Then, we create the configuration class that initializes the bean and marks its destroy() method as our shutdown callback:
@Configuration public class ShutdownHookConfiguration { @Bean(destroyMethod = "destroy") public Bean3 initializeBean3() { return new Bean3(); } }
The XML way of registering the destroy method is:
<bean class="com.baeldung.shutdownhooks.config.Bean3" destroy-method="destroy">
2.4. Using a Global ServletContextListener
Unlike the other three approaches, which register the callback at bean level, the ServletContextListener registers the callback at context level.
For this let’s create a custom context listener:
public class ExampleServletContextListener implements ServletContextListener { @Override public void contextDestroyed(ServletContextEvent event) { System.out.println( "Callback triggered - ContextListener."); } @Override public void contextInitialized(ServletContextEvent event) { // Triggers when context initializes } }
We need to register it to the ServletListenerRegistrationBean in the configuration class:
@Bean ServletListenerRegistrationBean<ServletContextListener> servletListener() { ServletListenerRegistrationBean<ServletContextListener> srb = new ServletListenerRegistrationBean<>(); srb.setListener(new ExampleServletContextListener()); return srb; }
3. Conclusion
We’ve learned about the different ways Spring provides to register shutdown callbacks, both at the bean level and at the context level.
These can be used for shutting down the application gracefully and effectively freeing up the used resources.
As always all the examples mentioned in this article can be found over on Github.