Docker — популярная платформа виртуализации на уровне ОС. Она поставляет приложения в пакетах (контейнерах), которые, представляют собой изолированные среды с собственным программным обеспечением, библиотеками и конфигурационными файлами.
Как и в любом другом современном программном обеспечении, протоколирование событий и сообщений, таких как предупреждения и ошибки, является неотъемлемой частью платформы Docker, что позволяет вам отлаживать приложения и решать производственные проблемы.
Мы рассмотрим несколько простых способов, с помощью которых вы можете управлять и отслеживать логи для своих контейнеров. Итак, давайте начнем.
Команда Docker Logs
Основной синтаксис для получения журналов контейнера следующий:
$ docker logs [OPTIONS] <CONTAINER-NAME OR ID>
или
$ docker container logs [OPTIONS] <CONTAINER-NAME OR ID>
Оба синтаксиса по сути одинаковы, поэтому в остальных командах в этой статье мы будем использовать именно docker logs.
Хотя следует отметить, что приведенная выше команда работает только для контейнеров, запущенных с драйвером журналирования json-file или journald.
Здесь OPTIONS относится к доступным поддерживаемым флагам команды docker logs, которые перечислены ниже:
Название, сокращение
Описание
--details
Показать дополнительные подробности.
--follow, -f
Проследить вывод
--since
Показывать журналы с временной меткой (например, 2021-08-28T15:23:37Z) или относительно (например, 56m для 56 минут)
--tail , -n
Количество строк, которые нужно показать с конца журнала
--timestamps, -t
Показать временные метки
--until
Показывать журналы до временной метки (например, 2021-08-28T15:23:37Z)
Пример:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
28913415ed22 nginx "/docker-entrypoint.…" 2 seconds ago Up 1 second 80/tcp gifted_edison
$ docker logs 28913415ed22
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2021/08/28 09:02:59 [notice] 1#1: using the "epoll" event method
2021/08/28 09:02:59 [notice] 1#1: nginx/1.21.1
2021/08/28 09:02:59 [notice] 1#1: built by gcc 8.3.0 (Debian 8.3.0-6)
2021/08/28 09:02:59 [notice] 1#1: OS: Linux 5.8.0-1039-azure
2021/08/28 09:02:59 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2021/08/28 09:02:59 [notice] 1#1: start worker processes
2021/08/28 09:02:59 [notice] 1#1: start worker process 31
2021/08/28 09:02:59 [notice] 1#1: start worker process 32
$
Расположение журналов Docker
Docker по умолчанию собирает стандартный вывод (и стандартную ошибку) всех ваших контейнеров и записывает их в файлы, используя формат JSON. Для этого используется драйвер логирования JSON File или json-file. По умолчанию эти журналы хранятся в специфических для каждого контейнера местах в файловой системе /var/lib/docker.
В качестве примера, для контейнера redis, указанного ниже, можно проверить файлы json, как показано во фрагменте ниже:
$ docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
551c9273bbea redis "docker-entrypoint.s…" 19 minutes ago Up 19 minutes 6379/tcp redis
6cc871763df1 nginx "/docker-entrypoint.…" 7 hours ago Up 7 hours 0.0.0.0:8080->80/tcp, :::8080->80/tcp nostalgic_wescoff
$ sudo ls -l /var/lib/docker/containers/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73-json.log
-rw-r----- 1 root root 1437 Aug 28 16:53 /var/lib/docker/containers/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73-json.log
$ sudo tail -10 /var/lib/docker/containers/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73/551c9273bbea6eaf66523ed735866b9ebe6924c3b504dfeb44bef90e69d59c73-json.log
{"log":"1:C 28 Aug 2021 16:53:42.160 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo\n","stream":"stdout","time":"2021-08-28T16:53:42.16031257Z"}
{"log":"1:C 28 Aug 2021 16:53:42.160 # Redis version=6.2.5, bits=64, commit=00000000, modified=0, pid=1, just started\n","stream":"stdout","time":"2021-08-28T16:53:42.160337871Z"}
{"log":"1:C 28 Aug 2021 16:53:42.160 # Warning: no config file specified, using the default config. In order to specify a config file use redis-server /path/to/redis.conf\n","stream":"stdout","time":"2021-08-28T16:53:42.160342171Z"}
{"log":"1:M 28 Aug 2021 16:53:42.160 * monotonic clock: POSIX clock_gettime\n","stream":"stdout","time":"2021-08-28T16:53:42.160792578Z"}
{"log":"1:M 28 Aug 2021 16:53:42.161 * Running mode=standalone, port=6379.\n","stream":"stdout","time":"2021-08-28T16:53:42.161148683Z"}
{"log":"1:M 28 Aug 2021 16:53:42.161 # Server initialized\n","stream":"stdout","time":"2021-08-28T16:53:42.161170984Z"}
{"log":"1:M 28 Aug 2021 16:53:42.161 # WARNING overcommit_memory is set to 0! Background save may fail under low memory condition. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.\n","stream":"stdout","time":"2021-08-28T16:53:42.161186984Z"}
{"log":"1:M 28 Aug 2021 16:53:42.161 * Ready to accept connections\n","stream":"stdout","time":"2021-08-28T16:53:42.161484389Z"}
$
Показать дополнительные подробности
Чтобы показать дополнительные подробности, предоставляемые в журналах, используйте флаг --details.
Пример:
$ docker logs 6cc871763df1 --details
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2021/08/28 10:29:05 [notice] 1#1: using the "epoll" event method
2021/08/28 10:29:05 [notice] 1#1: nginx/1.21.1
2021/08/28 10:29:05 [notice] 1#1: built by gcc 8.3.0 (Debian 8.3.0-6)
2021/08/28 10:29:05 [notice] 1#1: OS: Linux 5.8.0-1039-azure
2021/08/28 10:29:05 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2021/08/28 10:29:05 [notice] 1#1: start worker processes
2021/08/28 10:29:05 [notice] 1#1: start worker process 33
2021/08/28 10:29:05 [notice] 1#1: start worker process 34
172.17.0.1 - - [28/Aug/2021:10:29:26 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.68.0" "-"
$
Просмотр вывода журнала
Вы можете использовать флаг --follow или -f для отслеживания вывода журнала. Это позволит вам следить за новыми обновлениями в потоке журналов из постоянных STDOUT и STDERR.
Пример:
$ docker logs 6cc871763df1 -f
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2021/08/28 10:29:05 [notice] 1#1: using the "epoll" event method
2021/08/28 10:29:05 [notice] 1#1: nginx/1.21.1
2021/08/28 10:29:05 [notice] 1#1: built by gcc 8.3.0 (Debian 8.3.0-6)
2021/08/28 10:29:05 [notice] 1#1: OS: Linux 5.8.0-1039-azure
2021/08/28 10:29:05 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2021/08/28 10:29:05 [notice] 1#1: start worker processes
2021/08/28 10:29:05 [notice] 1#1: start worker process 33
2021/08/28 10:29:05 [notice] 1#1: start worker process 34
172.17.0.1 - - [28/Aug/2021:10:29:26 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.68.0" "-"
Хвостовые журналы
С помощью флага --tail или -n журналы контейнера можно свести в хвост, чтобы ограничить количество выводимых на экран данных. По умолчанию этот флаг принимает в качестве аргумента all, который показывает весь поток журналов. Чтобы показать фиксированное количество строк от конца журнала, укажите целое положительное число после флага --tail или -n.
Пример:
$ docker logs 6cc871763df1 -n 10
/docker-entrypoint.sh: Configuration complete; ready for start up
2021/08/28 10:29:05 [notice] 1#1: using the "epoll" event method
2021/08/28 10:29:05 [notice] 1#1: nginx/1.21.1
2021/08/28 10:29:05 [notice] 1#1: built by gcc 8.3.0 (Debian 8.3.0-6)
2021/08/28 10:29:05 [notice] 1#1: OS: Linux 5.8.0-1039-azure
2021/08/28 10:29:05 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2021/08/28 10:29:05 [notice] 1#1: start worker processes
2021/08/28 10:29:05 [notice] 1#1: start worker process 33
2021/08/28 10:29:05 [notice] 1#1: start worker process 34
172.17.0.1 - - [28/Aug/2021:10:29:26 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.68.0" "-"
$
Показать журналы с момента появления
Мы можем ограничить вывод журналов, используя флаг --since и указывая временную метку, например абсолютное значение с синтаксисом 2021-08-28T15:23:37Z или относительное, например 56m для 56 минут.
Параметр --since показывает только журналы контейнеров, созданные после заданной даты. Вы можете указать дату как дату RFC 3339, временную метку UNIX или строку длительности Go (например, 1m30s, 3h). Если в конце временной метки не указано Z или смещение +-00:00, будет использоваться локальный часовой пояс клиента. Параметр --since можно комбинировать с одним или обоими параметрами --follow или --tail.
В приведенном выше примере показаны журналы только за 2 минуты, где nostalgic_wescoff - это автоматически сгенерированное имя, присвоенное контейнеру nginx.
Показать журналы до
Как и флаг --since, журналы docker также поддерживают флаг --until, который показывает журналы до заданной временной метки. Аналогично предыдущему флагу, временная метка может быть указана как абсолютное значение с синтаксисом 2021-08-28T15:23:37Z или относительное, например 56m для 56 минут.
Пример:
$ docker logs --until=1h30m nostalgic_wescoff
/docker-entrypoint.sh: /docker-entrypoint.d/ is not empty, will attempt to perform configuration
/docker-entrypoint.sh: Looking for shell scripts in /docker-entrypoint.d/
/docker-entrypoint.sh: Launching /docker-entrypoint.d/10-listen-on-ipv6-by-default.sh
10-listen-on-ipv6-by-default.sh: info: Getting the checksum of /etc/nginx/conf.d/default.conf
10-listen-on-ipv6-by-default.sh: info: Enabled listen on IPv6 in /etc/nginx/conf.d/default.conf
/docker-entrypoint.sh: Launching /docker-entrypoint.d/20-envsubst-on-templates.sh
/docker-entrypoint.sh: Launching /docker-entrypoint.d/30-tune-worker-processes.sh
/docker-entrypoint.sh: Configuration complete; ready for start up
2021/08/28 10:29:05 [notice] 1#1: using the "epoll" event method
2021/08/28 10:29:05 [notice] 1#1: nginx/1.21.1
2021/08/28 10:29:05 [notice] 1#1: built by gcc 8.3.0 (Debian 8.3.0-6)
2021/08/28 10:29:05 [notice] 1#1: OS: Linux 5.8.0-1039-azure
2021/08/28 10:29:05 [notice] 1#1: getrlimit(RLIMIT_NOFILE): 1048576:1048576
2021/08/28 10:29:05 [notice] 1#1: start worker processes
2021/08/28 10:29:05 [notice] 1#1: start worker process 33
2021/08/28 10:29:05 [notice] 1#1: start worker process 34
172.17.0.1 - - [28/Aug/2021:10:29:26 +0000] "GET / HTTP/1.1" 200 612 "-" "curl/7.68.0" "-"
$
В приведенном выше примере будут показаны все журналы до 1 часа 30 минут.
Показать временные метки
Многие контейнерные приложения предлагают временные метки, встроенные в вывод логов, поэтому Docker также показывает их с помощью команды docker logs. Если вам нужно, чтобы Docker явно префиксировал свои временные метки в выводе, используйте флаг --timestamps или -t.
Пример:
$ docker logs -t redis
2021-08-28T16:53:42.160312570Z 1:C 28 Aug 2021 16:53:42.160 # oO0OoO0OoO0Oo Redis is starting oO0OoO0OoO0Oo
2021-08-28T16:53:42.160337871Z 1:C 28 Aug 2021 16:53:42.160 # Redis version=6.2.5, bits=64, commit=00000000, modified=0, pid=1, just started
2021-08-28T16:53:42.160342171Z 1:C 28 Aug 2021 16:53:42.160 # Warning: no config file specified, using the default config. In order to specify a config file use redis-server /path/to/redis.conf
2021-08-28T16:53:42.160792578Z 1:M 28 Aug 2021 16:53:42.160 * monotonic clock: POSIX clock_gettime
2021-08-28T16:53:42.161148683Z 1:M 28 Aug 2021 16:53:42.161 * Running mode=standalone, port=6379.
2021-08-28T16:53:42.161170984Z 1:M 28 Aug 2021 16:53:42.161 # Server initialized
2021-08-28T16:53:42.161186984Z 1:M 28 Aug 2021 16:53:42.161 # WARNING overcommit_memory is set to 0! Background save may fail under low memory condition. To fix this issue add 'vm.overcommit_memory = 1' to /etc/sysctl.conf and then reboot or run the command 'sysctl vm.overcommit_memory=1' for this to take effect.
2021-08-28T16:53:42.161484389Z 1:M 28 Aug 2021 16:53:42.161 * Ready to accept connections
$
Объединение флагов
Docker предлагает объединить некоторые флаги, чтобы получить более отфильтрованный вывод, а не печатать все содержимое журнала на экране. В качестве простого примера мы можем объединить флаг --tail с --since, чтобы получить более ограниченный вывод.
Утилиты оболочки Linux также могут быть использованы для более гибкого вывода журнала. Такие утилиты, как grep, head, tail и т. д., могут быть направлены на вывод логов docker для более сложных операций.
Обратите внимание, что нам нужно перенаправить потоки журналов, чтобы обеспечить единый конвейерный вход для grep с помощью 2>&1.
Резюме
Docker — это универсальная платформа, которая предлагает множество функций для администрирования среды. Управление логами системы - один из важнейших навыков, который должен знать каждый системный администратор. Управлять журналами в Docker очень просто, если знать доступные команды и возможные флаги в соответствии с вашими требованиями.
Для получения дополнительной информации о Docker и его функциональных возможностях обратитесь к документации Docker.
Научитесь использовать инструменты и методы DevOps для автоматизации тестирования, сборки и развертывания кода, управления инфраструктурой и ускорения процесса доставки продуктов в продакшн.
Станьте желанным специалистом в IT-индустрии и претендуйте на работу с высокой заработной платой.