İçeriğe geç
Muhammet Şafak
Diller 3 dk okuma

PHP'de tasarım desenlerini abartmadan kullanmak

Tasarım desenleri amaç değil araç. PHP'de hangi deseni ne zaman kullanmak gerektiği ve ne zaman gereksiz karmaşıklık yarattığı üzerine.


Tasarım desenleri öğrenildiğinde bir süre her yerde görülür. Bir form işleyicisi yazıyorsunuz, observer deseni aklınıza gelir. Bir veritabanı bağlantısı yönetiyorsunuz, singleton deseni akla gelir. Yeni bir kavram öğrenildiğinde onu her yere uygulamak doğal bir dürtü — ama bu dönem aşılmadan desenlerden gerçek değer alınamaz.

Ben de bu dönemden geçtim. Kod tabanlarında her sınıfın bir deseni taklit ettiği, ama hiçbirinin problemi gerçekten çözmediği projeler gördüm. Desenin kendisi doğruydu; ama ihtiyaç yoktu.

Desen bir çözüm, problem değil

Tasarım deseni, belirli bir bağlamda tekrar eden bir probleme kanıtlanmış bir çözümdür. Tanımın üç parçası da önemli: belirli bağlam, tekrar eden problem, kanıtlanmış çözüm.

Bağlam yoksa, problem yoksa — desen de yoktur.

Örüntü (pattern) dilini bilmek, o örüntüyü her fırsatta kullanmak zorunda olduğunuz anlamına gelmiyor. Bir tamircinin elinde tornavida, çekiç ve pense olması, vidayı çekiçle çakmayacağı anlamına gelir.

Gerçekten işe yaradığı yerler

PHP’de günlük geliştirmede gerçek değer gördüğüm birkaç desen var.

Strateji (Strategy): Birbirleriyle değiştirilebilir algoritmaları kapsüllemek için. Ödeme yöntemi, ihracat formatı, bildirim kanalı — bunlar tipik strateji kullanım yerleri. Yeni bir seçenek eklediğinizde mevcut kodu değiştirmiyorsunuz, yeni bir strateji sınıfı yazıyorsunuz.

interface PaymentStrategy
{
    public function charge(int $amount): bool;
}

class CreditCardPayment implements PaymentStrategy
{
    public function charge(int $amount): bool
    {
        // Kart işlemi
        return true;
    }
}

class BankTransferPayment implements PaymentStrategy
{
    public function charge(int $amount): bool
    {
        // Havale işlemi
        return true;
    }
}

class OrderProcessor
{
    public function __construct(
        private readonly PaymentStrategy $payment
    ) {}

    public function process(int $amount): bool
    {
        return $this->payment->charge($amount);
    }
}

Bu kod açık-kapalı ilkesini (Open-Closed Principle) doğal olarak takip ediyor, ama asıl kazanç orada değil. Asıl kazanç: ödeme mantığını test etmek için gerçek ödeme altyapısına ihtiyaç kalmıyor.

Dekoratör (Decorator): Mevcut nesnenin davranışını değiştirmeden üzerine ekleme yapmak için. Cache katmanı, loglama, rate limiting — bunlar mevcut işlevselliği sarmalar. Miras (inheritance) yerine kompozisyonla çalıştığı için daha esnek.

Şablon metodu (Template Method): Bir algoritmanın iskeletini üst sınıfta tanımlayıp adımları alt sınıflara bırakmak için. Laravel’in queued job sınıfları bu deseni kullanır: handle() metodunu siz yazarsınız, geri kalanını framework yönetir.

Abartının işaretleri

Bir deseni gereğinden fazla kullandığınızı nasıl anlarsınız?

İlki: soyut bir sınıf ya da interface yazdınız, onu implement eden tek bir sınıf var ve başka implement ekleme planınız yok. Bu, soyutlamanın değil törpünün kullanılacağı yer.

İkincisi: koda bakan birine “bu neden böyle?” diye sorduğunuzda cevap “desen kullandım” oluyor. Desenin adı bir gerekçe değil. Hangi sorunu çözdüğü gerekçe.

Üçüncüsü: basit bir fonksiyonla çözülebilecek şey için sınıf hiyerarşisi oluşturulmuş. PHP’de her şey nesne olmak zorunda değil. Bir dönüştürme işlemi ya da bir hesaplama, bazen sadece bir fonksiyon.

// Gereksiz fabrika (factory) sınıfı
class SlugFactory
{
    public function make(string $title): string
    {
        return strtolower(str_replace(' ', '-', $title));
    }
}

// Yeterince iyi
function make_slug(string $title): string
{
    return strtolower(str_replace(' ', '-', $title));
}

PHP’ye özgü bir not

PHP’de Laravel ya da Symfony gibi framework’ler birçok deseni zaten sağlıyor. Service container, dependency injection desenini yönetiyor. Olay sistemi observer desenini kapsıyor. Bunları kendiniz yazmaya kalkışmak, çoğu durumda framework’ü yeniden icat etmek anlamına gelir.

Bu desenleri framework aracılığıyla kullanmayı, yoktan yazmaktan ayırt etmek önemli. İkincisini yapmadan önce, ihtiyacı framework’ün zaten çözmediğinden emin olun.


Desenler, deneyimli geliştiricilerin paylaştığı bir iletişim dili. Birbirinizle konuşurken “burada strateji deseni kullandım” demek, tasarım kararını paragraflarla açıklamaktan çok daha verimli. Bu değer gerçek. Ama bu dili öğrenmek, her cümleyi teknik terimlerle doldurmak anlamına gelmiyor; sadece gerektiğinde doğru sözcüğü bulmak anlamına geliyor.

Etiketler: #PHP#OOP
Paylaş:

İlgili Yazılar

Sitede Ara

Yazı, proje ve sayfalarda arama yapmak için yazmaya başlayın.

Esc ile kapat Pagefind ile güçlendirildi