Docker kapsayıcısının günlükleri düzgün bir şekilde nasıl temizlenir?


211

docker logs [container-name]Belirli bir kabın günlüklerini görmek için kullanıyorum .

Bu günlükleri temizlemenin zarif bir yolu var mı?


15
Bir sidenote üzerinde, günlüklerin boyutunu alabilirsinizsudo sh -c "du -ch /var/lib/docker/containers/*/*-json.log"
Daniel F

Yanıtlar:


254

Gönderen bu soruya çalıştırabileceğiniz bir tek satırlık var:

echo "" > $(docker inspect --format='{{.LogPath}}' <container_name_or_id>)

veya benzer bir kesilme komutu var:

truncate -s 0 $(docker inspect --format='{{.LogPath}}' <container_name_or_id>)

Docker'ın dosyalarını doğrudan değiştirdikleri için bu ikisinin de büyük bir hayranı değilim. Harici günlük silme işlemi, docker dosyaya json biçimli veriler yazarken kısmi bir satırla sonuçlanabilir ve docker logsklipten herhangi bir günlük okuma yeteneğini bozabilir.

Bunun yerine, Docker'ın günlükleri sizin için otomatik olarak döndürmesini sağlayabilirsiniz. Varsayılan JSON günlük sürücüsünü kullanıyorsanız, dockerd ek bayraklarıyla yapılır :

dockerd ... --log-opt max-size=10m --log-opt max-file=3

Bunu başlangıç ​​komut dosyalarınızı değiştirmek yerine daemon.json dosyanızın bir parçası olarak da ayarlayabilirsiniz :

{
  "log-driver": "json-file",
  "log-opts": {"max-size": "10m", "max-file": "3"}
}

Bu seçeneklerin kök erişimi ile yapılandırılması gerekir. systemctl reload dockerAyarları uygulamak için bu dosyayı değiştirdikten sonra bir çalıştırdığınızdan emin olun . Bu ayar, yeni oluşturulan kapsayıcılar için varsayılan ayar olacaktır. Yeni günlük sınırlarını almak için mevcut kapsayıcıların silinip yeniden oluşturulması gerektiğini unutmayın.


Bu varsayılan değerleri geçersiz kılmak için tek tek kapsayıcılara benzer günlük seçenekleri geçirilerek tek tek kapsayıcılara daha fazla veya daha az günlük kaydetmenize olanak tanır. Bundan docker runşöyle görünür:

docker run --log-driver json-file --log-opt max-size=10m --log-opt max-file=3 ...

veya bir oluşturma dosyasında:

version: '3.7'
services:
  app:
    image: ...
    logging:
      options:
        max-size: "10m"
        max-file: "3"

Ek alan tasarrufu için json günlük sürücüsünden "yerel" günlük sürücüsüne geçiş yapabilirsiniz. Aynı maksimum boyut ve maksimum dosya seçeneklerini alır, ancak json'da depolamak yerine daha hızlı ve daha küçük bir ikili sözdizimi kullanır. Bu, aynı boyutlu dosyada daha fazla günlük depolamanızı sağlar. Bunun daemon.json girişi şuna benzer:

{
  "log-driver": "local",
  "log-opts": {"max-size": "10m", "max-file": "3"}
}

Yerel sürücünün dezavantajı, json günlüklerine doğrudan erişime bağlı olan harici günlük ayrıştırıcıları / ileticiler artık çalışmaz. Elastik'e göndermek için dosya atışı gibi bir araç veya Splunk'ın evrensel ileticisini kullanırsanız, "yerel" sürücüden kaçınırım.

İpuçları ve Püf Noktaları sunumumda biraz daha var .


6
Ben yaptım service docker restart kendi başına iş vermedi ki. Ayrıca, yürürlüğe girmeden önce yeni konteynerler oluşturmak zorunda kaldı. yani sadece eski kapları getirmek yeni günlüğü uygulamadı
Robbo_UK

Docker 1.13.1 kullanıyorum ve 'docker inspect --format =' {{. LogPath}} '<container id>' boş bir dize ("") döndürüyor .... ama yine de çıktı alıyorum ' liman işçisi <kapsayıcı kimliği> '?!? Bu nereden geliyor ve nasıl temizlerim ??
JD Allen

@JDAllen 1.13.1 desteği çok uzun. Denetim çıktılarını görmek için eski bir sistemim yok.
BMitch

Daha iyi olur echo -n > .... Her neyse, günlüklerim üzerinde daha fazla kontrole sahip olmak istiyorum. Örneğin, docker-compose yeniden başlattıktan sonra , korunmuş günlüklerle bir şeyler yapmak için mekanizmaya sahip olmak isterim.
NarūnasK

2
Docker'ı durdurabiliyorsanız, konteynerinizi durdurabilirsiniz. İkincisini yapabilirseniz, kapsayıcıyı günlük seçenekleriyle yeniden oluşturmak benim tavsiyem olacaktır. Yeni kapsayıcıda eski günlükler yoktur ve yeni günlükler otomatik olarak yuvarlanarak hem kısa vadeli hem de uzun vadeli sorunu aynı anda çözecektir.
BMitch

229

kullanın:

truncate -s 0 /var/lib/docker/containers/*/*-json.log

Sudo'ya ihtiyacınız olabilir

sudo sh -c "truncate -s 0 /var/lib/docker/containers/*/*-json.log"

ref. Jeff S. Docker konteyneri için günlükleri düzgün bir şekilde nasıl temizleyebilirim?

Başvuru: Bir dosyayı kullanılırken kesme (Linux)


4
truncate: yazmak için '/var/lib/docker/containers/*/*-json.log' açılamıyor: Böyle bir dosya veya dizin yok
BTR Naidu

2
@BTRNaidu root / sudo olarak çalıştırmalısınız, içeriği containersbaşka türlü kullanılamıyor.
spydon

25
sudo sh -c "truncate -s 0 /var/lib/docker/containers/*/*-json.log"- benim için çalıştı
Jeff S.

7
Yukarıdaki iki profesyoneli görmezden gelin. Emin değilseniz, "ls /var/lib/docker/containers/*/*-json.log" ile ne kesildiğini kontrol edebilirsiniz.
duketwo

1
günlük error from daemon in stream: Error grabbing logs: invalid character '\x00' looking for beginning of value
dosyasını

42
sudo sh -c "truncate -s 0 /var/lib/docker/containers/*/*-json.log"

4
Günlüklerin boyutunu almak için sudo sh -c "du -ch /var/lib/docker/containers/*/*-json.log", yalnızca günlüklerin toplamını elde etmek içinsudo sh -c "du -ch /var/lib/docker/containers/*/*-json.log | grep total"
Daniel F

Döndürülen günlük dosyalarını bilmeyen ve silemeyen dockerd / auf'larla ilgili herhangi bir sorun var mı?
ThorSummoner

Bu komut benim için çalıştı, ancak bu SO'daki diğer komutlar işe yaramadı. Önemli olursa, CentOS 7'de Docker sürüm 18'i çalıştırıyorum
Tundra Fizz

42

Windows ve Mac için Docker'da ve muhtemelen diğerlerinde de kuyruk seçeneğini kullanmak mümkündür. Örneğin:

docker logs -f --tail 100

Bu şekilde, yalnızca son 100 satır gösterilir ve ilk önce 1 milyon satır arasında ilerlemeniz gerekmez ...

(Ve bu nedenle, günlüğü silmek muhtemelen gereksizdir)


14
Fikir, günlük dosyalarını temizlemek ve günlük dosyalarının son n satırını yazdırmamaktır
Youssouf Maiga

27

Günlükleri periyodik olarak temizlemek için logrotate ayarlayabilirsiniz.

/Etc/logrotate.d/docker-logs dosyasındaki örnek dosya

/var/lib/docker/containers/*/*.log {
 rotate 7
 daily
 compress
 size=50M
 missingok
 delaycompress
 copytruncate
}

ve bunu nasıl kullanırım? docker run? ile varsayılan olarak kullanılır dosya /etc/logrotate.d/docker-logsmevcut değil, ben oluşturmak zorunda?
Carlos.V

Logrotate yardımcı programını çağırmanız gerekir (logrotate <config-file>) ve yapılandırmanızı okuyacak ve temizlemeyi çalıştıracaktır. Örneğin bir cron işi olarak da ayarlayabilirsiniz.
AlexPnt

Bu sorun, docker ne yapıyor ile düzgün senkronize olmayabilir olmasıdır. Liman işçisini kullanmak muhtemelen daha akıllıca olacaktır. ( "log-opts"BMitch tarafından gösterildiği gibi)
Alexis Wilke

12

Docker4Mac, 2018 çözümü:

LOGPATH=$(docker inspect --format='{{.LogPath}}' <container_name_or_id>)
docker run -it --rm --privileged --pid=host alpine:latest nsenter -t 1 -m -u -n -i -- truncate -s0 $LOGPATH

İlk satır, kabul edilen yanıta benzer şekilde günlük dosyası yolunu alır.

İkinci satır, Docker4Mac altındaki tüm docker kapsayıcıları için ana bilgisayar olarak sunucuların bulunduğu VM'de nsenterkomutları çalıştırmanıza izin veren kullanır xhyve. Çalıştırdığımız komut, truncate -s0 $LOGPATHMac dışı yanıtlardan tanıdık geliyor .

Kullanıyorsanız docker-compose, ilk satır:

local LOGPATH=$(docker inspect --format='{{.LogPath}}' $(docker-compose ps -q <service>))

ve dosyanızdaki <service>hizmet adıdır docker-compose.yml.

Sayesinde https://github.com/justincormack/nsenter1 için nsenterhile.


4
Ve tüm kapların günlüklerini docker run -it --rm --privileged --pid=host alpine:latest nsenter -t 1 -m -u -n -i -- sh -c 'truncate -s0 /var/lib/docker/containers/*/*-json.log'
kısaltmak için

11

Bunu doğrudan bir Docker komutu ile yapamazsınız.

Günlüğün boyutunu sınırlayabilir veya bir kapsayıcıyla ilgili günlükleri silmek için bir komut dosyası kullanabilirsiniz. Senaryo örnekleri burada bulabilirsiniz (alttan okunur): Özellik: Günlük geçmişini temizleme yeteneği # 1083

Check out günlüğü bölümüne bazı günlük sürücüleri için (örneğin günlük rotasyon ve günlük boyutu sınırı gibi) seçenekleri belirtebilirsiniz liman işçisi-oluşturma dosya referansı arasında.


7

Bir olarak kök kullanıcı aşağıdakileri çalıştırmayı:

>  /var/lib/docker/containers/*/*-json.log

veya

cat /dev/null > /var/lib/docker/containers/*/*-json.log

veya

echo "" > /var/lib/docker/containers/*/*-json.log

6

Ubuntu sunucularımda sudo bile alırdım Cannot open ‘/var/lib/docker/containers/*/*-json.log’ for writing: No such file or directory

Ancak liman işçisini taramak, cevapları incelemek ve kesmek

sudo truncate -s 0 `docker inspect --format='{{.LogPath}}' <container>`

2

Bunu (yukarıdaki çözümlerden) tercih ederim:

truncate -s 0 /var/lib/docker/containers/*/*-json.log

Ancak bu yol beklendiği gibi çalışmadığı birkaç sistem (örneğin Ubuntu 18.x Bionic) çalıştırıyorum. Docker Snap üzerinden yüklenir, bu nedenle kaplara giden yol daha çok benzer:

truncate -s 0 /var/snap/docker/common/var-lib-docker/containers/*/*-json.log

1

Log-opts parametrelerini docker runkomut satırında şu şekilde de sağlayabilirsiniz :

docker run --log-opt max-size=10m --log-opt max-file=5 my-app:latest

veya bunun gibi bir docker-compose.yml dosyasında

my-app:
image: my-app:latest
logging:
    driver: "json-file"
    options:
        max-file: "5"
        max-size: 10m

Kredi: https://medium.com/@Quigley_Ja/rotating-docker-logs-keeping-your-overlay-folder-small-40cfa2155412 (James Quigley)


Parametre değerleri , genel daemon.json dosyası için burada gösterildiği gibi tırnak içine alınmalıdır (yani sırasıyla) "5"ve ancak bir docker-compose.yml için aynıdır. Her iki durumda da, yalnızca yeni oluşturulan kapsayıcıları etkiler. "10m"
Adrian W

@AdrianW: docker-compose.yml'in tırnak içine alınması gerekmez. Bunlar tamamen farklı dosya formatlarıdır. Ve evet, haklısın: "docker run" komutları ve docker-compose parametreleri sadece yeni oluşturulan kapsayıcıları etkiliyor - buradaki yanıtın aksine, yalnızca yeniden başlatılan dockerd artalan süreçlerini etkileyen ve yalnızca root erişimi ile kullanılabilen cevapların aksine. Cevabım, tüm dockerd işlemini yeniden başlatmaktan çok daha basit ve güncellenmiş bir yol göstermesi gerekiyor.
Dag Baardsen

Tırnaklar olmadan, şunu alıyorum: HATA: uygulama için Hizmet uygulaması için kapsayıcı oluşturulamıyor: json: Go yapı alanına Logmarfig.Config türüne sayı kaldıramaz. Bu şekilde alıntı yaparsam: "5"çalışır. 10mGerçekten de alıntı yapmadan çalışır.
Adrian W

Görünüşe göre Docker for Windows ile Docker for Linux arasında bir fark var. İkincisinde, değerleri tırnak içine almalıyım. İlkinde değil. Açıklamayı her ikisine de uyacak şekilde güncellendi. Teşekkürler, @AdrianW
Dag Baardsen

0

Mac kullanıcıları için Docker, işte çözüm:

    1. Günlük dosyası yolunu şu yolla bulun:

      $ docker inspect | grep log

    1. SSH docker makinesine ( defaultvarsa , adı docker-machine lsbulmak için çalıştırıldığını varsayalım ):

      $ docker-machine ssh default

    1. Kök kullanıcı olarak değiştir ( başvuru ):

      $ sudo -i

    1. Günlük dosyası içeriğini silin:

      $ echo "" > log_file_path_from_step1


2
docker-makine Mac için Docker ile çalışmaz. Bunun yerine çalıştırabilir "liman işçisi çalıştırmak -ti -v / var / lib / liman işçisi / konteynerler: / var / günden centos bash" ardından "trankulatı --size 0 /var/inception/08d29a7d469232cfef4456dc6eebcbf313bf01ba73e479520a036150c5ab84de/08d29a7d469232cfef4456dc6eebcbf313bf01ba73e479520a036150c5ab84de-json.log"
Jamshid

docker exec -it default shBir kaba bir sh kabuğu girmek için kullanabilirsiniz . Ancak, birçok kapsayıcı dolaylı olarak sudokomutu kullanılabilir hale getirmez .
Dag Baardsen
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.