DistributedChallenge
Bu repoda aslında asenkron mesaj kuyruklarını hedef alan bir dağıtık sistem problemi oluşturmaya ve bu problemin çözümünü uygulamaya çalışıyorum.
Install / Use
/learn @buraksenyurt/DistributedChallengeREADME
Distributed Challenge
Bu repoda asenkron mesaj kuyruklarını hedef alan bir dağıtık sistem problemi oluşturmaya ve bu problemin çözümünü uygulamaya çalışıyorum.
- Distributed Challenge
- Geliştirme Ortamı
- Senaryo
- Aday Çözüm
- Envanter
- Baş Ağrıtacak Dayanıklılık Senaryoları
- Yapılacaklar Listesi (ToDo List)
- Sistemin Çalıştırılması
- Docker Unsurları
- Dış Sistem Entegrasyonları
- Redis Stream Entgrasyonu ile Event Takibi
- SonarQube ile Kod Kalite Ölçümü
- Secure Vault Entegrasyonu
- Local NuGet Entegrasyonu
- Github Actions ve Local Nuget Repo Problemi
- Servisler için HealthCheck Uygulaması
- Resiliency Deneyleri
- Service Discovery ve Hashicorp Consul Entegrasonu
- Ftp Entegrasyonu ile Arşivleme Stratejisi
- Planlı İşler (Scheduled Jobs)
- Elasticsearch ve Kibana Entegrasyonu ile Log Takibi
- Ölçüm Metrikleri için Prometheus ve Grafana Entegrasyonu
- POCO Diagramları
- Tartışılabilecek Problemler
- Youtube Anlatımları
Geliştirme Ortamı
Süreç boyunca iki farklı ortamda çalışma fırsatı buldum. İlki Moon isimli ev bilgisayarım. Ubuntu tabanlı sistemin özellikleri şöyle.
| Özellik | Açıklama | |-----------|-------------------------------| | OS | Ubuntu 22.04 LTS | | CPU | Intel® Core™ i7 2.80GHz × 8 | | RAM | 32 Gb | | IDE | Visual Studio Code | | Framework | .Net 8.0 |
Diğer sistem ise iş bilgisayarı ve Windows tabanlı.
| Özellik | Açıklama | |-----------|-------------------------------| | OS | Windows 10 Enterprise | | CPU | Intel(R) Core(TM) i7 2.30GHz | | RAM | 32 Gb | | IDE | Visual Studio Pro 2022 | | Framework | .Net 8.0 |
Ancak bunların haricinde herhangi bir lokasyondan da çalışma şansımız var. Bu noktada Github Codespaces oldukça işe yarıyor.
Senaryo
Kullanıcılarına oyun kiralayan bir internet şirketi olduğunu düşünelim. Şirketin son kullanıcılara (End Users) sunduğu web ve mobile bazlı uygulamalar dışında şirket genel merkezinde kullanılan Back Office tadında farklı bir programları daha var. Bu programda yer alan ekranlardan birisi de raporlama talepleri için kullanılıyor. Şirketin sahip olduğu veri miktarı ve rapor taleplerinin belli bir onay sürecinden geçip içeriklerini farklı alanlardan toplaması nedeniyle bir raporun çekilmesi bazen birkaç dakikayı bulabiliyor. Her ne kadar şirket içerisinde bu işleri üstelenen bir raporlama ekibi bulunsa da personelin kullandığı web sayfalarında bu şekilde belirsiz süreyle beklenmeleri istenmiyor. Çözüm olarak rapor talebinin girildiği bir formun tasarlanması ve talebin raporlama ekibine ait uygulamalara ulaştırılıp hazır hale geldikten sonra personelin bilgilendirilmesi şeklinde bir yol izlenmesine karar veriliyor. Tüm bu sürecin tamamen sistem tarafından gerçekleştirilmesi ve otomatize edilmesi isteniyor. İşte Örnek Birkaç Rapor İfadesi;
| Rapor Başlığı | İfade (Expression) | |---------------|---------------------| | En Pozitif Yorumları Toplayanlar | Geçtiğimiz yıl kiraladığımız oyunlardan en çok pozitif yorum alan ilk 25 adedinin ülke bazlı satış rakamları.| | Güncel Firma Bazlı Kiralamalar | Dün yapılan kiralamalardan firma ve oyun türü bazında gruplanmış kar değerleri. | | En İyi Oyuncuların Harcamaları | Geçen ay en yüksek puan alan oyuncuların yaptığı oyun için satın alma harcamalarının toplam tutarları. | | Çak Norizin Bireysel Başarımları | Dövüş oyunlarından puan olarak benimkini geçen en iyi 10 oyunun kullanım istatistikleri. | | En Sağlıklı Oyuncularımız | Oyun oynarken platformumuz üzerinden yemek siparişi verenler arasında en sağlıklı şekilde tıkınanlar | | Patlamış Mısır Sevdalıları | Hafta sonu oyuncularından en çok patlamış mısır siparişi veren ilk 1000 kullanıcının tercih ettiği markalar | | AFK Modunda Takılan Sakinler | Oyunun başından kalkıp AFK modundan kalan kullanıcılardan son bir ayda en yüksek süre duraksayanlar | | Strateji Oyunlarından Vazgeçmeyenler |Kırk yaş üstü olup 90lı yılların en popüler strateji oyunlarını kiralamaya devam edenlerin ülke bazlı harcama değerleri. |
Aday Çözüm
Bu problemi aşağıdaki gibi çözmeye çalıştığımızı düşünelim.

Senaryodaki adımları da aşağıdaki gibi tarifleyelim.
- CEO'muz geçtiğimiz yıl en çok pozitif yorum alan oyunlardan ilk 50sini ülke bazında satış rakamları ile birlikte talep eder. Bu talebi web uygulamasındaki forma girer.
- Bu rapor talebi web form üstünden kaydedildiğinde şimdilik Event Trigger Service olarak adlandırılan ve başka bir process'de yer alan bir servis tetiklenir. Servise formdaki veriler benzersiz bir ID ile (işlemleri tüm süreç boyunca benzersiz bir GUID ile takip edebilmek için) damgalanarak POST metoduyla gönderilir.
- Event Trigger Service'in tek işi gelen içeriği ReportRequestedEvent isimli bir olay mesajı olarak hazırlayıp kuyruğa bırakmaktır.
- Şimdilik Event Consumer/Publisher Gateway(Gamersworld.EventHost) diye adlandırdığımız başka bir process olayları dinlemek ve bazı aksiyonlar almakla görevlidir. ReportRequestedEvent isimli olayları dinleyen thread'leri vardır.
- Event Consumer/Publisher Gateway(Gamersworld.EventHost) servisi bir ReportRequestedEvent yakaladığında Reporting App Service(Kahin.Gateway) isimli bir başka servise POST çağrısı gönderir. Reporting App Service(Kahin.Gateway)'in gelen rapor taleplerini toplayan bir başka process olduğunu ifade edebiliriz.
- İç çalışma dinamiğini pek bilmediğimiz Reporting App Service(Kahin.Gateway) belli bir zaman diliminde raporun hazırlanmasından sorumludur. Hazırlanan raporu kendi Local Storage alanında saklar ve hazır olduğunda bunun için şimdilik External Reader Service(GamersWorld.Service.Gateway) olarak adlandırılan ve kendi Process'i içinde çalışan bir diğer servise POST bildiriminde bulunur.
- External Reader Service(GamersWorld.Service.Gateway), raporun hazır olduğuna dair ReportReadyEvent isimli yeni bir olay mesajı hazırlar ve bunu kuyruğa bırakır.
- Event Consumer/Publisher(Gamersworld.EventHost) tarafındaki Process ReportReadyEvent isimli olayları dinler.
- Event Consumer/Publisher(Gamersworld.EventHost) tarafında ReportReadyEvent yakalandığında yine farklı bir process'te çalışan Reporting File Service hizmeti GET ile çağrılır ve üretilen rapora ait PDF çıktısı çekilir.
- Servisten çekilen PDF içeriği bu sefer Back Office uygulamasının bulunduğu ağ tarafındaki local storage'e aktarılır. Aynı anda bu sefer ReportIsHereEvent isimli bir başka olay mesajı kuyruğa bırakılır.
- Kendi process'i içinde çalışan Report Trace Service isimli servis uygulaması ReportIsHereEvent olayını dinler. (Bunu da belki Event Consumer/Publisher(Gamersworld.EventHost) isimli Host uygulamasında ele alabiliriz)
- Report Trace Service hizmeti, ReportIsHereEvent isimli bir olay yakaladığında Local Storage'a gider ve ilgili PDF'i çeker.
- Rapor artık hazırdır. Rapor e-posta ile CEO'ya gönderilir ve Local Storage ortamlarında gerekli temizlikler yapılır.
Senaryoda dikkat edileceği üzere bazı ihlal noktaları da vardır. Örneğin Form uygulamasından girilen rapor talebindeki ifade geçersiz olabilir. Sistemden bilgi sızdırmaya yönelik güvensiz ifadeler içerebilir vs. Bu gibi bir durumda SystemMiddleEarth'nin geçersiz bir mesaj olduğuna dair SystemHome'ü bilgilendirmesi de gerekir. SystemMiddleEarth'nin kendi içinde ele alıp detay loglarla değerlendirdiği bu durum SystemHome'e bir Event olarak girer ve buna karşılık da bir süreç başlayabilir. Resimde görülen soru işaret kısmı dikkat edileceği üzere hata durumu yakalandıktan sonra ne yapılacağına dairdir. Rapor talebi sahibinin bilgilendirilmesi için e-posta gönderimi, sistem loglarına bilgi düşülmesi, form uygulamasında popup ile bilgilendirme yapılması vs gibi bir işler bütünü başlatılabilir.
Envanter
Güncel olarak çözüm içerisinde yer alan ve bir runtime'a sahip olan uygulamalara ait envanter aşağıdaki gibidir.
| Sistem | Servis | Tür | Görev | Dev Adres | |----------------|----------------------------------|-------------|-----------------------------------------------------------|----------------| | HAL | Eval.AuditApi | REST | Rapor talebindeki ifadeyi denetlemek | localhost:5147 | | HOME | GamersWorld.Service.Gateway | REST | Middle Earth için rapor statü güncelleme hizmeti | localhost:5102 | | HOME | GamersWorld.Service.Messenger | REST | Web önyüz için backend servisi | localhost:5234 | | HOME
