⚙️ B4 · Service Katmanı: iş kuralları nerede yaşar
B4 · Service Katmanı: iş kuralları: Service katmanı, API'nin **karar veren yöneticisidir**: repository ham depolamayı yapar, controller request'i karşılar — ama "bir CLOSED bug t
Service katmanı, API'nin **karar veren yöneticisidir**: repository ham depolamayı yapar, controller request'i karşılar — ama "bir CLOSED bug tekrar açılabilir mi?", "aynı başlıkla iki bug oluşturulabilir mi?" gibi **iş kuralları** burada yaşar. Peki bu kuralları neden controller'a ya da repository'ye koymuyoruz, orada da çalışmaz mı? Çünkü iş kuralı controller'a girerse her yeni giriş noktası (REST, mesaj kuyruğu, zamanlanmış görev) aynı kuralı tekrar yazmak zorunda kalır ve biri sessizce farklılaşır; repository'ye girerse depolama teknolojisiyle iş mantığı birbirine yapışır. Service, kuralların **tek doğru kaynağıdır**. Java'da bunun karşılığı, bir `@Service` sınıfında toplanan ve `@Transactional` ile korunan iş mantığıdır; controller sadece "bunu yap" der, nasıl yapıldığını bilmez. QA açısından service katmanı, en değerli hataların yaşadığı yerdir: bir alan validasyonu değil, bir **iş kuralı ihlali** (kapalı bug'ın yeniden açılması, çift kayıt) çoğu zaman UI'dan görünmez ama veriyi sessizce bozar — testerın bu kuralları senaryo bazlı (state geçişleri) test etmesi gerekir.
İş Kuralları Service'te
**🐞 Defect Doğum Anı — "zaten CLOSED" kuralı unutulursa** **Kod:** `closeBug` içindeki `if (bug.getStatus() == Status.CLOSED) throw ...` kontrolü YOK; metot doğrudan status'u CLOSED yapıp kaydediyor. **Ne olur:** Zaten kapalı bir bug'a tekrar `PATCH /api/v1/bugs/42/status {"status":"CLOSED"}` gönderilince request 409/400 yerine 200 döner. Görünürde sorun yok ama eğer kapatma işlemi bir sayaç artırıyor, bildirim gönderiyor veya bir SLA kronometresi durduruyorsa, bu işlemler İKİNCİ kez tetiklenir — çift bildirim, yanlış metrik. **Neden sinsi:** Tek bir request'te hiçbir şey görünmez; kayıt zaten CLOSED'du, yine CLOSED. Yan etkiler (bildirim, metrik) sessizce tekrarlanır ve ancak raporlar tutarsızlaşınca fark edilir. **Tester nerede yakalar:** State-geçiş testinde — bir bug'ı kapat, sonra AYNI kapatmayı tekrar gönder; ikinci request'te hata (409 Conflict) bekle. İş kuralı yoksa ikinci kapatma sessizce geçer.
🎬 İki Kez Kapatmak: Görünmez Yan Etki Nasıl İki Kez Tetiklenir?
Bir bug kapatılıyor: PATCH .../status {CLOSED}. Kapatma sadece status değiştirmez — bir bildirim gönderir, SLA kronometresini durdurur.
Aynı kapatma request'i tekrar geliyor (çift tık, retry, race). Kayıt zaten CLOSED. Şimdi iş kuralı devreye girmeli.
Kural VARSA: "zaten CLOSED" kontrolü ikinci request'i 409 Conflict ile reddeder. Yan etki bir kez çalışır. Sistem tutarlı kalır.
Kural YOKSA: ikinci kapatma sessizce geçer (200), bildirim İKİNCİ kez gider, metrik iki kez artar — sessiz ama yayılan bir bozulma.
Ders — İş kuralları service katmanında yaşar ve state geçişlerini korur. Tester bunları senaryo bazlı test eder: "kapat, tekrar kapat, 409 bekle".
İş Kuralı Neden Controller'da Değil Service'te?
Controller sadece kapı…
Controller request'i alır ve service'e devreder; iş kuralı bilmez. Farklı giriş noktaları aynı service'i kullanır.
Service tek doğru kaynak…
Kural service'te tek yerde durursa REST, kuyruk, zamanlanmış görev — hepsi aynı kuralı uygular.