Wednesday, July 9, 2008

Brusque shutdowns?? Hang on, using Java Shutdown Hooks!!

Every application that you build has some well defined and methodical steps for its closure. However, users usually come up with their own ways of shutting down your application. And not every time your cleanup code is given a chance to work.
Brusque shutdowns cause many nightmares to developers than anything else. Java once again provides yet another rescue - Java Shutdown Hooks!!
Essentially, a shutdown hook is used to guarantee that your cleanup code is given its chance to run, irrespective of how the user terminates the application. Very crudely defined the shutdown-hooks are the Java Threads associated or hooked up with the Runtime.
Historically there was a workaround; that if you pass the -Xrs flag to the JVM (1.3.1 and earlier) parameters while creating the JVM, then the shutdown hook will NOT be called. This might be because -Xrs reduces use of OS signals by Java/VM.
This is by far the better technique than to rely on ever reliable (pun intended) finalizers. Off-course it still won't work against the fatal `kill -9`.
In Java, the virtual machine shuts down itself in response to two types of events: first, when the application exits normally, by calling the System.exit method or when the last non-daemon thread exits. Second, when the user abruptly forces the virtual machine to terminate; for example, by typing Ctrl+C or logging off from the system before closing a running Java program.
Fortunately, the virtual machine follows this two-phase sequence when shutting down:
  1. The virtual machine starts all registered shutdown hooks, if any. Shutdown hooks are threads registered with the Runtime. All shutdown hooks are run concurrently until they finish.
  2. The virtual machine calls all uninvoked finalizers, if appropriate.

Creating a shutdown hook is simple:
  1. Write a class extending the Thread class.
  2. Provide the implementation of your class' run method. This method is the code that needs to be run when the application is shut down, either normally or abruptly.
  3. In your application, instantiate your shutdown hook class.
  4. Register the shutdown hook with the current runtime's addShutdownHook method.

Simple shutdown hooks can often be written as anonymous inner classes, as in this example:
 Runtime.getRuntime().addShutdownHook(new Thread() {  
      public void run() { database.close(); }  
 });  
This idiom is fine as long as you'll never need to cancel the hook, in which case you'd need to save a reference to the hook when you create it.
Or more formal way as in the following example:
 package test;  
 public class ShutdownHookDemo {  
      public void start() {  
           System.out.println("Demo");  
           ShutdownHook shutdownHook = new ShutdownHook();  
           Runtime.getRuntime().addShutdownHook(shutdownHook);  
      }  
      public static void main(String[] args) {  
           ShutdownHookDemo demo = new ShutdownHookDemo();  
           demo.start();  
           try {  
                System.in.read();  
           }  
           catch(Exception e) {  
                // Do nothing.  
           }  
      }  
 }  
 class ShutdownHook extends Thread {  
      public void run() {  
           System.out.println("Shutting down");  
      }  
 }  
Last thing that I want to mention it here is that the shutdown hooks are with us since JSDK 1.3. So guys, start hanging out with Shutdown Hooks!!
PS: http://java.sun.com/j2se/1.5.0/docs/api/java/lang/Runtime.html