Come reindirizzare i log del contenitore Docker a un singolo file?


111

Desidero reindirizzare tutti i registri del mio contenitore Docker a un singolo file di registro per analizzarli. Provai

docker logs container > /tmp/stdout.log 2>/tmp/stderr.log

ma questo dà accesso a due file diversi. Ho già provato

docker logs container > /tmp/stdout.log

ma non ha funzionato.

Risposte:


137

Non è necessario reindirizzare i registri.

Docker per impostazione predefinita archivia i log in un file di log. Per controllare il percorso del file di registro eseguire il comando:

docker inspect --format='{{.LogPath}}' containername

/var/lib/docker/containers/f844a7b45ca5a9589ffaa1a5bd8dea0f4e79f0e2ff639c1d010d96afb4b53334/f844a7b45ca5a9589ffaa1a5bd8dea0f4e79f0e2ff639c1d010d96afb4b53334-json.log

Apri il file di registro e analizza.

se reindirizzi i log, otterrai solo i log prima del reindirizzamento. non sarai in grado di vedere i registri live.

MODIFICARE:

Per vedere i registri in tempo reale puoi eseguire il comando seguente

tail -f `docker inspect --format='{{.LogPath}}' containername`

Nota:

Questo file di registro /var/lib/docker/containers/f844a7b45ca5a9589ffaa1a5bd8dea0f4e79f0e2ff639c1d010d96afb4b53334/f844a7b45ca5a9589ffaa1a5bd8dea0f4e79f0e2ff639c1d010d96afb4b53334-json.logverrà creato solo se docker genera registri se non ci sono registri, questo file non sarà presente. è simile come a volte se eseguiamo il comando docker logs containernamee non restituisce nulla. In quello scenario questo file non sarà disponibile.


tail -f `docker inspect --format='{{.LogPath}}' myapp`- è davvero JSON
Adam

fallirà se quel file non è presente. significa che se docker non genera alcun registro, questo file non verrà creato. ma se docker genera log, questo comando è utile per vedere i log in tempo reale. grazie Adam. aggiungendolo alla mia risposta per aiutare gli altri.
pl_rock

"Docker per impostazione predefinita archivia i registri in un file di registro." - in che contesto? Tutti i contenitori in esecuzione su un host Docker ottengono l'output in un singolo file? Un unico contenitore?
Chris Stryczynski

@ChrisStryczynski Docker crea un file di registro per contenitore
Eddy Hernandez

127

Che ne dici di questa opzione:

docker logs containername >& logs/myFile.log

Non reindirizzerà i registri richiesti nella domanda, ma li copierà una volta in un file specifico.


Se non sbaglio, questo comando copierà sostanzialmente tutti i registri da quando il contenitore è stato avviato per presentarli a myFile.logs. Giusto.?
S Andrew,

@SAndrew fondamentalmente sì! ma le nuove versioni di Docker potrebbero cambiare. meglio vedere docker logs --helpper essere sicuri
Eddy Hernandez

39

docker logs -f <yourContainer> &> your.log &

Spiegazione:

  • -f(cioè --follow): scrive tutti i log esistenti e continua ( segue ) registrando tutto ciò che viene dopo.
  • &> reindirizza sia lo standard output che lo standard error.
  • È probabile che tu voglia eseguire quel metodo in background, quindi il file &.
  • Puoi separare output e stderr con: > output.log 2> error.log(invece di usare &>).

9

Per acquisire sia stdout che stderr dal tuo contenitore Docker in un singolo file di log, esegui quanto segue:

docker logs container > container.log 2>&1

8

Supponendo che tu abbia più contenitori e desideri aggregare i log in un unico file, devi usare un aggregatore di log come fluentd. fluentd è supportato come driver di registrazione per i container Docker.

Quindi in docker-compose, è necessario definire il driver di registrazione

  service1:
    image: webapp:0.0.1
    logging:
      driver: "fluentd"
      options:
        tag: service1 

  service2:
        image: myapp:0.0.1
        logging:
          driver: "fluentd"
          options:
            tag: service2

Il secondo passaggio sarebbe aggiornare la configurazione fluentd per soddisfare i registri sia per il servizio 1 che per il servizio 2

 <match service1>
   @type copy
   <store>
    @type file
    path /fluentd/log/service/service.*.log
    time_slice_format %Y%m%d
    time_slice_wait 10m
    time_format %Y%m%dT%H%M%S%z
  </store>
 </match> 
 <match service2>
    @type copy
   <store>
    @type file
    path /fluentd/log/service/service.*.log
    time_slice_format %Y%m%d
    time_slice_wait 10m
    time_format %Y%m%dT%H%M%S%
  </store>
 </match> 

In questa configurazione, chiediamo che i log vengano scritti su un singolo file in questo percorso
/fluentd/log/service/service.*.log

e il terzo passo sarebbe eseguire il fluentd personalizzato che inizierà a scrivere i log su file.

Ecco il link per le istruzioni passo passo

Bit lungo, ma in modo corretto poiché si ottiene un maggiore controllo sul percorso dei file di registro ecc.E funziona bene anche in Docker Swarm.


1

Poiché Docker unisce stdout e stderr per noi, possiamo trattare l'output del log come qualsiasi altro flusso di shell. Per reindirizzare i registri correnti a un file, utilizzare un operatore di reindirizzamento

$ docker logs test_container > output.log
docker logs -f test_container > output.log

Invece di inviare l'output a stderr e stdout, reindirizza l'output della tua applicazione a un file e mappa il file su una memoria permanente al di fuori del contenitore.

$ docker logs test_container> /tmp/output.log

Docker non accetterà percorsi relativi sulla riga di comando, quindi se desideri utilizzare una directory diversa, dovrai utilizzare il percorso completo.


1

Se lavori su Windows e utilizzi PowerShell (come me), puoi utilizzare la seguente riga per acquisire stdoute stderr:

 docker logs <containerId> | Out-File 'C:/dev/mylog.txt'

Spero che aiuti qualcuno!


1
Per salvare tutti i log del contenitore in un file, in base al nome del contenitore ...foreach ($element in $(docker ps -a --format "{{.Names}}")) {docker logs $element | Out-File "C:/dockerlogs/$element.log"}
xisket

1

Il modo più semplice che uso è questo comando sul terminale:

docker logs elk > /home/Desktop/output.log

la struttura è:

docker logs <Container Name> > path/filename.log

1

Prima controlla il tuo ID contenitore

docker ps -a

Puoi vedere la prima riga nelle colonne CONTAINER ID. Probabilmente assomiglia a questo "3fd0bfce2806" quindi digitalo nella shell

docker inspect --format='{{.LogPath}}' 3fd0bfce2806

Vedrai qualcosa di simile

/var/lib/docker/containers/3fd0bfce2806b3f20c2f5aeea2b70e8a7cff791a9be80f43cdf045c83373b1f1/3fd0bfce2806b3f20c2f5aeea2b70e8a7cff791a9be80f43cdf045c83373b1f1-json.log

allora puoi vederlo come

cat /var/lib/docker/containers/3fd0bfce2806b3f20c2f5aeea2b70e8a7cff791a9be80f43cdf045c83373b1f1/3fd0bfce2806b3f20c2f5aeea2b70e8a7cff791a9be80f43cdf045c83373b1f1-json.log

Sarebbe in formato JSON, puoi usare il timestamp per tracciare gli errori


0

Script Bash per copiare tutti i log del contenitore in una directory specificata:

#!/usr/bin/env bash

TARGET_DIR=~/logs/docker_logs
mkdir -p "$TARGET_DIR"
for name in `sudo docker ps --format '{{.Names}}'`;
do
    path=$(sudo docker inspect --format='{{.LogPath}}' $name)
    sudo cp -rf "$path" "$TARGET_DIR"/$name.log
done
Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.