Java Design Pattern

Design Patterns are very popular among software developers. A design pattern is a well described solution to a common software problem.
Some of the benefits of using design patterns are:
  1. Design Patterns are already defined and provides industry standard approach to solve a recurring problem, so it saves time if we sensibly use the design pattern.
  2. Using design patterns promotes reusability that leads to more robust and highly maintainable code. It helps in reducing total cost of ownership (TCO) of the software product.
  3. Since design patterns are already defined, it makes our code easy to understand and debug. It leads to faster development and new members of team understand it easily.
Java Design Patterns are divided into three categories – creationalstructural, and behavioral design patterns. This post serves as an index for all the java design patterns articles I have written so far.

Creational Design Patterns

Creational design patterns provide solution to instantiate a object in the best possible way for specific situations.
  1. Singleton Pattern

    Singleton pattern restricts the instantiation of a class and ensures that only one instance of the class exists in the java virtual machine. It seems to be a very simple design pattern but when it comes to implementation, it comes with a lot of implementation concerns. The implementation of Singleton pattern has always been a controversial topic among developers. Check out Singleton Design Patternto learn about different ways to implement Singleton pattern and pros and cons of each of the method.

    What is Singleton ? and Double-checked locking ?


    Need to follow :
    * private constructor , can't create object from outside of the class
    * Synchronized methods are used to ensure that the class is thread-safe.
    * This class cannot be sub classed because the constructor is private. This may or may
    not be a good thing depending on the resource being protected.



    //Single-checked locking
    //Thread 1 enters the synchronized block, and, before it can assign the singleton member variable, the thread is preempted. Subsequently, another thread can enter the if block. The second thread will wait for the first thread to finish, but we will still wind up with two distinct singleton instances

    Double checked locking
    public class Singleton{
    private static Singleton instance;
    private static Singleton();
    public static Singleton getInstance(){
    if(instance==null){
    Synchronized(Singleton.class){
      if(instance==null){
    s.o.p(“First instance invalid”)}}}
    return instance;
    }public void doSomthing(){
    s.o.p (“”);}
    }
  2. Factory Pattern

    Factory design pattern is used when we have a super class with multiple sub-classes and based on input, we need to return one of the sub-class. This pattern take out the responsibility of instantiation of a class from client program to the factory class. We can apply Singleton pattern on Factory class or make the factory method static. Check out Factory Design Pattern for example program and factory pattern benefits.
  3. Abstract Factory Pattern

    Abstract Factory pattern is similar to Factory pattern and it’s factory of factories. If you are familiar with factory design pattern in java, you will notice that we have a single Factory class that returns the different sub-classes based on the input provided and factory class uses if-else or switch statement to achieve this.
    In Abstract Factory pattern, we get rid of if-else block and have a factory class for each sub-class and then an Abstract Factory class that will return the sub-class based on the input factory class. Check outAbstract Factory Pattern to know how to implement this pattern with example program.
  4. Builder Pattern

    This pattern was introduced to solve some of the problems with Factory and Abstract Factory design patterns when the Object contains a lot of attributes. Builder pattern solves the issue with large number of optional parameters and inconsistent state by providing a way to build the object step-by-step and provide a method that will actually return the final Object. Check out Builder Pattern for example program and classes used in JDK.
  5. Prototype Pattern

    Prototype pattern is used when the Object creation is a costly affair and requires a lot of time and resources and you have a similar object already existing. So this pattern provides a mechanism to copy the original object to a new object and then modify it according to our needs. This pattern uses java cloning to copy the object.
    Prototype design pattern mandates that the Object which you are copying should provide the copying feature. It should not be done by any other class. However whether to use shallow or deep copy of the Object properties depends on the requirements and its a design decision. Check out Prototype Pattern for sample program.

Structural Design Patterns

Structural patterns provide different ways to create a class structure, for example using inheritance and composition to create a large object from small objects.
  1. Adapter Pattern

    Adapter design pattern is one of the structural design pattern and its used so that two unrelated interfaces can work together. The object that joins these unrelated interface is called an Adapter. As a real life example, we can think of a mobile charger as an adapter because mobile battery needs 3 volts to charge but the normal socket produces either 120V (US) or 240V (India). So the mobile charger works as an adapter between mobile charging socket and the wall socket. Check out Adapter Patternfor example program and it’s usage in Java.
  2. Composite Pattern

    Composite pattern is one of the Structural design pattern and is used when we have to represent a part-whole hierarchy. When we need to create a structure in a way that the objects in the structure has to be treated the same way, we can apply composite design pattern.
    Lets understand it with a real life example – A diagram is a structure that consists of Objects such as Circle, Lines, Triangle etc and when we fill the drawing with color (say Red), the same color also gets applied to the Objects in the drawing. Here drawing is made up of different parts and they all have same operations. Check out Composite Pattern article for different component of composite pattern and example program.
  3. Proxy Pattern

    Proxy pattern intent is to “Provide a surrogate or placeholder for another object to control access to it”. The definition itself is very clear and proxy pattern is used when we want to provide controlled access of a functionality.
    Let’s say we have a class that can run some command on the system. Now if we are using it, its fine but if we want to give this program to a client application, it can have severe issues because client program can issue command to delete some system files or change some settings that you don’t want. Check out Proxy Pattern post for the example program with implementation details.
  4. Flyweight Pattern

    Flyweight design pattern is used when we need to create a lot of Objects of a class. Since every object consumes memory space that can be crucial for low memory devices, such as mobile devices or embedded systems, flyweight design pattern can be applied to reduce the load on memory by sharing objects. String Pool implementation in java is one of the best example of Flyweight pattern implementation. Check out Flyweight Pattern article for sample program and implementation process.
  5. Facade Pattern

    Facade Pattern is used to help client applications to easily interact with the system. Suppose we have an application with set of interfaces to use MySql/Oracle database and to generate different types of reports, such as HTML report, PDF report etc. So we will have different set of interfaces to work with different types of database. Now a client application can use these interfaces to get the required database connection and generate reports. But when the complexity increases or the interface behavior names are confusing, client application will find it difficult to manage it. So we can apply Facade pattern here and provide a wrapper interface on top of the existing interface to help client application. Check out Facade Pattern post for implementation details and sample program.
  6. Bridge Pattern

    When we have interface hierarchies in both interfaces as well as implementations, then builder design pattern is used to decouple the interfaces from implementation and hiding the implementation details from the client programs. Like Adapter pattern, its one of the Structural design pattern.
    The implementation of bridge design pattern follows the notion to prefer Composition over inheritance. Check out Bridge Pattern post for implementation details and sample program.
    1. Decorator Pattern

      Decorator design pattern is used to modify the functionality of an object at runtime. At the same time other instances of the same class will not be affected by this, so individual object gets the modified behavior. Decorator design pattern is one of the structural design pattern (such as Adapter Pattern, Bridge Pattern, Composite Pattern) and uses abstract classes or interface with composition to implement.
      We use inheritance or composition to extend the behavior of an object but this is done at compile time and its applicable to all the instances of the class. We can’t add any new functionality of remove any existing behavior at runtime – this is when Decorator pattern comes into picture. Check out Decorator Pattern post for sample program and implementation details.

    Behavioral Design Patterns

    Behavioral patterns provide solution for the better interaction between objects and how to provide lose coupling and flexibility to extend easily.
    1. Template Method Pattern

      Template Method is a behavioral design pattern and it’s used to create a method stub and deferring some of the steps of implementation to the subclasses. Template method defines the steps to execute an algorithm and it can provide default implementation that might be common for all or some of the subclasses.
      Suppose we want to provide an algorithm to build a house. The steps need to be performed to build a house are – building foundation, building pillars, building walls and windows. The important point is that the we can’t change the order of execution because we can’t build windows before building the foundation. So in this case we can create a template method that will use different methods to build the house. Check out Template Method Pattern post for implementation details with example program.
    2. Mediator Pattern

      Mediator design pattern is used to provide a centralized communication medium between different objects in a system. Mediator design pattern is very helpful in an enterprise application where multiple objects are interacting with each other. If the objects interact with each other directly, the system components are tightly-coupled with each other that makes maintainability cost higher and not flexible to extend easily. Mediator pattern focuses on provide a mediator between objects for communication and help in implementing lose-coupling between objects.
      Air traffic controller is a great example of mediator pattern where the airport control room works as a mediator for communication between different flights. Mediator works as a router between objects and it can have it’s own logic to provide way of communication. Check out Mediator Pattern post for implementation details with example program.
    3. Chain of Responsibility Pattern

      Chain of responsibility pattern is used to achieve lose coupling in software design where a request from client is passed to a chain of objects to process them. Then the object in the chain will decide themselves who will be processing the request and whether the request is required to be sent to the next object in the chain or not.
      We know that we can have multiple catch blocks in a try-catch block code. Here every catch block is kind of a processor to process that particular exception. So when any exception occurs in the try block, its send to the first catch block to process. If the catch block is not able to process it, it forwards the request to next object in chain i.e next catch block. If even the last catch block is not able to process it, the exception is thrown outside of the chain to the calling program.
      ATM dispense machine logic can be implemented using Chain of Responsibility Pattern, check out the linked post.
    4. Observer Pattern

      Observer design pattern is useful when you are interested in the state of an object and want to get notified whenever there is any change. In observer pattern, the object that watch on the state of another object are called Observer and the object that is being watched is called Subject.
      Java provides inbuilt platform for implementing Observer pattern through java.util.Observable class and java.util.Observer interface. However it’s not widely used because the implementation is really simple and most of the times we don’t want to end up extending a class just for implementing Observer pattern as java doesn’t provide multiple inheritance in classes.
      Java Message Service (JMS) uses Observer pattern along with Mediator pattern to allow applications to subscribe and publish data to other applications. Check out Observer Pattern post for implementation details and example program.
    5. Strategy Pattern

      Strategy pattern is used when we have multiple algorithm for a specific task and client decides the actual implementation to be used at runtime.
      Strategy pattern is also known as Policy Pattern. We defines multiple algorithms and let client application pass the algorithm to be used as a parameter. One of the best example of this pattern is Collections.sort() method that takes Comparator parameter. Based on the different implementations of Comparator interfaces, the Objects are getting sorted in different ways.
      Check out Strategy Pattern post for implementation details and example program.
    6. Command Pattern

      Command Pattern is used to implement lose coupling in a request-response model. In command pattern, the request is send to the invoker and invoker pass it to the encapsulated command object. Command object passes the request to the appropriate method of Receiver to perform the specific action.
      Let’s say we want to provide a File System utility with methods to open, write and close file and it should support multiple operating systems such as Windows and Unix.
      To implement our File System utility, first of all we need to create the receiver classes that will actually do all the work. Since we code in terms of java interfaces, we can have FileSystemReceiver interface and it’s implementation classes for different operating system flavors such as Windows, Unix, Solaris etc. Check out Command Pattern post for the implementation details with example program.
    7. State Pattern

      State design pattern is used when an Object change it’s behavior based on it’s internal state.
      If we have to change the behavior of an object based on it’s state, we can have a state variable in the Object and use if-else condition block to perform different actions based on the state. State pattern is used to provide a systematic and lose-coupled way to achieve this through Context and State implementations.
      Check out State Pattern post for implementation details with example program.
    8. Visitor Pattern

      Visitor pattern is used when we have to perform an operation on a group of similar kind of Objects. With the help of visitor pattern, we can move the operational logic from the objects to another class.
      For example, think of a Shopping cart where we can add different type of items (Elements), when we click on checkout button, it calculates the total amount to be paid. Now we can have the calculation logic in item classes or we can move out this logic to another class using visitor pattern. Let’s implement this in our example of visitor pattern. Check out Visitor Pattern post for implementation details.
    9. Interpreter Pattern

      is used to defines a grammatical representation for a language and provides an interpreter to deal with this grammar.
      The best example of this pattern is java compiler that interprets the java source code into byte code that is understandable by JVM. Google Translator is also an example of interpreter pattern where the input can be in any language and we can get the output interpreted in another language.
      Check out Interpreter Pattern post for example program.
    10. Iterator Pattern

      Iterator pattern in one of the behavioral pattern and it’s used to provide a standard way to traverse through a group of Objects. Iterator pattern is widely used in Java Collection Framework where Iterator interface provides methods for traversing through a collection.
      Iterator pattern is not only about traversing through a collection, we can provide different kind of iterators based on our requirements. Iterator pattern hides the actual implementation of traversal through the collection and client programs just use iterator methods. Check out Iterator Pattern post for example program and implementation details.
    11. Memento Pattern

      Memento design pattern is used when we want to save the state of an object so that we can restore later on. Memento pattern is used to implement this in such a way that the saved state data of the object is not accessible outside of the object, this protects the integrity of saved state data.
      Memento pattern is implemented with two objects – Originator and Caretaker. Originator is the object whose state needs to be saved and restored and it uses an inner class to save the state of Object. The inner class is called Memento and its private, so that it can’t be accessed from other objects.
      Check out Memento Pattern for sample program and implementation details.


Using Singleton Class for DB Connection Java

The Servlet which loads the Singleton class should be loaded during the server startup
ConfigServlet.java

public class ConfigServlet extends HttpServlet
{
  @Override
  public void init() throws ServletException
  {
    super.init();
    SingletonDBConnection.getInstance();
  }
}
web.xml

<servlet>
   <servlet-name>StartUpServlet</servlet-name>
   <servlet-class>com.mugil.tutor.ConfigServlet</servlet-class>
   <load-on-startup>1</load-on-startup>
</servlet>
DBConnection.java

import java.sql.Connection;
import java.sql.SQLException;

public class DBConnection
{
  public Connection getDBConnection()
  {
    Connection connection = null;

    try
    {
      connection = DriverManager.getConnection(
          "HOST_NAME", "USER_NAME", "PASSWORD");

    }
    catch (SQLException e)
    {
      e.getLocalizedMessage(); 
      System.out.println("Connection Failed! Check output console");
      e.printStackTrace();
      return null;
    }
    return connection;
  }
}
SingletonDBConnection.java

import java.sql.Connection;
import java.sql.SQLException;

import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.sql.DataSource;

public class SingletonDBConnection
{
  private static SingletonDBConnection singleInstance;
  private static DataSource dataSource;
  private static Connection dbConnect;
   
  private SingletonDBConnection()
  {
    try
    {
      Context initContext = new InitialContext();
      Context envContext  = (Context) initContext.lookup("java:/comp/env");
      dataSource       = (DataSource) envContext.lookup("jdbc/testdb");
       
      try
      {
        dbConnect  = dataSource.getConnection();
      }
      catch (SQLException e)
      {
        e.printStackTrace();
      }  
    }
    catch (NamingException e)
    {
      e.printStackTrace();
    }
  }
   
  public static SingletonDBConnection getInstance()
  {
    if(singleInstance == null)
    {
      synchronized (SingletonDBConnection.class)
      {
        if(singleInstance == null)
        {
          singleInstance = new SingletonDBConnection();
        }
      }
    }

    return singleInstance;
  }
   
  public static Connection getConnInst()
  {
    try
    {
      dbConnect = dataSource.getConnection();
    }
    catch (SQLException e1)
    {
      e1.printStackTrace();
    }
     
    if(dbConnect == null)
    {
      try
      {
        Context initContext = new InitialContext();
        Context envContext  = (Context) initContext.lookup("java:/comp/env");
        dataSource        = (DataSource) envContext.lookup("jdbc/testdb");
         
        try
        {
          dbConnect  = dataSource.getConnection();
        }
        catch (SQLException e)
        {
          e.printStackTrace();
        }  
      }
      catch (NamingException e)
      {
        e.printStackTrace();
      }
    }
     
    return dbConnect;   
  }
}
ListUsers.java

public List<User> getUsersList()
  {
    Connection conn;
    Statement  stmt = null;
    ResultSet  rs;
    List<User> arrUsersList = new ArrayList<User>();
    conn = SingletonDBConnection.getInstance().getConnInst();
     
    String strSQL = "SELECT UserId, UserName, Gender, UserLocation " +
            "  FROM tblusers";
     
    try
    {
      stmt = conn.createStatement();     
      rs = stmt.executeQuery(strSQL);
       
      while(rs.next())
      {
        User objUser = new User();
        objUser.setUserId(rs.getString("UserId"));
        objUser.setUserName(rs.getString("UserName"));
        objUser.setUserGender(rs.getString("Gender"));
        objUser.setUserLocation(rs.getString("UserLocation"));
        arrUsersList.add(objUser);
      }
    }
    catch (SQLException e)
    {
      e.printStackTrace();
    }
    finally
    {
      if(conn != null) try { conn.close(); } catch (SQLException e) { e.printStackTrace(); }
    }
     
     
    return arrUsersList;
  }





Definition:
Singleton
is a part of Gang of Four design pattern and it is categorized under creational design patterns.

In this article we are going to take a deeper look into the usage of the Singleton pattern. It is one of the most simple design pattern in terms of the modelling but on the other hand this is one of the most controversial pattern in terms of complexity of usage.

In Java the Singleton pattern will ensure that there is only one instance of a class is created in the Java Virtual Machine. It is used to provide global point of access to the object. In terms of practical use Singleton patterns are used in logging, caches, thread pools, configuration settings, device driver objects. Design pattern is often used in conjunction with Factory design pattern. This pattern is also used in Service Locator JEE pattern.
Why We Use Singleton?
One reason that tends to come up over and over again on the internets is that of a "logging" class (which you mentioned). In this case, a Singleton can be used instead of a single instance of a class because a logging class usually needs to be used over and over again ad nauseam by every class in a project. If every class uses this logging class, dependency injection becomes cumbersome.
Logging is a specific example an "acceptable" Singleton because it doesn't affect the execution of your code. Disable logging, code execution remains the same. Enable it, same.





Singleton Class Diagram
  • Static member : This contains the instance of the singleton class.
  • Private constructor : This will prevent anybody else to instantiate the Singleton class.
  • Static public method : This provides the global point of access to the Singleton object and returns the instance to the client calling class.

Implementation Example: Lazy initialization

Let us look into a singleton implementation example in Java. The below code uses Lazy initialization process.
public class SingletonExample {

// Static member holds only one instance of the
// SingletonExample class
private static SingletonExample singletonInstance;
// SingletonExample prevents any other class from instantiating
private SingletonExample() {
}

// Providing Global point of access
public static SingletonExample getSingletonInstance() {
if (null == singletonInstance) {
 singletonInstance = new SingletonExample();
}
return singletonInstance;
}

public void printSingleton(){
System.out.println("Inside print Singleton");
}
}

Singleton Pattern Code Explanation
When this class will be called from the client side using SingletonExample.getSingletonInstance().printSingleton(); then at the first time only an instance will be created. During second time onwards for all subsequent calls we will be referring to the same object and the getSingletonInstance() method returns the same instance of the SingletonExample class which was created during the first time. You can test this by adding a print statement the following code as:
public static SingletonExample getSingletonInstance() {
if (null == singletonInstance) {
singletonInstance = new SingletonExample();
System.out.println("Creating new instance");
}
return singletonInstance;
}
If we now call Singleton class from the client class as:
1.SingletonExample.getSingletonInstance().printSingleton();
2.SingletonExample.getSingletonInstance().printSingleton();
3.SingletonExample.getSingletonInstance().printSingleton();
4.SingletonExample.getSingletonInstance().printSingleton();
The output of the above call is:
1.Creating new instance
2.Inside print Singleton
3.Inside print Singleton
4.Inside print Singleton
5.Inside print Singleton

Implementation Example: Double check locking

The above code works absolutely fine in a single threaded environment and processes the result faster because of lazy initialization. However the above code might create some abrupt behaviour in the results in a multithreaded environment as in this situation multiple threads can possibly create multiple instance of the same SingletonExample class if they try to access the getSingletonInstance() method at the same time. Imagine a practical scenario where we have to create a log file and update it or while using a shared resource like Printer. To prevent this we must use some locking mechanism so that the second thread cannot use this getInstance() method until the first thread has completed the process.







show how multiple threads access the singleton instance. Since the singleton instance is a static class variable in the stored in the PermGen space of the heap. This applies to getSingletonInstance() instance method as well since it is static too. In the multithreading environment to prevent each thread to create another instance of singleton object and thus creating concurrency issue we will need to use locking mechanism. This can be achieved by synchronized keyword. By using this synchronized keyword we prevent Thread2 or Thread3 to access the singleton instance while Thread1 inside the method getSingletonInstance().
From code perspective it means:
public static synchronized SingletonExample getSingletonInstance() {
if (null == singletonInstance) {
singletonInstance = new SingletonExample();
}
return singletonInstance;
}
So this means that every time the getSingletonInstance() is called it gives us an additional overhead . To prevent this expensive operation we will use double checked locking so that the synchronization happens only during the first call and we limit this expensive operation to happen only once. It is only required for:
1.singletonInstance = new SingletonExample();
Code example:
public static volatile SingletonExample getSingletonInstance() {
if (null == singletonInstance) {
synchronized (SingletonExample.class){
if (null == singletonInstance) {
singletonInstance = new SingletonExample();
}
}
}
return singletonInstance;
}
In the above code snippet imagine that multiple threads comes concurrently and tries to create the new instance. In such situation the may be three or more threads are waiting on the synchronized block to get access. Since we have used synchronized only one thread will be given access. All the remaining threads which were waiting on the synchronized block will be given access when first thread exits this block. However when the remaining concurrent thread enters the synchronized block they are prevented to enter further due to the double check : null check. Since the first thread has already created an instance no other thread will enter this loop.
All the remaining threads that were not lucky to enter the synchronized block along with the first thread will be blocked at the first null check. This mechanism is called double checked locking and it provides significant performance benefit and also it is cost effective solution.

Implementation Example: Volatile Keyword

We can also use the volatile keyword to the instance variable declaration.
1.private volatile static SingletonExample singletonInstance;
The volatile keyword helps as concurrency control tool in a multithreaded environment and provides the latest update in a most accurate manner.However please note that double check locking might not work before Java 5. In such situation we can use early loading mechanism. If we remember about the original sample code we had used lazy loading. In case of early loading we will instantiate the SingletonExample class at the start and this will be referred to the private static instance field.
public class SingletonExample {
private static final SingletonExample singletonInstance = new SingletonExample;

// SingletonExample prevents any other class from instantiating
private SingletonExample() {
}

// Providing Global point of access

public static SingletonExample getSingletonInstance() {
return singletonInstance;
}
public void printSingleton(){
System.out.println("Inside print Singleton");
}
}
In this approach the singleton object is created before it is needed. The JVM takes care of the static variable initialization and ensures that the process is thread safe and that the instance is created before the threads tries to access it. In case of Lazy loading the singletonInstance is created when the client class calls the getSingleInstance() whereas in case of the early loading the singletonInstance is create when the class is loaded in the memory.

Implementation Example: Using enum

Implementing Singleton in Java 5 or above version using Enum:
Enum is thread safe and implementation of Singleton through Enum ensures that your singleton will have only one instance even in a multithreaded environment. Let us see a simple implementation:

public enum SingletonEnum {
INSTANCE;
public void doStuff(){
System.out.println("Singleton using Enum");
}
}
And this can be called from clients :
public static void main(String[] args) {
SingletonEnum.INSTANCE.doStuff();


}

FAQs:

Question: Why can’t we use a static class instead of singleton?
Answer:

  • One of the key advantages of singleton over static class is that it can implement interfaces and extend classes while the static class cannot (it can extend classes, but it does not inherit their instance members). If we consider a static class it can only be a nested static class as top level class cannot be a static class. Static means that it belongs to a class it is in and not to any instance. So it cannot be a top level class.
  • Another difference is that static class will have all its member as static only unlike Singleton.
  • Another advantage of Singleton is that it can be lazily loaded whereas static will be initialized whenever it is first loaded.
  • Singleton object stores in Heap but, static object stores in stack.
  • We can clone the object of Singleton but, we can not clone the static class object.
  • Singleton can use the Object Oriented feature of polymorphism but static class cannot.
Question: Can the singleton class be subclassed?
Answer: Frankly speaking singleton is just a design pattern and it can be subclassed. However it is worth to understand the logic or requirement behind subclassing a singleton class as the child class might not inherit the singleton pattern objective by extending the Singleton class. However the subclassing can be prevented by using the final keyword in the class declaration.

Question: Can there be multiple instance of singleton using cloning?
Answer: That was a good catch! What do we do now? To prevent the another instance to be created of the singleton instance we can throw exception from inside the clone() method.

Public class MySingleton implements Cloneable {
  private static MySingleton Instance;

  private MySingleton() {
    // private constructor prevents instantiation by untrusted callers
  }

  // Lazy initialization
  public static synchronized MySingleton getInstance() {
    if (Instance == null) {
      Instance = new MySingleton();
    }
    return Instance;
  }

  public Object clone() throws CloneNotSupportedException {
    throw new CloneNotSupportedException();
  }
}

Question: What is the impact if we are creating another instance of singleton using serialization and deserialization?
Answer: When we serialize a class and deserialize it then it creates another instance of the singleton class. Basically as many times as you deserialize the singleton instance it will create multiple instance. Well in this case the best way is to make the singleton as enum. In that way the underlying Java implementation takes care of all the details. If this is not possible then we will need to override the readobject() method to return the same singleton instance.

Adding a readResolve() method that returns the original instance is insufficient to enforce the singleton property. This is insecure even when all the fields are declared transient or static.
class MySingleton implements Serializable {
  private static final long serialVersionUID = 6825273283542226860L;
  private static MySingleton Instance;

  private MySingleton() {
    // private constructor prevents instantiation by untrusted callers
  }

  // Lazy initialization
  public static synchronized MySingleton getInstance() {
    if (Instance == null) {
      Instance = new MySingleton();
    }
    return Instance;
  }

  private Object readResolve() {
    return Instance;
  }
}
At runtime, an attacker can add a class that reads in a crafted serialized stream:
public class Untrusted implements Serializable {
  public static MySingleton captured;
  public MySingleton capture;
   
  public Untrusted(MySingleton capture) {
    this.capture = capture;
  }

  private void readObject(java.io.ObjectInputStream in)
                          throws Exception {
    in.defaultReadObject();
    captured = capture;
  }
}
The crafted stream can be generated by serializing the following class:
public final class MySingleton
                   implements java.io.Serializable {
  private static final long serialVersionUID =
      6825273283542226860L;
  public Untrusted untrusted =
      new Untrusted(this); // Additional serial field
  
  public MySingleton() { }
}
Upon deserialization, the field MySingleton.untrusted is reconstructed before MySingleton.readResolve() is called. Consequently, Untrusted.captured is assigned the deserialized instance of the crafted stream instead of MySingleton.Instance. This issue is harmful when an attacker can add classes to exploit the singleton guarantee of an existing serializable class.

Question: Which other pattern works with Singleton?
Answer:There are several other pattern like Factory method, builder and prototype pattern which uses Singleton pattern during the implementation.

Question: Which classes in JDK uses singleton pattern?
Answer: java.lang.Runtime : In every Java application there is only one Runtime instance that allows the application to interface with the environment it is running. The getRuntime is equivalent to the getInstance() method of the singleton class.

Uses of Singleton design pattern:

Various usages of Singleton Patterns:
  • Hardware interface access: The use of singleton depends on the requirements. However practically singleton can be used in case external hardware resource usage limitation required e.g. Hardware printers where the print spooler can be made a singleton to avoid multiple concurrent accesses and creating deadlock.
  • Logger : Similarly singleton is a good potential candidate for using in the log files generation. Imagine an application where the logging utility has to produce one log file based on the messages received from the users. If there is multiple client application using this logging utility class they might create multiple instances of this class and it can potentially cause issues during concurrent access to the same logger file. We can use the logger utility class as a singleton and provide a global point of reference.
  • Configuration File: This is another potential candidate for Singleton pattern because this has a performance benefit as it prevents multiple users to repeatedly access and read the configuration file or properties file. It creates a single instance of the configuration file which can be accessed by multiple calls concurrently as it will provide static config data loaded into in-memory objects. The application only reads from the configuration file at the first time and there after from second call onwards the client applications read the data from in-memory objects.
  • Cache: We can use the cache as a singleton object as it can have a global point of reference and for all future calls to the cache object the client application will use the in-memory object.







Previous
Next Post »