event driven design, sistemin “biri bir şey yaptıysa herkes bilsin ama kimse kimsenin yakasına yapışmasın” diye tasarlanmış halidir.

kulağa medeni geliyor.

ama yanlış yapılırsa medeni değil, apartman whatsapp grubu olur.

herkes bir şey yazar.

kimse ne olduğunu tam anlamaz.

sonra biri gece 03:00’te “bu event’i kim dinliyor?” diye production loglarında ayin yapar.

event driven design’ın mantığı basittir: sistemde önemli bir şey olur, bu olay event olarak yayınlanır. diğer parçalar da bu olayı dinler ve kendi işini yapar.

sipariş oluşturuldu.

ödeme alındı.

stok düştü.

fatura kesildi.

kargo süreci başladı.

müşteriye mail gönderildi.

bunların hepsi birbirinin boğazına sarılmadan çalışabilir. sipariş servisi “ben mail attım mı, stok düştü mü, fatura kesildi mi?” diye her yere telefon açmaz. sadece der ki:

“ordercreated.”

gerisi duyanın problemi.

işte olay burada güzelleşir.

çünkü iyi event-driven mimaride sistemler birbirine bağımlı olmadan haberleşir. her servis kendi işini bilir. bir olay olur, ilgilenen alır, kendi tarafında gerekeni yapar. bu, doğru kurulduğunda sistemin nefes almasını sağlar.

monolitin içinde her şeyin birbirine elini soktuğu çorba yerine, daha gevşek bağlı, daha esnek, daha genişleyebilir bir yapı oluşur.

ama buradan şu sonuç çıkmasın:

“her şeye event basalım.”

hayır kardeşim.

her şeye event basarsan mimari kurmazsın.

kafka’ya dedikodu taşırsın.

event driven design’ın en büyük tuzağı budur. insan bir kere event fikrini sevince her şeyi event yapmak istiyor. userloggedın. userlookedatbutton. useralmostclicked. userchangedmind. userbreathed. userprobablyexists.

sonra sistemde event var ama anlam yok.

bu, düğün salonunda herkesin mikrofon alıp konuşması gibi. ses çok. bilgi az.

iyi event, domain açısından anlamlı olaydır.

“ordercreated” anlamlıdır.

“paymentfailed” anlamlıdır.

“stockreserved” anlamlıdır.

“ınvoiceıssued” anlamlıdır.

ama “databaserowupdated” diye event fırlatıyorsan geçmiş olsun. sen domain event değil, veritabanı geğirmesi yayınlıyorsun.

event dediğin şey teknik çöp olmamalı.

iş dünyasında karşılığı olmalı.

bir iş olayı yaşanmış olmalı.

yani event, sistemin “bir şey değişti” demesi değil; domain’in “önemli bir şey oldu” demesidir.

aradaki farkı anlamayan adam event-driven değil, log-driven kaos yazar.

event driven design’ın güzelliği, özellikle büyük sistemlerde ortaya çıkar. sipariş sistemi ödeme sistemine göbekten bağlı olmaz. ödeme sistemi kargo sisteminin telefonunu beklemez. mail sistemi faturanın burnuna girmez. herkes olayı dinler, kendi kararını verir.

bu yapı doğru kurulursa sistem daha dayanıklı olur.

bir servis düşerse bütün sistem mezara girmez.

event kuyruğa düşer.

servis kalkınca işler devam eder.

kulağa güzel geliyor.

çünkü güzel.

ama tabii yazılım dünyasında her güzel şeyin altında bir çukur vardır.

event-driven sistemlerde debug yapmak bazen normal hata ayıklama değil, olay yeri inceleme olur.

bir sipariş neden faturalandırılmadı?

ordercreated atılmış mı?

atılmış.

paymentcompleted gelmiş mi?

gelmiş.

stockreserved olmuş mu?

olmuş gibi.

ınvoiceservice dinlemiş mi?

dinlemiş ama retry patlamış.

retry neden patlamış?

message schema değişmiş.

kim değiştirmiş?

geçen ay ayrılan burak.

belge var mı?

yok.

tebrikler.

artık mimari değil, polisiye roman okuyorsun.

event-driven sistemlerde en büyük sorunlardan biri görünmez akıştır. request-response dünyasında en azından kim kimi çağırıyor bellidir. burada event yayınlanır, sonra kim dinliyor, ne yapıyor, hangi sırayla yapıyor, hata olursa ne oluyor, retry kaç kere dönüyor; bunları düzgün tasarlamazsan sistemin içinde hayalet tren dolaşır.

iş çalışıyor gibi görünür.

ta ki çalışmayana kadar.

sonra herkes event kuyruğuna bakar.

kuyruk da sana bakar.

bu mimaride idempotency denen şey hayat memat meselesidir. aynı event iki kere gelirse ne olacak? sipariş iki kere mi oluşacak? müşteriden iki kere mi para çekeceksin? aynı faturayı iki kere mi keseceksin? aynı maili beş kere mi atacaksın?

“bir kere gelir ya” diyorsan, production seni eğitir.

hem de sert eğitir.

event-driven dünyada event’in bir kere gelmesini ummak, yağmurda sunucu odasının tavanına güvenmek gibidir. olabilir. ama mimari bunun üstüne kurulmaz.

iyi sistem aynı event iki kere gelse de sapıtmaz.

kötü sistem iki kere gelen event’le müşteriye iki kargo yollar, sonra support ekibi “sistemsel bir durum olmuş” diye kurumsal ağıt yakar.

event ordering de başka bir derttir.

olayların sırası önemliyse iyi düşünmen gerekir.

paymentcompleted, ordercreated’dan önce işlenirse ne olacak?

stockreleased, stockreserved’dan önce gelirse ne olacak?

userdeleted geldikten sonra userupdated gelirse sistem ne yapacak?

bunlar teorik soru değildir.

distributed sistemler teorik soruları production’da tokat olarak geri verir.

event-driven design biraz da şunu kabul etmektir:

sistem artık tek parça düşünmüyor.

parçalar konuşuyor.

ama her konuşma aynı anda duyulmuyor.

bazıları geç duyuyor.

bazıları iki kere duyuyor.

bazıları hiç duymuyor.

bazıları duyup yanlış anlıyor.

yani mimari kurarken insan ilişkileri simülasyonu yapıyorsun.

bu yüzden event schema çok önemlidir. event’in formatı, adı, versiyonu, taşıdığı veri, anlamı net olacak. “userupdated” diye event atıp içine ne değiştiğini koymazsan, dinleyen servis kristal küreyle çalışmak zorunda kalır.

event adı net olacak.

payload net olacak.

versioning net olacak.

backward compatibility düşünülecek.

kim yayınlıyor, kim tüketiyor, ne garanti ediliyor, ne edilmiyor belli olacak.

yoksa event değil, dijital sis bombası atıyorsun.

bir de event-driven design ile event sourcing karıştırılır.

bu da ayrı komedi.

event-driven design, sistemlerin olaylarla haberleşmesi demektir.

event sourcing ise sistemin state’ini event geçmişinden üretmektir.

yani biri mahalleye “yangın çıktı” diye haber salmaksa, diğeri mahallenin bütün tarihini yangın, tamir, taşınma, kavga kayıtlarından yeniden kurmaktır.

ikisi akraba olabilir.

aynı şey değildir.

bunu karıştıran ekipler genelde üçüncü sprintte kendi mimarilerinden korkmaya başlar.

event sourcing güzel tekniktir ama her yere basılmaz. basit crud paneline event sourcing gömersen sistem değil, arşiv bakanlığı kurarsın. müşteri “ürünü güncelle” der. sen “productnamechanged event’i üzerinden aggregate rebuild edelim” diye ayağa kalkarsın.

kardeşim dur.

ürün adı değişti.

roma yanmadı.

event-driven design da aynı şekilde her projeye gerekmez. küçük sistemde, basit iş akışında, iki tablo bir panelde event bus kuruyorsan büyük ihtimalle mimari değil, cv süslüyorsundur.

ama karmaşık domain varsa, farklı sistemler gevşek bağlı çalışacaksa, işlemler asenkron ilerleyecekse, ölçek ve dayanıklılık önemliyse, event-driven design çok güçlüdür.

doğru yerde kullanılırsa sistemin omurgasını rahatlatır.

yanlış yerde kullanılırsa herkesin birbirine bağırdığı dağıtık bir tımarhane olur.

iyi event-driven mimaride olaylar anlam taşır.

kötüsünde event kuyruğu çöp tenekesine döner.

iyi sistemde servisler birbirinden bağımsız nefes alır.

kötüsünde biri hapşırınca üç servis retry’a düşer, iki consumer ölür, biri aynı maili altı kere atar.

iyi sistemde event izlenebilir.

kötüsünde event kayboldu mu, işlendi mi, öldü mü, tatile mi çıktı kimse bilmez.

iyi sistemde eventual consistency bilinçli tercihtir.

kötüsünde “veri birazdan düzelir” diye dua edilir.

event-driven design’ın en sevdiğim tarafı şu: doğru kullanıldığında iş süreçlerini daha doğal modelletir. çünkü gerçek hayatta da olaylar olur ve başka şeyleri tetikler.

müşteri ödeme yapar.

muhasebe etkilenir.

stok etkilenir.

kargo etkilenir.

bildirim etkilenir.

raporlama etkilenir.

bunların hepsini tek request içinde sıraya dizip “hepsi başarılı olmazsa hiçbir şey olmasın” demek bazen sistemin boğazına ip takmaktır.

event-driven yapı der ki:

olay gerçekleşti.

şimdi ilgililer kendi işini yapsın.

bu sağlıklı.

ama sadece disiplin varsa.

disiplin yoksa event-driven design, kontrolsüz dedikodu mimarisidir.

kim ne duydu belli değil.

kim ne yaptı belli değil.

kim ne zaman yaptı belli değil.

sonra müşteri arar:

“siparişim oluştu ama fatura yok.”

sen de sistemde geriye doğru iz sürersin.

sipariş var.

ödeme var.

event var.

consumer yok.

log yok.

dokümantasyon yok.

sadece kafka’nın derinliklerinden gelen hafif bir uğultu var.

o uğultu mimari pişmanlıktır.

özetle event driven design; doğru olayları doğru kişilere duyurup sistemi gevşek bağlı, dayanıklı ve genişleyebilir hale getirme disiplinidir.

ama yanlış yapılırsa sistemin içine dağıtık belirsizlik salar.

event, domain’in anlamlı hafızası olmalıdır.

her teknik kıpırtının megafonu değil.

iyi event-driven sistem, orkestrayı yönetir.

kötü event-driven sistemde herkes davul çalar.

ve production gecesi geldiğinde kimse şefi bulamaz.
1 1
ayı kullanıcısının profil fotografı