Arkar Myat

Understanding builder pattern

Aug 23, 2023Arkar
Design Patterns

Learn about the Builder pattern and how it can be used to create complex objects with ease.

On this page

In this article, we will explore the Builder pattern i and demonstrate how it can be used to build a complex object with an example. We will also look at the different components of the pattern and how they work together to create a final product.

A real-world example of the Builder pattern is the construction of a car. A car can have many components, such as the engine, wheels, seats, and stereo system. Each component has different variations and options that can be selected by the buyer.

Using the Builder pattern, the buyer can select the specific options they want for each component and the builder will construct the car accordingly. This ensures that the final product meets the buyer's specific needs and requirements.

Components of the Builder Pattern

The Builder pattern usually involves a basic structure that outlines the steps needed to create the object, as well as specific versions of this structure that provide more detail in terms of how those steps are carried out.

The Builder Interface

The first component of the Builder pattern is the Builder interface. This interface defines the steps needed to create the object and provides methods for setting the object's properties.

In our car example, we can define the Builder interface as follows:

export interface Builder {
  addSeats(seats: number): Builder;
  addNitro(mili: number): Builder;
  addEngine(type: string): Builder;
  addGps(type: boolean): Builder;
  build(): Car;
}

The Builder interface has methods like addSeats, addNitro, addEngine, addGps, and build that you can use to set up the car one step at a time. You can chain these methods together to make it easier to configure the car object.

The Product Interface

The second component of the Builder pattern is the Product interface. This interface defines the properties of the object being built. In our car example, we can define the Car interface as follows:

export interface Car {
  seats: number;
  nitro: number;
  engine: string;
  gps: boolean;
}

The Concrete Builder

The third component of the Builder pattern is the Concrete Builder. This class implements the Builder interface and provides the implementation for all the methods defined in the interface.

In our car example, we can define the CarBuilder class as follows:

export class CarBuilder implements Builder {
  private seats: number;
  private nitro: number;
  private engine: string;
  private gps: boolean;

  constructor() {
    this.seats = 0;
    this.nitro = 0;
    this.engine = "";
    this.gps = false;
  }

  addSeats(seats: number): CarBuilder {
    this.seats = seats;
    return this;
  }

  addNitro(mili: number): CarBuilder {
    this.nitro = mili;
    return this;
  }

  addEngine(type: string): CarBuilder {
    this.engine = type;
    return this;
  }

  addGps(type: boolean): CarBuilder {
    this.gps = type;
    return this;
  }

  build(): Car {
    return {
      seats: this.seats,
      nitro: this.nitro,
      engine: this.engine,
      gps: this.gps,
    };
  }
}

The CarBuilder class helps you build complicated objects bit by bit. It makes sure the final result matches what the buyer wants.

The Director

The fourth component of the Builder pattern is the Director. This class is responsible for using the Builder object to create the final product. In our car example, we can define the Application class as follows:

export class Application {
  private builder: Builder;

  constructor(builder: Builder) {
    this.builder = builder;
  }

  makeSportCar(): Car {
    return this.builder
      .addEngine("v8")
      .addGps(true)
      .addNitro(1000)
      .addSeats(2)
      .build();
  }

  makeFamilyCar(): Car {
    return this.builder
      .addEngine("v4")
      .addGps(true)
      .addNitro(0)
      .addSeats(4)
      .build();
  }
}

The Application class makes different types of cars based on what the buyer wants. The makeSportCar and makeFamilyCar methods use the CarBuilder object to set the features of the car and give the final result.

Using the Builder Pattern to Create a Car

Now that we know what the different parts of the Builder pattern are, let's see how we can use them to make a car object with different options.

let carBuilder = new CarBuilder();
let app = new Application(carBuilder);

let sport = app.makeFamilyCar();
console.log(sport);
let fam = app.makeSportCar();
console.log(fam);

Thank you so much for your time and I hope this article helpful to you. ❤️❤️❤️❤️

Subscribe to my NewsLetter!

Join my web development newsletter to receive the latest updates, tips, and trends directly in your inbox.