← Tüm yazılar
2 dk okuma

AWS Lambda üzerinde gerçek zamanlı stok kontrol sistemi tasarlamak

awsserverlessmimarievent-driven

Aynı parfümü tek bir havalimanının içindeki 23 mağazada satıyorsanız, "kaç tane kaldı?" artık basit bir soru olmaktan çıkar. Bir yolcu son ürünü bir kapıda satın alırken, bir diğeri iki terminal ötede aynı ürüne uzanıyor olabilir. Yanlış yaparsanız ya elinizde olmayan stoğu satarsınız ya da satabileceğiniz stoğu gizlemiş olursunuz.

İstanbul Havalimanı'ndaki Unifree duty-free operasyonu için Stok Kontrol Sistemi'ni (SCS) kurarken çözdüğümüz problem buydu. Yaklaşımımızı — ve benzer bir "gerçek zamanlı paylaşımlı envanter" problemiyle karşılaşan her founder'a söyleyeceklerimi — burada anlatıyorum.

Neden serverless, neden event-driven

Bir havalimanının yük profili doğası gereği dalgalıdır. Uçuşlar kümelenir, terminaller boşalıp dolar, aralarda sistem uzun süre boşta bekler. Zirveye göre sunucu ayırmak, en dip an için para ödemek demektir. AWS Lambda talebe göre ölçeklenmemizi ve yalnızca gerçekten kullandığımız kadarını ödememizi sağladı.

Ama daha büyük karar sistemi event-driven yapmaktı. Her satış, iade ve stok girişi bir olaydır. Tek bir servisin paylaşılan bir sayacı oku-değiştir-yaz yapmaya (ve kilitler üzerinde boğuşmaya) çalışması yerine, her olay envanter durumunu güncelleyen ve bilmesi gerekenlere dağıtan bir pipeline'dan akar.

Kimsenin bahsetmediği ödünleşme

Gerçek zamanlı envanterin rahatsız edici bir gerçeği var: doğruluğa da sahip olabilirsiniz erişilebilirliğe de, ama uçlarda seçim yapmak zorundasınız. İki kasa aynı saniye içinde son ürüne satış işlerse, bir şeyden vazgeçmek gerekir.

Idempotent olay işleme ve sayım için tek bir doğruluk kaynağına yaslandık; çift satış riskine girmektense arayüzün gerçeğin bir adım gerisinde bir sayı göstermesini kabul ettik. Bir duty-free mağazası için doğru karar bu — anlık olarak temkinli bir sayım, kapıda elinde var olmayan bir ürünün fişini tutan bir müşteriden çok daha ucuzdur.

Bir founder'a söyleyeceğim

Paylaşımlı, çekişmeli durum üzerine bir şey kuruyorsanız — envanter, koltuk, limit, bakiye — framework seçiminizden daha çok üç şey önemli:

  1. Onu mutasyona uğrattığınız bir sayı değil, olaylar olarak modelleyin. Sayı bir izdüşümdür; olaylar gerçektir.
  2. Hata modunuza bilerek karar verin. Fazla mı satarsınız eksik mi? Bayat okuma mı, bloke yazma mı? Trafik sizin yerinize seçmeden siz seçin.
  3. Her handler'ı idempotent yapın. Dağıtık sistemlerde retry bir uç durum değildir; sıradan bir salıdır.

Serverless kısmı neredeyse teferruat. Zor olan — ve doğru yapmaya değen — kısım, iki gerçek çakıştığında "doğru"nun ne demek olduğu konusunda bilinçli olmak.


Founder'lara ve ekiplere tam da bu tür problemlerde yardım ediyorum. Gerçek yük altında tutarlı kalması gereken çekişmeli bir sisteme bakıyorsan, konuşalım.