Autoscaling scale-in sırasında SIGTERM ile graceful shutdown'ı nasıl sağlarım?
Soru
AWS'te CPU %70'i geçince Autoscaling yeni EC2 açıyor, %30'un altına düşünce bazılarını kapatıyor (scale-in). Sunucu kapanırken içeride işlenen uzun HTTP istekleri veya kuyruk job'ları yarıda kesiliyor ve tutarsızlık oluşuyor. Uygulamanın (Laravel Octane / Go) `SIGTERM`'i yakalayıp mevcut istekleri bitirerek ve yeni istek almayarak zarifçe kapanmasını nasıl sağlarım?
Cevap
Kısa cevap: Scale-in işleri yarıda kesiyor çünkü uygulama SIGTERM’de drain etmiyor — sürecin kapanış yaşam döngüsünü düzeltmeniz gerekiyor.
Asıl mesele autoscaling değil, kapanış protokolü: platform SIGTERM gönderdiğinde uygulamanız ya hemen ölüyor ya da işini bitirmeden kesiliyor. Doğru sıra şu: önce trafiği kesin, sonra mevcut işi bitirin, en son ölün.
- SIGTERM’i yakalayın ve yeni istek almayı durdurun. İlk hamle, readiness probe’unu fail ettirmek veya kendinizi load balancer’dan deregister etmek; böylece LB size yeni istek yönlendirmeyi keser. Mevcut bağlantıları henüz kapatmayın — sadece akışı durdurun.
- Go’da
server.Shutdown(ctx)kullanın.signal.NotifyContextile SIGTERM’i yakalayın,http.Server’a deadline’lı bir context verin:server.Shutdown(ctx). Bu yeni bağlantıları reddeder, açık istekleri timeout’a kadar bitirir.ListenAndServe’ikill -9ile değil bu yolla sonlandırın. - Octane’de graceful stop/reload kullanın. Octane sürecini
octane:stop/graceful reload ile indirin; worker’lar mevcut isteği bitirip yenisini almaz. Kuyruk tarafındaqueue:work,kill -9atmadığınız sürece SIGTERM’i kendisi ele alır — çalışan job’ı bitirir, yeni job claim etmez. - Platformun grace süresini drain’inizle hizalayın. ASG’de lifecycle hook, k8s’te
terminationGracePeriodSecondsile platformun “öldürmeden önce kaç saniye bekleyeceğini” en uzun kabul edilebilir drain süresine eşitleyin. Aksi halde platform SIGTERM’den sonra SIGKILL atıp drain’i yarıda keser. - Uzun job’ları idempotent/resumable yapın. Grace süresi yetmez ve süreç sert kapanırsa bile güvende olmak için uzun işleri tekrar çalıştırılabilir tasarlayın — her adım idempotent olsun, yarıda kalan job baştan veya kaldığı yerden güvenle dönsün.
Sonuç: Sıra önemli: önce LB’yi drain edin, sonra yeni istek alımını kesin, sonra mevcut işi bitirin, en son ölün. Go’da bunu server.Shutdown(ctx), Octane’de graceful reload + queue:work’ün doğal SIGTERM davranışı verir; platform tarafında grace süresini gerçek drain süresine hizalayın. Üstüne job’ları idempotent yaparsanız sert kill bile veriyi bozmaz. Octane’in kalıcı süreç modelinin bu kapanış davranışını neden değiştirdiğini hub’daki yazıda daha ayrıntılı anlattım.
İlgili Yazılar
Yorumlar
Yorum yapmak için GitHub hesabınızla giriş yapmanız yeterli. Yorumlar GitHub Discussions üzerinde saklanır.