Event emitter dünyası dışarıdan bakınca pek heyecanlı görünmüyor. Hani şöyle “tamam işte, dinleyici ekle, olay gönder, bitsin” diye düşünüyorsunuz ya… sonra bir gün küçük bir yarış durumu yüzünden yanlış sırada çalışan bir handler buluyorsunuz. Bütün geceyi o minicik bug’a harcıyorsunuz. İşin aslı şu ki Zephyr Events tam da bu tatsız köşeye dokunuyor.
İtiraf edeyim, Bogdan “Bodo” Dumitrescu’nun çıkardığı bu küçük TypeScript kütüphanesi, sadece boyutuyla değil yaklaşımıyla da farklı bir yerde duruyor (ki bu çoğu kişinin gözünden kaçıyor). 2 KB civarında, bağımlılığı yok denecek kadar az. En önemlisi şu can sıkıcı senaryoya karşı dayanıklı: bir handler kendi çalışırken off() çağırırsa, sonraki handler’ın atlanması meselesi. Ben bu tarz sorunu ilk kez 2022’nin sonlarında İstanbul’da bir yan projede yaşamıştım — ufak bir chat servisinde bildirimler bazen yarım kalıyordu, loglara baktım, her şey “normal” görünüyordu. Normalmiş gibi yapan bug’lar zaten en sinir bozucu olanlar, değil mi? Hiçbir iz bırakmıyor, sessizce yiyor sizi.
Neden böyle bir kütüphaneye ihtiyaç var?
Bak şimdi… event emitter dediğimiz şey uygulamanın arka planında sessiz sedasız çalışan ama sistemi ayakta tutan parçalardan biri. UI tarafında buton tıklaması olur, backend’de veri geldiği anda başka modüller haberdar edilir, oyun motorunda skor değişir, analitikte bir olay kaydedilir — kısacası her yere sızmış durumda. Fark etmeden kullanıyorsunuz zaten.
Sorun da tam burada başlıyor. Çoğu geliştirici event sistemini kurduktan sonra uzun süre unutuyor çünkü ilk günlerde gayet iyi çalışıyor. Evet, gayet iyi. Ama handler sayısı artınca veya biri “ben bu event içinde kendimi kaldırayım” deyince ince çatlaklar çıkıyor — Node’un yerleşik EventEmitter’ında, EventEmitter3’te, mitt’te, hepsinde benzer sürprizler var. Bunu geçen mart ayında Kadıköy’de birlikte çalıştığım bir ekipte tekrar gördüm; test ortamında sapasağlam geçiyor gibi duran akış prod’da iki kez patladı. Tam anlamıyla “neden?” diye bakakaldık.
Zephyr Events’in hoş tarafı şu: problemi gizlemeye çalışmıyor, doğrudan tasarım kararına çeviriyor. Güvenli iterasyon istiyorsanız bunu veriyor; daha hızlı ama daha riskli yolu seçmek isterseniz ayrı mod sunuyor. Açık konuşayım, bu ayrım kağıt üstünde güzel görünmekle kalmıyor — pratikte de mantıklı duruyor.
Snapshot tabanlı yapı ne yapıyor?
Aslında — dur bir saniye, önce şunu söyleyeyim — “snapshot-based iteration” kulağa ağır geliyor ama mantık günlük hayattan o kadar da uzak değil. Diyelim ki kalabalık bir toplantıda isim listesiyle ilerliyorsunuz; biri kalkıp gidince siz elinizdeki güncel listeyi karıştırmak yerine o anki nottan devam ediyorsunuz. İşte Zephyr Events kabaca bunu yapıyor. Basit. Neredeyse sıradan.
Bu yaklaşımın artısı net: emit sırasında subscribe ya da unsubscribe artık yayının akışını bozmaz. Mesela bir listener kendi görevini bitirip sahneden — itiraz edebilirsiniz tabi — çekiliyorsa, bir sonraki listener yine çalışır, terlemez, atlanmaz. Bu detay küçük görünüyor ama büyük projede domino etkisi yaratabiliyor — inanın bana, bir kez yaşayınca anlıyorsunuz (buna dikkat edin)
import { zephyrEvents } from 'zephyr-events';
type Events = {
'user:login': { id: number; name: string };
error: Error;
};
const emitter = zephyrEvents<Events>();
const unsub = emitter.on('user:login', (user) => {
console.log(`Welcome ${user.name}`);
});
emitter.emit('user:login', { id: 1, name: 'Alice' });
unsub();
Şahsen, Kod örneği basit görünüyor. Ama arka planda ciddi fark yaratıyor. Tip güvenliği yalnızca “string event adı yazdım geçti” seviyesinde kalmıyor; handler imzası da sıkı tutuluyor, yani yanlış payload gönderirseniz derleme zamanında yüzünüze vuruyor. Geçen yıl Ankara’daki küçük bir SaaS ürününde buna benzer güçlü tip tanımı kullanmıştık ve hatalı payload gönderen iki ayrı yeri compile aşamasında yakalamıştık. O gün debug süresi bayağı düşmüştü. Bayağı. Bu konuyla ilgili AI Reasoning Sistemleri: Zihin Teorisi Gerçekten Geldi mi? yazımıza da göz atmanızı tavsiye ederim.
| Özellik | Klasik yaklaşım | Zephyr Events |
|---|---|---|
| Emit sırasında off() | Bazen sonraki handler atlanabilir | Snapshot sayesinde güvenli |
| Paket boyutu | Daha şişkin olabilir | Yaklaşık 1.9–2 KB |
| Tip desteği | Sınırlı ya da gevşek olabilir | Tam TypeScript generics desteği |
| Performans modu | Tek yol vardır çoğu zaman | Zehirli olmayan hızlı mod var |
| Takas noktası | Kod kolaylığı / belirsizlik | Güvenlik ile hız arasında seçim imkânı |
Sadece güvenlik değil, hız pazarlığı da var
“Safe” ile “fast” arasındaki çizgi
E tabi işin diğer yüzü performans meselesi (şaşırtıcı ama gerçek). Snapshot almak her zaman bedava değil — özellikle yüksek frekansta event fırlatan sistemlerde ekstra kopyalama maliyeti hissedilebilir, bu gerçek (ben de ilk duyduğumda şaşırmıştım). Zephyr Events burada dürüst davranıp zephyrEventsFast diye ayrı bir kapı açıyor ve bazı senaryolarda yüzde 82’ye kadar hız kazancı sunduğunu söylüyor. İddia büyük. Test etmek lazım tabii. Daha fazla bilgi için Multi-Turn Prompt Injection: ML’siz Tespit Taktikleri yazımıza bakabilirsiniz. Erişilebilirlik Skoru Size Yalan Söylüyor: Neye Güvenmeli? yazımızda bu konuya da değinmiştik.
Bana kalırsa bu ayrım iyi bir fikir ama herkes için otomatik doğru seçenek değil (ben de ilk duyduğumda şaşırmıştım). Küçük bir startup’ta birkaç dashboard olayı için safe mod fazlasıyla yeterli olabilirken, enterprise seviyede saniyede binlerce emit varsa fast moda göz atmak gerekir — tabii ölçerek, kör kör değil. Benim geçen sene İzmir’de incelediğim iç araçlardan birinde tam böyle oldu; başlangıçta güvenli mod kullandılar, yoğunluk artınca kritik path’leri fast’e aldılar. Ölçümlerde rahatlama gördüler. Anlamlı bir rahatlama.
Şöyle söyleyeyim, Neyse uzatmayalım: burada önemli olan tek cevap vermek değil, doğru varsayılanı seçmek. Bu konuda %100 emin değilim ama sanırım çoğu ekip için güvenli olanın varsayılan olması daha az baş ağrıtır. Çünkü insanlar varsayılanları değiştirmiyor genelde.
Emit sırasında listener değiştirmek masum görünür ama bazen zinciri kırar… Zephyr Events’in yaptığı şey tam olarak bu zinciri sağlam tutmak.
Kime uygun? Startup mı kurumsal yapı mı?
Bi saniye — Küçük ekiplerde işler genelde daha hızlı döner ama disiplin zayıflarsa bug’lar çabuk büyür. Bir startup’ta ürün ekibi sabah yeni feature isterken öğleden sonra analitik event’i değiştiriyor, tam orada tipi sıkı tutan sistem hayat kurtarıyor. Zephyr Events gibi hafif çözümler burada iyi oturuyor. Bağımlılık yükü yok denecek kadar az — bir de paket yöneticisi tarafında kasıntı yaşamıyorsunuz, bu küçük detay aslında büyük rahatlık.
Eğer kurumsal taraftaysanız mesele biraz farklılaşıyor. Orada konu sadece performans değil; bakım maliyeti, gözlemlenebilirlik ve ekipler arası sözleşme oluyor. Benim deneyimimde büyük organizasyonlarda en pahalı hata çoğu zaman CPU yemiyor — insan zamanı yiyor. Bu yüzden snapshot temelli güvenlik önemli olabilir. Ama eş zamanlı olarak benchmark şart, kimseye inanmadan ölçün.
Aklınızda kalması gereken üç pratik nokta
- Kritik akışlarda güvenli modu tercih edin.
- Saniyeler içinde milyonlarca event dönüyorsa fast modu ölçün. (bence en önemlisi)
- Paket boyutu önemliyse tree-shakeable yapı avantaj sağlar.
Peki eksik yani yok mu?
Var tabii. Her şeyi övüp göklere çıkaracak halimiz yok. İlk eksik taraf performans algısı olabilir; yani safe mode’u herkes aktif bırakırsa “küçücük kütüphane” hissi yerini gereksiz overhead’e bırakabilir, özellikle kimse düşünmeden devam ederse. İkinci mesele ise API tercihi — kimi geliştirici daha minimal syntax isterken kimi de Node ekosistemine birebir benzeyen davranışı sever. Hangisi doğru? Bilmiyorum. İkisi de tartışılır.
Evet, doğru duydunuz.
Eh, Bence burada beklediğim kadar parlak olmayan nokta şu: ayrılmış safe/fast yaklaşımı akıllıca olsa da belgelerde iyice anlatılmazsa kullanıcı yanlış modu seçebilir. Teknik olarak güzel çözüm, ama iletişim kısmı biraz daha pişmeli. Bir arkadaşım Berlin’deki ürün takımında benzer ikili modu olan başka bir utility kullanmıştı; ekiplerin yarısı hangi modu niye açtığını bilmeden ilerliyordu ve sonuç karmaşa olmuştu. Belge yazmak sıkıcı ama bu yüzden önemli.
Neden yine de ilgimi çekti?
Lafı gevelemeden söyleyeyim: küçücük araçlarla büyük dertlerin çözülmesi bana hep cazip gelmiştir. 2024’ün Kasım ayında editör masasında bu haberi görünce hemen test etmek istedim çünkü “race-condition safe emitter” ifadesi lafta kolay söylenir. Kodda işi gerçekten zordur. Birkaç satırlık örnek bile fikri net veriyor:
const off = emitter.on('tick', () => {
off();
});
emitter.on('tick', () => {
console.log('İkinci listener kaçmaz.');
});
emitter.emit('tick');
Araya gireyim: Böyle durumlarda ikinci listener’ın gerçekten çalışması çok şey anlatıyor. Sistem size “seni yarıda kesmem” diyorsa güven duygusu oluşuyor —. Bu güven duygusu, özellikle production’da beklenmedik bir anda çöken bir sistemin ardından geliyorsa, paha biçilmez oluyor. Tabii bunun bedeli var mı? Var. Ama mühendislik zaten bedelsiz rahatlık oyunu değil. WebAssembly 3.0 ve .NET: 2026’da Web Uygulamalarının Yeni Ritmi yazımızda da bu konuya değinmiştik.
Sıkça Sorulan Sorular
Zep hyr Events Node.js EventEmitter yerine kullanılabilir mi?
Evet, küçük ve orta ölçekli projelerde kullanılabilir.
En çok da TypeScript tipi sıkılığı ve emit sırasında gelen güvenlik ihtiyacı varsa mantıklı durur.
Ama mevcut altyapınız Node’un yerleşik davranışına birebir bağlıysa önce test etmeniz gerekir.
Safe mod ile fast mod arasındaki temel fark nedir?
Fast mod ise ekstra korumaları azaltıp daha hızlı çalışmayı hedefler.
Hangi modun uygun olduğu tamamen kullanım yoğunluğuna bağlıdır.
Paket boyutu gerçekten neden önemli?Paket boyutu mobil web’den SSR’a kadar birçok yerde hissedilir.
Kütüphane ne kadar hafifse başlangıç süresi ve bundle baskısı o kadar azalır.
Mesela çok sayıda bağımlılık kullanan projelerde küçük farklar bile önem kazanır.
Tamam da her projede gerekli mi?Hayır.
Kütüphane ne kadar hafifse başlangıç süresi ve bundle baskısı o kadar azalır.
Mesela çok sayıda bağımlılık kullanan projelerde küçük farklar bile önem kazanır.
Eğer uygulamanızda çok az event varsa ya da listeners üzerinde karmaşık müdahaleler olmuyorsa daha basit çözümler işinizi görebilir.
Zephyr Events özellikle ince bug’lardan kaçınmak isteyen ekipler için anlamlı.
Zephyr Events npm PaketiNode.js events Kaynak Kodumitt GitHub SayfasiEventEmitter3 GitHub Sayfasi
Eğer JavaScript tarafında performansla tip guvenligini ayni cati altinda dusunuyorsaniz,
bu tür minik kutuphaneler gözden kacmamali.
Ayrıca su yazilarimizi da okuyabilirsiniz:
AI Reasoning Sistemleri:Zihin Teorisi Gerçekten Geldi mi?
>>
Bu içerik işinize yaradı mı?
Benzer içerikleri kaçırmamak için beni sosyal medyada takip edin.



