Builder Tasarım Kalıbı Nedir?



3 dakikalık okuma
July 28, 2019

Builder tasarım kalıbı da Tasarım kalıplarının “Creational” kategorisi içerisinde yer alır. Bu kategori önceden de bahsettiğim üzere nesnelerin oluşturulması ve yönetilmesi ile ilgili kalıpların bulunduğu kategoridir.

Bu tasarım kalıbı, bazı nesnelerin “constructor” kısmında karmaşık değişkenler girmek zorunda olduğumuz zaman bu durumu basitleştirerek daha okunaklı, tekrar kullanılabilir ve bakımı kolay yapılabilir hale getirir.

Örnekle anlatmaya devam edelim.

Mesela bir “Pizza” sınıfımız olsun. Bu tasarım kalıbını kullanmadan önce şöyle bir tasarım yaptığımızı farz edin:

<?php

class Pizza
{
    private $tarif;
    private $ekPeynir;
    private $boyut;
    private $sos

    public function __construct(string $tarif, bool $ekPeynir, int $boyut, string $sos) 
    {
        $this->tarif    = $tarif;
        $this->ekPeynir = $ekPeynir;
        $this->boyut    = $boyut;
        $this->sos      = $sos;
    } 

    public function olusturulanPizza():string
    {
        $peynir = $this->ekPeynir ? " (ek peynir)" : "";

        return $this->tarif.$peynir. " pizza ile ". $this->sos.
        " sos ve boyutu ".$this->size;

    }

}

Kullanımı:

$pizzam = new Pizza('Margarita',true,10,'ketçap');
echo $pizzam->olusturulanPizza();

Yukarıdaki koda şöyle bir göz attığımızda idare ettiğini görüyoruz ama nesne oluştururken girilen parametre değişkenleri gerçekten biraz karışık gibi duruyor. Bu parametre sayısının çok daha fazla olduğunu düşünürseniz ne kadar çirkin duracağını siz düşünün.

İşte bu durumlarda “Builder” tasarım kalıbını kullanarak constructor’da kullanacağımız değişkenlerin sayısını azaltarak kodumuzu daha okunaklı, tekrar kullanılabilen ve bakımı kolay yapabiliriz.

Evvela bir PizzaBuilder adında sınıf oluşturalım:

class PizzaBuilder
{
    private $tarif;
    private $ekPeynir;
    private $boyut;
    private $sos

    public function __construct(string $tarif)
    {
        $this->tarif    = $tarif;

        //ön değerler giriyorum. Kullanılmadığında
        // otomatik bunları atayacak.
        $this->ekPeynir = false
        $this->boyut    = 10;
        $this->sos      = 'ketçap';     
    }

    public function peynirEkle()
    {
        $this->ekPeynir = true;
        return $this;
    }

    public function boyutBelirle(int $boyut)
    {
        $this->boyut = $boyut;

        return $this;
    }  

    public function sosEkle(string $sos)
    {
        $this->sos = $sos;

        return $this;

    }

    //magic metod kullandım. Private değişkenler($tarif,$ekPeynir,$boyut,$sos) sınıf dışı kullanıldığında küçük bir hile ile  bunları bu magic metod ile dışarıda kullanıma sunuyorum. Aşağıdaki Pizza sınıfında göreceksiniz bunu.
    public function __get($propertyName)
    {
        return $this->$propertyName;
    }
}

Şimdi “Pizza” sınıfımıza özelleştirilmiş pizza menümüzü dışarıdan enjekte edebiliriz. Şöyle:

class Pizza
{
    private $tarif;
    private $ekPeynir;
    private $boyut;
    private $sos

    public __construct(PizzaBuilder $builder)
    {
        $this->tarif    = $builder->tarif;
        $this->ekPeynir = $builder->ekPeynir;
        $this->boyut    = $builder->boyut;
        $this->sos      = $builder->sos;            
    }   

    public function olusturulanPizza():string
    {
        $peynir = $this->ekPeynir ? " (ek peynir)" : "";

        return $this->tarif.$peynir. " pizza ile ". $this->sos.
        " sos ve boyutu ".$this->size;

    }
}

Kullanımı:

$pizzam = (new PizzaBuilder('FourCheese'))
                     ->peynirEkle()
                     ->sosEkle('Acılı Domates Sosu');

//ya da

$pizzam = (new PizzaBuilder('Margarita'))
                     ->peynirEkle()
                     ->boyutBelirle(8)
                     ->sosEkle('Tatlı Domates Sosu');


$pizzaHazirla = new Pizza($pizzam);
echo $pizza->olusturulanPizza();                 

Nasıl ama ?


Etiketler: