deniz.in

Piyasalar

Hava durumu

Hava durumu yükleniyor

· kaynak dev.to (home feed)

Docker Compose'un Laravel dağıtımlarını bozan beş tuzağı ve çözümleri

Dev.to'daki bir rehber, Laravel'in Docker Compose'a taşındığında ortaya çıkan beş altyapı hatasını ele alıyor: uyuşmayan veritabanı host adlarından replikalar arasındaki migration yarışlarına kadar her biri için çözümüyle birlikte.

Docker Compose'un Laravel dağıtımlarını bozan beş tuzağı ve çözümleri

Docker Compose altında bir Laravel uygulaması çalıştırmak ilk bakışta basit görünür; ta ki bir dağıtımın, uygulama koduyla hiçbir ilgisi olmayan nedenlerle başarısız olmasına kadar. Aslen İspanyolca yayınlanmış bir dev.to yazısı, yazarın gerçek projelerde hata ayıklarken karşılaştığı beş altyapı hatasını, her birinin belirtisi, nedeni ve çözümüyle birlikte ele alıyor.

Veritabanı host adı service adıyla eşleşmeli

İlk hata, getaddrinfo failed veya Connection refused gibi bağlantı hataları olarak ortaya çıkar. Dev.to yazısına göre neden, Compose ağındaki container'ların birbirlerini service adıyla bulmasıdır: veritabanı servisi compose dosyasında postgres olarak adlandırılmışken uygulama ortamında DB_HOST=db ayarlanmışsa, çözülecek bir şey yoktur. Bu genellikle servisler yeniden adlandırıldığında ya da başka bir projeden .env dosyası kopyalandığında yaşanır. Çözüm, DB_HOST değerini service adıyla birebir aynı yapmak. İlgili bir tuzak da container içinde localhost kullanmaktır; burada localhost, host'u ya da kardeş servisleri değil, o container'ın kendisini işaret eder.

Var olmayan bir role'ü yoklayan healthcheck'ler

Buradaki belirti, her bağlı servisin de hiç başlamadığı, FATAL: role "postgres" does not exist loglarını veren ve unhealthy durumunda takılı kalan bir Postgres container'ıdır. Healthcheck, POSTGRES_USER başka bir değere ayarlanmış olmasına rağmen pg_isready komutunu varsayılan postgres kullanıcısına karşı çağırmakta, yani hiç oluşturulmamış bir role'ü test etmektedir. Dev.to yazarı, healthcheck'in servisin kullandığı aynı ortam değişkenlerini okumasını ve dolar işaretlerinin $$ olarak kaçışlanmasını öneriyor; böylece bunları genişleten Compose değil, container'ın kendisi olur. Bunu depends_on ve condition: service_healthy ile birleştirmek, uygulamanın container'ın yalnızca var olmasını değil, veritabanının gerçekten bağlantı kabul etmesini beklemesini sağlar.

Scheduler ve eksik cache tablosu

Scheduler cache veya cache_locks tablolarıyla ilgili hatalar bildirdiğinde — özellikle withoutOverlapping() veya onOneServer() kullanan görevlerde — asıl sorun yapılandırmadır. CACHE_STORE=database ile Laravel, cache'ini ve kilitlerini veritabanı tablolarında tutar; taze ya da migration uygulanmamış bir veritabanı, scheduler'ın kilit alamamasına yol açar. Yazıdaki çözüm, cache tablosu migration'ını oluşturup çalıştırmaktır: Laravel 11 ve sonrasında php artisan make:cache-table (eski sürümlerde cache:table) kullanılır ve scheduler php artisan schedule:work ile ayrı bir süreç olarak çalıştırılır.

Her container'a tek süreç

Geliştirme kurulumlarında genellikle web sunucusu, queue worker ve scheduler tek bir terminalde birlikte başlatılır. Bu düzeni üretime taşımak tek bir container'a birkaç süreç yerleştirir ve Docker yalnızca ana süreci denetler: queue worker ölürse fark eden olmaz, worker'lar bağımsız ölçeklenemez ve yeniden başlatma davranışı öngörülemez hale gelir. Önerilen yapı tek bir image kullanır ama onu farklı komutlarla servislere böler — uygulama için php-fpm, queue için retry ve timeout bayraklarıyla php artisan queue:work, zamanlama için php artisan schedule:work. Dev.to yazısı kazancı şöyle özetliyor: bağımsız yeniden başlatmalar, worker'lar için ayrı ölçekleme, daha temiz loglar ve Docker tarafından yönetilen durdurma sinyalleri.

Migration'lar boot dizisine değil dağıtıma aittir

php artisan migrate --force komutunu container entrypoint'ine koymak tek instance ile çalışır ama birkaç instance ile bozulur: replikalar birbiriyle yarışır ve aralıklı migration hataları, veritabanı kilitleri veya yarım oluşturulmuş tablolar ortaya çıkar. Migration'lar bunun yerine dağıtım başına bir kez çalışmalı — ya yeni container'lar başlamadan önce CI/CD pipeline'ında bir adım olarak, ya da restart: "no" ile sağlıklı bir veritabanına bağımlı tek seferlik bir Compose servisi olarak. Uygulama, queue ve scheduler servisleri ise yalnızca o migration adımı başarılı olduktan sonra başlamalıdır.

Bir sonraki dağıtım için kontrol listesi

Yazı kısa bir kontrol listesiyle kapanıyor: DB_HOST service adıyla eşleşmeli ve asla localhost olmamalı; veritabanı healthcheck'i servisin gerçek kimlik bilgilerini kullanmalı; depends_on, service_healthy beklemeli; cache store veritabanıysa cache tablosu mevcut olmalı; web, queue ve scheduler ayrı container'larda çalışmalı; migration'lar dağıtım başına bir kez çalışmalı; image'lar latest yerine sabit sürümlere sabitlenmeli.

Neden önemli

Listedeki her hatanın tek bir ortak kök nedeni var, yazarın ifadesiyle: altyapının yerel bir geliştirme makinesi gibi davranacağını varsaymak. Compose'un belirleyici kuralları vardır — isim tabanlı çözümleme, sıralı başlatma, container başına tek denetlenen süreç — ve bu hataların her biri bunlardan birinin ihlalidir. Bu ders Laravel'ın da ötesine geçer: aynı tür hata Compose'a taşınan herhangi bir PHP, Python veya Node uygulamasını da ısırır ve bu deseni tanımak, kafa karıştırıcı bir üretim kesintisini kısa bir yapılandırma düzeltmesine dönüştürür.

  • #laravel
  • #docker
  • #docker-compose
  • #php
  • #devops
  • #deployment

İlgili yazılar