Docker & DevOps

    Trivy ile Konteyner İmajı Güvenlik Taraması

    Konteyner imajlarındaki güvenlik açıklarını Trivy ile bulup CI hattında kapıya bağlama rehberi.

    9 dk okuma Güncellendi: 25 Ağustos 2026

    Uygulaman sorunsuz çalışıyor olabilir; bu, imajının güvenli olduğu anlamına gelmez. Aylar önce FROM node:20 yazıp derlediğin bir imaj, o günden bu yana açıklanmış onlarca kütüphane zafiyetini içinde taşıyor olabilir. Trivy ile konteyner imajı güvenlik taraması, tam olarak bu görünmez borcu ölçülebilir hâle getirir: imajın içindeki işletim sistemi paketlerini ve uygulama bağımlılıklarını tek tek çıkarır, bilinen CVE veritabanıyla karşılaştırır ve hangi paketin hangi sürüme yükseltilmesi gerektiğini söyler.

    Bu rehberde Trivy'nin neyi nasıl taradığını, kurulumun üç farklı yolunu, çıktıyı doğru okumayı, gürültüyü azaltıp gerçekten önemli bulgulara odaklanmayı, .trivyignore ile kabul edilen riskleri belgelemeyi ve taramayı bir CI/CD kapısına dönüştürmeyi anlatacağım. Kapanışta da "tarama yaptım ama bulguları kapatamıyorum" çıkmazından çıkış stratejisini paylaşacağım. İmaj yapısına ve katman mantığına aşina değilsen Dockerfile en iyi pratikler yazısı iyi bir ön okuma olur.

    Trivy Ne Yapar, Neyi Tarar#

    Trivy açık kaynaklı bir güvenlik tarayıcısıdır ve tek bir ikili dosyadan ibarettir; ajan kurmaz, sunucuya servis bırakmaz. Bir imajı taradığında yaptığı iş kabaca üç adımdır: imajın katmanlarını açar, içindeki paket envanterini çıkarır (dpkg, rpm, apk veritabanları ile package-lock.json, go.sum, composer.lock gibi kilit dosyaları), sonra bu envanteri indirdiği zafiyet veritabanıyla eşleştirir.

    Kapsamı yalnızca imajlarla sınırlı değil. Tarayıcı türlerini --scanners bayrağıyla seçersin:

    TarayıcıNe bulurTipik kullanım
    vulnPaket ve bağımlılık zafiyetleri (CVE)İmaj ve kaynak kod taraması
    secretKoda kaçmış API anahtarı, parola, özel anahtarDepo ve imaj taraması
    misconfigHatalı Dockerfile / Kubernetes / Terraform ayarıAltyapı kodu incelemesi
    licenseUyumsuz veya riskli lisanslarKurumsal uyum kontrolleri

    Hedef türleri de birden fazladır: trivy image bir konteyner imajını, trivy fs bir dizini, trivy repo bir Git deposunu, trivy config altyapı kodunu tarar. Sırların koda kaçması konusunun neden ayrı bir başlık olduğunu merak ediyorsan .env dosyası ifşası yazısı olayın maliyetini iyi anlatıyor.

    Kurulum: Üç Yol#

    Ne yaptığına göre üçünden birini seçersin.

    1. Docker ile çalıştırmak (hiçbir şey kurmadan denemek için). En hızlısı budur:

    docker run --rm \
      -v /var/run/docker.sock:/var/run/docker.sock \
      -v "$HOME/.cache/trivy:/root/.cache/trivy" \
      aquasec/trivy:latest image nginx:alpine
    

    Buradaki ikinci -v satırı önemlidir: zafiyet veritabanı birkaç yüz megabayttır ve önbelleği kalıcı bir dizine bağlamazsan her taramada baştan indirilir. Docker soketini bağlamak ise yerel imajları görebilmesi içindir; yalnızca uzak registry'deki imajları tarayacaksan soketi bağlamana gerek yok.

    2. Paket deposundan kurmak (sunucularda kalıcı kullanım için).

    # Debian / Ubuntu
    sudo apt-get install -y wget gnupg
    wget -qO - https://aquasecurity.github.io/trivy-repo/deb/public.key | sudo gpg --dearmor -o /usr/share/keyrings/trivy.gpg
    echo "deb [signed-by=/usr/share/keyrings/trivy.gpg] https://aquasecurity.github.io/trivy-repo/deb generic main" \
      | sudo tee /etc/apt/sources.list.d/trivy.list
    sudo apt-get update && sudo apt-get install -y trivy
    
    trivy version
    

    AlmaLinux/Rocky tarafında dnf deposu ekleyip sudo dnf install -y trivy ile kurarsın; paket yönetimi mantığını tazelemek istersen AlmaLinux ve Rocky'de dnf paket yönetimi yazısına bakabilirsin.

    3. Tek ikili dosya olarak indirmek (CI koşucuları için). Resmî kurulum betiği ikiliyi istediğin dizine bırakır ve hiçbir sistem paketi kirletmez; kısa ömürlü CI konteynerlerinde en pratik yöntemdir.

    Kurulumdan sonra veritabanını önden indirip önbelleğe almak, ilk taramanın zaman aşımına düşmesini engeller:

    trivy image --download-db-only
    

    İlk Tarama ve Çıktıyı Okumak#

    Şimdi gerçek bir tarama yapalım:

    trivy image firmaniz/api:1.4
    

    Çıktı, her paket kaynağı için ayrı bir tablo verir. Tipik bir satır şöyle okunur:

    firmaniz/api:1.4 (debian 12.5)
    ==============================
    Total: 47 (UNKNOWN: 0, LOW: 21, MEDIUM: 19, HIGH: 6, CRITICAL: 1)
    
    ┌──────────────┬────────────────┬──────────┬────────┬───────────────────┬───────────────┐
    │   Library    │ Vulnerability  │ Severity │ Status │ Installed Version │ Fixed Version │
    ├──────────────┼────────────────┼──────────┼────────┼───────────────────┼───────────────┤
    │ libssl3      │ CVE-YYYY-NNNNN │ CRITICAL │ fixed  │ 3.0.11-1          │ 3.0.13-1      │
    │ libc-bin     │ CVE-YYYY-NNNNN │ HIGH     │ affected │ 2.36-9          │               │
    └──────────────┴────────────────┴──────────┴────────┴───────────────────┴───────────────┘
    

    Bu tabloda dikkat etmen gereken iki sütun var. Status sütunu fixed ise üstyapı bir düzeltme yayınlamış demektir; affected ya da will_not_fix ise şu an yapabileceğin bir şey yoktur. Fixed Version boşsa yükseltecek bir sürüm bile yok demektir. Bu ayrım kritik: 47 bulgunun 30'u düzeltmesiz olabilir ve o 30'u kovalamak zaman kaybıdır.

    Gürültüyü kesmek için ilk günden kullanacağın iki bayrak şunlar:

    # Yalnızca düzeltmesi olan HIGH ve CRITICAL bulgular
    trivy image --severity HIGH,CRITICAL --ignore-unfixed firmaniz/api:1.4
    
    # JSON çıktı (rapor arşivi veya başka bir araca beslemek için)
    trivy image --format json --output rapor.json firmaniz/api:1.4
    
    # Yalnızca uygulama bağımlılıkları (işletim sistemi paketlerini atla)
    trivy image --pkg-types library firmaniz/api:1.4
    

    --ignore-unfixed bayrağı, pratikte 200 satırlık bir raporu 12 satıra indirir ve elindeki listeyi gerçekten "yapılabilir işler" listesine dönüştürür.

    Severity Seviyeleri ve CI Kapısı Kurmak#

    Trivy varsayılan olarak bulgu bulsa bile 0 çıkış kodu döner; yani hiçbir şey yapmazsan CI hattın yeşil kalır. Kapıyı sen kurarsın:

    # CRITICAL bulgu varsa hattı kırmızıya çevir
    trivy image \
      --severity CRITICAL \
      --ignore-unfixed \
      --exit-code 1 \
      --no-progress \
      firmaniz/api:1.4
    

    Uygulamada başarılı bulduğum kademeli yaklaşım şudur:

    AşamaPolitikaAmaç
    1. haftaTara, raporla, kırma (--exit-code 0)Mevcut borcu ölçmek
    2-4. haftaYalnızca CRITICAL kırarEkibi alıştırmak
    SonrasıHIGH,CRITICAL kırarKalıcı standart
    Yeni projelerİlk günden HIGH,CRITICALBorç birikmesin

    İlk gün HIGH,CRITICAL kapısını açarsan hattaki her derleme kırmızı olur, ekip birkaç gün içinde kontrolü tamamen atlamanın yolunu bulur ve tarama fiilen ölür. Kademeli geçiş kulağa gevşek gelse de kalıcı olan yöntem budur.

    GitHub Actions tarafında minimal bir iş tanımı şöyle görünür:

    name: imaj-guvenlik
    on: [push]
    
    jobs:
      tara:
        runs-on: ubuntu-latest
        steps:
          - uses: actions/checkout@v4
    
          - name: İmajı derle
            run: docker build -t firmaniz/api:${{ github.sha }} .
    
          - name: Trivy taraması
            uses: aquasecurity/trivy-action@master
            with:
              image-ref: firmaniz/api:${{ github.sha }}
              severity: HIGH,CRITICAL
              ignore-unfixed: true
              exit-code: "1"
              format: table
    

    GitLab CI kullanıyorsan aynı işi trivy image --exit-code 1 ... satırını bir script adımına koyarak yaparsın; artefakt olarak JSON raporu saklamak sonradan karşılaştırma yapmayı kolaylaştırır.

    Kabul Edilen Riskleri Belgelemek: .trivyignore#

    Bazı bulgular gerçekten seni ilgilendirmez. Örneğin imajda bulunan ama hiç çalıştırılmayan bir kütüphanedeki zafiyet, ya da düzeltmesi olmayan ve üstyapının "etkilenmiyoruz" dediği bir kayıt. Bunları görmezden gelmek yerine belgelemek gerekir; .trivyignore dosyası tam olarak bunun için var:

    # .trivyignore — proje kökünde durur
    # Her satır bir CVE kimliği; # ile başlayan satırlar açıklamadır.
    
    # Yalnızca derleme aşamasında kullanılıyor, son imajda çalışmıyor.
    # Gözden geçirme tarihi: 2026-10-01
    CVE-YYYY-11111
    
    # Üstyapı düzeltme yayınlamayacağını duyurdu, etkilenen kod yolu bizde kapalı.
    CVE-YYYY-22222
    

    Buradaki en önemli disiplin, her satıra neden ve ne zaman tekrar bakılacağı bilgisini yazmaktır. Açıklamasız bir ignore satırı, altı ay sonra kimsenin dokunmaya cesaret edemediği bir kara kutuya dönüşür. Dosyayı depoya koyarsan Trivy otomatik olarak bulur; farklı bir konum için --ignorefile yol/dosya kullanırsın.

    Bulguları Gerçekten Kapatma Stratejisi#

    Tarama kolay, düzeltme zordur. Pratikte işe yarayan sıralama şu:

    1. Temel imajı güncelle. Bulguların çoğunluğu genelde uygulama kodundan değil temel imajdan gelir. FROM debian:12 yerine güncel bir debian:12-slim etiketine geçmek ya da sadece imajı yeniden derlemek onlarca CVE'yi tek hamlede kapatır.
    2. Daha küçük bir temel imaj seç. İçinde paket yoksa zafiyet de yoktur. alpine, -slim ve distroless varyantları raporunu genelde onda birine indirir. Bu, imaj boyutunu da düşürür; Docker imaj boyutu optimizasyonu yazısındaki teknikler doğrudan güvenlik kazancı olarak da geri döner.
    3. Bağımlılık kilit dosyalarını güncelle. npm audit fix, composer update, pip-compile --upgrade gibi araçlarla uygulama katmanındaki kütüphaneleri tazele.
    4. Çok aşamalı derleme kullan. Derleyiciler, başlık dosyaları ve test bağımlılıkları son imaja hiç girmezse taranacak yüzey de daralır.
    5. Düzeltmesizleri ayrı listede takip et. Kapatılamayanları .trivyignore içine gerekçesiyle koy ve aylık gözden geçir.

    Bir noktayı net söyleyeyim: imaj taraması bir çevre güvenliği önlemi değildir. Sıfır CVE'li bir imaj bile yanlış yapılandırılmış bir uygulamayla sömürülebilir. Tarama, uygulama katmanındaki koruma araçlarının yerine değil yanına konur; dışa açık servislerde WAF ve DDoS koruma katmanları farklı bir tehdit sınıfını karşılar.

    Sık Yapılan Hatalar ve Tuzaklar#

    1. latest etiketini taramak. firmaniz/api:latest bugün taradığın imajla yarın çalışacak imajın aynı olduğunu garanti etmez. Her zaman değişmez bir etiketi veya doğrudan digest'i (imaj@sha256:...) tara.
    2. Önbelleği bağlamamak. Docker ile çalıştırırken ~/.cache/trivy dizinini bağlamazsan her koşuda yüzlerce megabayt veritabanı indirilir; CI süren uzar ve indirme sınırlarına takılırsın.
    3. Taramayı derlemeden önce yapmak. Kaynak kodu taramak (trivy fs .) faydalıdır ama son imajın içinde ne olduğunu göstermez. Kapıyı derlenmiş imaj üzerinde kur.
    4. Tüm severity seviyelerini kapıya bağlamak. LOW ve UNKNOWN bulguları hattı kırmaya başladığında ekip kontrolü baypas etmenin yolunu arar. Kapıyı yalnızca HIGH,CRITICAL ve --ignore-unfixed ile kur.
    5. Raporu bir kere alıp rafa kaldırmak. Zafiyet veritabanı her gün güncellenir; bugün temiz olan imaj iki hafta sonra kritik bulgu verebilir. Üretimdeki imajları haftalık olarak yeniden tarayan zamanlanmış bir görev kur.
    6. Sır taramasını atlamak. --scanners secret çoğu ekibin hiç bakmadığı ama en yüksek etkili bulguyu çıkaran taramadır; imaj katmanına kaçmış bir .env ya da özel anahtar, silinmiş olsa bile eski katmanda durmaya devam eder.

    Sıkça Sorulan Sorular#

    Trivy ücretsiz mi#

    Evet, Trivy açık kaynaklıdır ve komut satırı aracı ücretsiz kullanılır; ticari kullanım için de bir lisans bedeli yoktur. Zafiyet veritabanı da açık kaynak kaynaklardan derlenir ve ücretsiz indirilir. Aqua Security ayrıca ticari bir platform sunar, ancak bu rehberdeki her şey ücretsiz sürümle yapılabilir.

    Trivy taraması ne kadar sürer#

    İlk çalıştırmada zafiyet veritabanının indirilmesi birkaç dakika alabilir; sonraki taramalar önbellekten okuduğu için çok daha hızlıdır. Orta boy bir imaj (200-400 MB) genelde 10-30 saniye içinde taranır. Süre imajın büyüklüğüne ve içindeki paket sayısına bağlıdır; ince temel imajlar hem daha hızlı taranır hem de daha az bulgu üretir.

    Trivy imajı çalıştırmadan mı tarıyor#

    Evet. Trivy imajın katmanlarını statik olarak açar ve paket envanterini dosya sisteminden okur; konteyneri hiç başlatmaz. Bu yüzden tarama güvenlidir ve şüpheli bir imajı da risk almadan inceleyebilirsin. Kaydedilmiş bir tar arşivini --input imaj.tar ile tarayarak Docker daemon'a hiç ihtiyaç duymadan da çalıştırabilirsin.

    CVE bulundu ama düzeltme sürümü yok, ne yapmalıyım#

    Bu durumda Fixed Version sütunu boş kalır ve şu an yükseltebileceğin bir sürüm yoktur. Yapılacaklar sırayla şunlardır: paketin imajda gerçekten gerekli olup olmadığını sorgula ve gereksizse kaldır, zafiyetin sömürülebilmesi için gereken koşulun sende oluşup oluşmadığını değerlendir, kalıcı olarak kabul ediyorsan .trivyignore dosyasına gerekçe ve gözden geçirme tarihiyle ekle.

    Trivy ile Docker Scout arasındaki fark nedir#

    İkisi de imaj zafiyet taraması yapar; Trivy tek ikili dosya olarak her ortamda çalışır, açık kaynaktır ve imaj dışında dosya sistemi, Git deposu ve altyapı kodu taraması da yapabilir. Docker Scout ise Docker ekosistemiyle daha sıkı bütünleşiktir ve bazı yetenekleri abonelik gerektirir. CI hattında sağlayıcıdan bağımsız bir çözüm arıyorsan Trivy daha esnektir.

    Taramayı ne sıklıkla çalıştırmalıyım#

    En az iki yerde: her imaj derlemesinde CI hattında, bir de üretimde çalışan imajlar için haftalık zamanlanmış bir görevle. İkinci kısım genelde atlanır ama en değerlisidir, çünkü imajın kendisi değişmese bile hakkında yeni CVE yayınlanabilir. Haftalık taramanın çıktısını bir kanala düşürmek, güvenlik borcunun sessizce büyümesini engeller.

    Kapanış#

    Trivy'yi kurmak beş dakika, ondan gerçekten fayda sağlamak ise birkaç alışkanlık meselesi. Aklında kalması gerekenler şunlar: taramayı --ignore-unfixed ile anlamlı bir listeye indir, kapıyı kademeli aç ve yalnızca HIGH,CRITICAL üzerinden kur, kabul ettiğin riskleri .trivyignore içinde gerekçeli olarak belgele ve üretim imajlarını haftalık olarak yeniden tara. Bulguların büyük çoğunluğunun temel imajdan geldiğini unutma; çoğu zaman en etkili düzeltme, imajı küçültmek ve tazelemektir.

    Bu döngüyü kurmak veya bakımını üstlenmek için yardım istersen Clou.TR tarafında birkaç seçenek var. Kendi CI ve konteyner altyapını kurmak için tam root erişimli VDS ve bulut sunucu paketlerimize bakabilir, güncelleme ve izleme yükünü devretmek istersen sunucu yönetimi hizmetimizi tercih edebilir, dışa açık uygulamaların önüne bir koruma katmanı koymak istersen WAF çözümümüzü inceleyebilirsin.

    TrivyGüvenlikDocker

    Uygulamaya geçmeye hazır mısınız?

    NVMe SSD, ücretsiz SSL ve %99.9 uptime garantisiyle Clou.TR hosting ve sunucu çözümleriyle projenizi hayata geçirin.