Hizmetler Hosting & Sunucu Araçlar Blog Ara Kurumsal EnglishEN
Teklif Alın

Tek servisli bir uygulama için Docker Compose'a gerçekten ihtiyaç var mı?

Tek bir konteyner çalıştırmak için çoğunlukla docker run komutuna imaj adı, port eşlemesi, birkaç volume tanımı ve birkaç ortam değişkeni eklenir. Komut satırı hızla uzar, terminal geçmişinde kaybolur ve bir sunucudan diğerine aynen taşınması zorlaşır. Sunucu yeniden başladığında ya da kurulum başka bir makineye taşınırken bu uzun komutu doğru hatırlamak, bir script içine gömmek ya da elle yeniden yazmak gerekir. Docker Compose, tek servisli kurulumlarda bile bu sorunu ortadan kaldırır: konteynerin nasıl çalıştırılacağını anlatan tüm parametreler tek bir docker-compose.yml dosyasında toplanır.

Docker Compose nedir, docker run'dan farkı nedir?

Docker Compose, bir uygulamayı tek bir YAML dosyasıyla tanımlamayı ve yönetmeyi sağlayan bir araçtır; birden fazla konteyner için tasarlanmış olsa da tek servisli projelerde de aynı avantajları sunar. Modern docker compose (v2, Docker CLI'ye eklenti olarak gömülüdür) artık Compose Specification'ı kullanır ve üst seviye version: alanını gerektirmez; bu alan kullanımdan kaldırılmıştır ve dosyada bulunsa bile yok sayılır. Eski, bağımsız docker-compose (tire ile yazılan, Python tabanlı v1 sürümü) ise artık bakımı yapılmayan bir eski araçtır ve yeni kurulumlarda tercih edilmemelidir.

docker run ile karşılaştırıldığında Compose'un asıl farkı imperatif değil deklaratif olmasıdır: komutu adım adım yazmak yerine, konteynerin son halinin nasıl olması gerektiği YAML içinde tanımlanır. Bunun pratik sonuçları üçtür. Birincisi, dosya sürüm kontrolüne (Git) eklenebilir; bir port ya da ortam değişkeni değiştiğinde bu değişiklik commit geçmişinde net biçimde görülür. İkincisi, aynı dosya Docker kurulu herhangi bir sunucuda çalıştırıldığında aynı sonucu üretir; bu da kurulumu tekrarlanabilir kılar. Üçüncüsü, servisin tüm yaşam döngüsü tek bir dosya üzerinden birkaç kısa komutla yönetilir; docker run, docker stop, docker rm gibi ayrı komutları elle ve doğru sırada çalıştırmaya gerek kalmaz.

docker-compose.yml'in temel yapısı

Compose dosyası services: anahtarı altında bir veya daha fazla servis tanımlar. Tek servisli bir kurulum genellikle şu alanları içerir: servisin hangi imajdan (image) oluşturulacağı, dışarıya açılacak portlar, kalıcı veri için volume tanımları, ortam değişkenleri ve bir restart politikası. Aşağıda tipik bir örnek yer alır:

services:
  app:
    image: node:20-alpine
    restart: unless-stopped
    ports:
      - "3000:3000"
    volumes:
      - ./data:/app/data
    environment:
      - NODE_ENV=production

image alanı Docker Hub ya da başka bir registry'deki hazır imajı belirtir; kendi kaynak kodunuzdan bir imaj oluşturmak isterseniz image yerine build: . kullanılabilir. ports altındaki her satır HOST:CONTAINER biçimindedir: iki nokta üst üstenin solunda host makinedeki port, sağında ise konteynerin içinde uygulamanın dinlediği port yer alır. restart alanı konteynerin ne zaman otomatik olarak yeniden başlatılacağını belirler.

Restart değeriDavranış
noVarsayılan değerdir. Konteyner hiçbir koşulda otomatik olarak yeniden başlatılmaz.
on-failureKonteyner hata koduyla (0 dışında bir kodla) durursa yeniden başlatılır.
unless-stoppedElle durdurulmadığı sürece, Docker servisi yeniden başladığında (örneğin sunucu reboot sonrası) konteyner de otomatik olarak başlar.
alwaysElle durdurulmuş olsa dahi, Docker servisi her yeniden başladığında konteyner tekrar başlatılır.

Bind mount mu, named volume mu?

Volume tanımları da benzer bir HOST:CONTAINER mantığıyla yazılır, ama iki farklı türü karıştırmamak gerekir. ./data:/app/data gibi bir tanım bir bind mount'tur: host makinedeki göreli bir dizini doğrudan konteynerin içine bağlar, dosyalar host üzerinde normal dosya sistemi üzerinden doğrudan görünür ve düzenlenebilir. dbdata:/var/lib/postgresql/data gibi bir tanım ise bir named volume'dur; bu, Docker'ın kendi yönettiği ve host dosya sisteminde belirli bir yola bağlı olmayan bir depolama alanıdır. Named volume kullanılacaksa, bu volume'un adı dosyanın üst seviyesindeki volumes: bloğunda da ayrıca tanımlanmalıdır; aksi halde Compose hata verir.

Temel çalışma akışı: up, logs, down

Dosya docker-compose.yml adıyla kaydedildikten sonra, aynı dizinde birkaç komutla servisin tüm yaşam döngüsü yönetilir:

  • docker compose up -d — servisi arka planda (detached mode) başlatır; terminal penceresi kapatılsa bile konteyner çalışmaya devam eder.
  • docker compose ps — bu dosyaya ait servislerin çalışma durumunu listeler.
  • docker compose logs -f — servisin günlük çıktısını canlı olarak izlemeye devam eder (takip/follow modu).
  • docker compose down — servisi durdurur, oluşturduğu konteyner ve ağı kaldırır; named volume'lar varsayılan olarak silinmez.

Sık yapılan hatalar

Tek servisli bir Compose dosyası basit görünse de, aşağıdaki hatalar sık tekrarlanır ve genellikle servisin beklenmedik biçimde erişilemez olmasına ya da sunucu yeniden başladığında kaybolmasına yol açar.

  • Port sırasını karıştırmak: ports altındaki değer daima HOST:CONTAINER sırasındadır. Bu sıra ters yazıldığında Compose hata vermez, ama tarayıcıdan beklenen adrese bağlanılamaz; çünkü host üzerinde açılan port farklı bir numara olur.
  • Bind mount ile konteyner içindeki node_modules'ün üzerine yazmak: Proje dizininin tamamını bind mount olarak bağlamak, imaj derlenirken konteyner içinde kurulmuş olan bağımlılık klasörünü host'taki (bazen eksik ya da farklı platform için derlenmiş) haliyle örter ve uygulama modül bulunamadı hatasıyla başlamaz.
  • Restart politikasını atlamak: Alan hiç yazılmazsa varsayılan değer no'dur, yani konteyner sunucu yeniden başladığında ya da çöktüğünde otomatik olarak geri gelmez. Kalıcı çalışması gereken servislerde unless-stopped ya da always açıkça belirtilmelidir.
  • latest etiketini kullanmak: Sürüm belirtmeden yalnızca imaj adını yazmak (örtük olarak latest etiketine karşılık gelir) her pull işleminde farklı bir imaj içeriği çekilmesine yol açabilir. Bu da Compose dosyasının asıl amacı olan tekrarlanabilirliği ortadan kaldırır; imaj için sabit bir sürüm etiketi (örneğin node:20-alpine) kullanılmalıdır.

docker-compose.yml'i elle yazmak yerine oluşturmak

Yukarıdaki alanların hepsini doğru sırada, doğru girintiyle ve doğru ayraçlarla elle yazmak, özellikle YAML'e alışkın olmayanlar için hataya açıktır; fazladan bir boşluk ya da yanlış yerleştirilmiş bir tire dosyayı geçersiz kılabilir. Servis adı, imaj, restart politikası, port listesi, volume listesi ve ortam değişkenlerini bir forma girip anında geçerli bir docker-compose.yml çıktısı almak, özellikle tek servisli ve tekrar eden kurulumlar için pratik bir kısayoldur.

Oluşturulan dosyayı proje dizininize docker-compose.yml olarak kaydettikten sonra docker compose up -d ile başlatabilir, docker compose logs -f ile günlükleri izleyebilir ve gerektiğinde docker compose down ile durdurabilirsiniz.

WhatsApp