Builder in PHP [Design pattern with examples]

Coding (Php 7.x)

Apr 30, 2020

Discover one of the most advanced creational design patterns
 
/img/blog/builder-in-php-design-pattern-with-examples.jpg

The moment I am writing this post is quite a strange one.

 

Humanity is confined indoor because of a worldwide quarantine, 

 

Everyone must stay home and can get out only for a limited amount of time and a specific purpose.

 

While people are at home Netflix has tripled its quarterly revenue and Disney+ got millions of subscribers in just the last few months.

 

These are thousands of hours of movies and TV series watched.

 

Here is the question:

How are movies made?

 

Here is a better question:

How, as a Web developer, would YOU make a movie?

 

In this article, you will take advantage of this time to learn how to make a software that makes movies and,

 

You will do so by using one of the most popular (and a bit complex) creational design patterns available.

 

The Builder pattern!

 

The Series

 

If you have followed my blog you might already know that I am creating a series about Design Pattern.

 

In this series, I describe the most popular design patterns available for PHP developer and not.

 

I am using very easy examples to explain elaborate concepts and I do so using PHP language and clear UML schemes

 

You can discover the other design pattern following the links below:

 

 

 

 

 

The builder pattern

 

So, movies.

 

As with everything in life if you want to create something special you need to have a plan and follow specific procedures.

 

Weird to say that but, the art of creating movies is quite similar to the one of creating web applications.

 

  1. You need to know what you want to make.
  2. Arrange a plan and write down a checklist according to the plan.
  3. Eventually, perform every task in the checklist until hitting the “go live” button.

 

This is why we have product managers who love software like Asana and Jira.

 

To make a movie the step should look like the following:

 

  1. get equipment
  2. write the script
  3. casting
  4. filming
  5. editing
  6. distribution

 

Easy right?

 

 

The issues

 

Things start to become complicated when you add in the fact that movies can fall in different categories, action, comedy, drama. 

 

A way to solve this is to create an abstract class movie and a lot of subclasses that extend his features

 

abstract class Movie {}

class ActionMovie extends Movie {}

class ComedyMovie extends Movie {}

class DramaMovie extends Movie {}

 

 

And what about action movies with a bit of comedy in it? 

 

Should we create a brand new class just for it?

 

Also if you have to code a movie you might be tempted to add everything in a constructor.

 

Writing code like this

class movie 
{
    public function __construct(
          Camera $camera, 
          Director $director, 
          Actor $hero, 
          Actor $antagonist, 
          string $filmType, 
          int $categoryMovieId,
          Producer $producer,
          Distributer $distributer 
    ) {...}
}

 

I don't need to highlight how bad this code looks, 

 

Imagine instantiating dozens of objects of the class movie and adding all of these attributes each time.

 

And if a movie is a biography and it does not have an antagonist? Or there is no producer. 

 

We are going to end up filling constructor with null variable or empty strings

 

What a nightmare!

 

What is the solution then?

 

The builder

 

In the specific case of the example we are looking at in this article one of the solutions might be to implement the builder pattern in the code.

 

The Builder pattern consists of extracting the construction code outside of the class and using specific builders to create everything we need into separate objects.

 

To be more clear the builder is in charge of executing a list of steps, included in our checklist, that have as end goal the creation of the object we want to instantiate.

 

Even better, using this pattern you can create movies in every category you want,

 

If, for instance, we want to create a biography we just create a specific builder for it, which will be different from a builder of action movies.

 

In the case there is no antagonist in our movie we just skip the step, thus avoid passing null variables around our classes.

 

The UML scheme for our builder will look something like this

 

 

What we are going here is creating a builder class that has all the steps needed to create a movie.

Since we need different builders for different category of movies we can also make this builder a contract and used its concrete class instead

 


 

In the image above the MovieBuilder is an interface and it declares all the necessary steps that need to be performed by the two concrete classes related to it.

 

The concrete builders' classes, on the other side, supply all the elements needed for the creation of their specific type of movie.

 

 

 

 

 

 

Note that the builders can create movies that don’t track the MovieBuilder interface.

 

 

The Director

 

We can increase the readability (and complexity) of our code by adding a Director class to our application.

 

As an architect that commands the constructor of a building, the director is in charge of defining the tasks that the builder has to perform and describe them step-by-step.

 

Creating a director is not mandatory,

 

Your application will work just fine even if you decide to call the steps directly in your code.

 

What the director does is to include in a specific place all the steps that are defined.

 

Once you define these construction checklists you can take advantage of the Director class and reuse them in different places in your application.

 

 

The Implementation of the example

 

Now that you understand what this pattern is all about and what are the parts that play a role in it.

 

Let’s have a look at how you can implement this design pattern in your PHP application.

class ActionMovieBuilder implements MovieBuilder

{
    private $movie;

    public function __construct()
    {
        $this->movie = new Movie();
    }

    public function setCamera()
    {
        return ‘creating camera’;
    }

    public function setMovieDirector(){...};
    public function setProtagonist(){...};
    public function setAntagonist(){...};
    public function setGuns(){...};
    public function setExplosive(){...};
    public function setFilmType(){...};
    public function setProducer(){...};
    public function setDistributer(){...};
}

 

 

The pseudocode in here is quite straightforward.

 

The class above is the one in charge of making action movies.

 

Action movies often show a story about a hero, which is the protagonist against a villain or antagonist, this type of movie often uses fancy guns and explosives.

 

Very different from a comedy or romantic movie.


 

class Director
{
    private $builder;

    public function setBuilder(Builder $builder): void
    {
        $this->builder = $builder;
    }

    public function setActionMovie()
    {
        echo $this->builder->setCamera();
        echo $this->builder->setMovieDirector();
        echo $this->builder->setProtagonist();        
        echo $this->builder->setAntagonist();
        echo $this->builder->setGuns();
        echo $this->builder->setExplosive();
        echo $this->builder->setFilmType();
        echo $this->builder->setProducer();
        echo $this->builder->setDistributer();
    }

    public function setBiographyMovie()
    {
        echo $this->builder->setCamera();
        echo $this->builder->setMovieDirector();
        echo $this->builder->setProtagonist();        
        echo $this->builder->setFilmType();
        echo $this->builder->setProducer();
        echo $this->builder->setDistributer();
    }
}

The Director class here is the one that orchestrates what class and method have to be called.

 

Do not confuse the Director class with the MovieDirector element.

 

The Director class in a wrapper in which all the methods that build a specific category of movies are called.

 

$director = new Director();
$builder = new ActionMovieBuilder();
$director->setBuilder(builder);
$director->setActionMovie();

 

Above we see the client code,

 

In here we create the Director class of our pattern we create the Builder class and connect it to the Director then we invoke the method that creates an action movie.

 

If we wanted another type of movie we would just create a different builder and invoke a different method.

 

Ps: I haven’t added in here because I did not want to make the example more complex but surely you will need the Movie class, the MovieBuilder interface, and implement the correct code into each method.

 

If you want to replicate this Builder pattern yourself and you need help with the missing pieces head over the Basic of PHP.

 

In the example,

 

we have created a scalable web application that avoids the use of dozens of parameters in the constructor (telescopic constructor).

 

We can now simply add and use a different class whenever we want to create a brand-new type of Movies.

 

 

Integrating Builder in your code

 

This is one of the few design patterns that belong to the creational category.

 

When implementing a creational design pattern you will often find yourself using the Factory pattern being the easier one to be implemented and open to modification. 

 

The factory method can expand to Builder and make your code more flexible.

 

A con of using these two patterns together is that the code will be very complicated and difficult to maintain.

 

The difference between the Builder the Factory method and the Abstract Factory is that the builder, as the examples, let us define the steps before getting the actual object.

 

We can also integrate the Builder with the Bridge pattern where the director becomes the abstraction.

 

 

become a Patron!

 

 

Conclusion

 

Using design patterns correctly can be considered a skill on its own.

 

Is not rare during job interviews, especially for companies that do not have a codebase written in any framework, to be asked if you know any design pattern and where did you implement it before.

 

This is a question you must be able to answer, and this article like the other one of this series is here to help you with that.

 

If you are looking for a place to start learning the easier you can read the Factory method pattern.

 

If you want to learn some not-PHP related skills you can opt for Docker or read the Git series.

 
 
If you like this content and you are hungry for some more join the Facebook's community in which we share info and news just like this one!

Other posts that might interest you

Coding (Php 7.x) Apr 14, 2020

Git for PHP developers [sync]

See details
Coding (Php 7.x) May 20, 2020

Domain-driven design quickest {the basics}

See details
Coding (Php 7.x) May 27, 2020

Domain-driven design {building blocks}

See details
Get my free books' review to improve your skill now!
I don't want to improve