Blue-green deploy kusursuz çalıştı. Tek sorun, green ortamının farklı bir config'e sahip olmasıydı.

Kurulum:

  • Blue ortamı: üretimi çalıştırıyor
  • Green ortamı: boşta, deploy'a hazır
  • Green'e deploy et, test et, trafiği çevir

Ne ters gitti:

Haftalar önce blue'da bir feature flag çevrilmişti — doğrudan, admin arayüzünden. Green'e kimse dokunmadı. Bir sonraki release green'e deploy edilip trafik oraya geçince flag sessizce eski değerine döndü ve kullanıcılar haftalardır güvendikleri bir özelliği kaybetti. Hiçbir deploy başarısız olmadı, hiçbir alarm çalmadı; ortam yalnızca kendi bayat config'i hakkında doğruyu söylüyordu.

Denetleyince daha fazla drift bulduk:

  • Farklı veritabanı connection pool boyutları
  • Farklı log seviyeleri
  • Farklı timeout değerleri
  • Yalnızca blue'da rotate edilmiş API anahtarları

Çözüm — iki tür config, iki ayrı ev:

Naif çözüm listesi — “config'i Git'e koy” ve “harici bir config deposu kullan” — neyin nereye ait olduğunu ayırmadığınız sürece zıt yönleri gösterir.

Sürümlenen config Git'te yaşar ve release ile birlikte çıkar. Pool boyutları, timeout'lar, log seviyeleri, kaynak limitleri: bunlar bir release'in özellikleridir, dolayısıyla blue ve green'e birebir aynı uygulanan render edilmiş manifest'ler olarak repoda durmalıdır. Bir GitOps controller'ı — bizde Argo CD, Flux da aynı derecede iyi çalışır — canlı durumu Git ile sürekli karşılaştırır; böylece iki ortamdan birine yapılan bant dışı bir düzenleme cutover'da değil, dakikalar içinde drift olarak görünür. Bu, CI/CD pipeline tasarımında asgari standart saydığımız disiplinin ta kendisidir.

Çalışma zamanı toggle'ları tek bir paylaşımlı harici serviste yaşar. Feature flag'ler ortam başına hiç var olmamalıdır. Onları her iki rengin de okuduğu tek bir flag servisine (OpenFeature uyumlu bir sağlayıcı) taşıdık; böylece bir flag değişikliği o anda trafiği karşılayan ortam hangisiyse ona uygulanır. Flag durumunun tek bir evi vardır; blue ve green yalnızca tüketicidir.

Ve her cutover'dan önce bir kapı. Pipeline, iki ortamın render edilmiş config'ini karşılaştırır ve en ufak bir farkta trafiği çevirmeyi reddeder:

# refuse to cut over if blue and green disagree
diff \
  <(kubectl get cm app-config -n blue -o jsonpath='{.data}') \
  <(kubectl get cm app-config -n green -o jsonpath='{.data}') \
  || { echo "config drift detected - aborting cutover"; exit 1; }

Secret'lar da aynı muameleyi gördü: tek bir harici depoda rotate edilip bir operatör tarafından her iki ortama senkronlanıyor; asla elle “blue'da” rotate edilmiyor. Blue-green'in veritabanı tarafının kendi tuzakları var — bkz. blue-green veritabanı kâbusumuz.

Ders: Blue-green deploy'lar blue-green config yönetimi gerektirir. Boşta duran bir ortam varsayılan olarak drift eder; bunu yalnızca otomasyon fark eder.


← Çıkarılan Dersler'e dön

Bu tür olaylar önlenebilir. AWS Yönetilen Hizmetler ekibimiz müşteri ortamlarını yapay zekâ destekli izleme ve nöbetteki kıdemli mühendislerle 7/24 gözetir — böylece bu tür hikâyeler arşivde kalır.