Про systemd і автооновлення контейнерів podman
Поговоримо про те, що болить: оновлення контейнерів. Якщо їх у вас багато, цей процес може затягнутися на довго. Як розв’язати цю проблему в Podman і причому тут systemd?
Контейнерний движок Podman
Podman — це проєкт з відкритим вихідним кодом, доступний на більшості платформ Linux і знаходиться на GitHub. Podman — це самостійна заміна Docker, яка не вимагає демонів. В утиліти схожий інтерфейс і набір команд як у Docker, і що більш цікаво — вона може обробляти контейнери з повним і некореневим доступом. Утиліта Podman встановлена на Fedora Linux, так що ви можете відразу її використовувати.
Якщо хочете встановити Podman, виберіть відповідну команду для вашого середовища:
# Fedora Workstation / Server / Spins
$ sudo dnf install -y podman
# Fedora Silverblue, IoT, CoreOS
$ rpm-ostree install podman
Podman також доступний для інших дистрибутивів Linux: CentOS, Debian, Ubuntu та інших. Більше інструкцій тут.
Автооновлення контейнерів
Запуск оновлень для контейнерів може бути виснажливим, оскільки вам потрібно:
- витягти новий образ,
- зупинити та зняти контейнер, що працює,
- запустити контейнер з новим образом.
Цю процедуру необхідно виконати для кожного контейнера. Для оновлення 10 контейнерів може знадобитися виконати 30-40 команд. Автоматизація цих кроків заощадить час і забезпечить актуальність всіх даних.
Podman і systemd
Ви можете запускати, зупиняти, перезапускати контейнери через systemd без окремого демона. Все тому що Podman має вбудовану підтримку цієї підсистеми.
Функції автоматичного оновлення Podman потрібно, щоб контейнери працювали через systemd. Це єдиний спосіб автоматизувати все і зробити так, щоб це “все” добре працювало.
Що потрібно зробити?
Запустіть контейнер з бажаними налаштуваннями:
# Run httpd container with some custom settings
$ sudo podman container run -d -t -p 80:80 –name web -v web-volume:/usr/local/apache2/htdocs/:Z docker.io/library/httpd:2.4
# Just a quick check of the container
$ sudo podman container ls
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
58e5b07febdf docker.io/library/httpd:2.4 httpd-foreground 4 seconds ago Up 5 seconds ago 0.0.0.0:80->80/tcp web
# Also check the named volume
$ sudo podman volume ls
DRIVER VOLUME NAME
local web-volume
Тепер налаштуйте systemd для обробки розгортання. Podman згенерує необхідний файл.
# Generate systemd service file
$ sudo podman generate systemd –new –name –files web
/home/USER/container-web.service
Далі, він згенерує файл container-web.service в вашому поточному каталозі. Перегляньте файл і внесіть необхідні зміни так, щоб вам було зручно.
Ось вміст файлу з доданими символами нового рядка і форматуванням для поліпшення читабельності.
# container-web.service
[Unit]
Description=Podman container-web.service
Documentation=man:podman-generate-systemd(1)
Wants=network.target
After=network-online.target
RequiresMountsFor=%t/containers
[Service]
Environment=PODMAN_SYSTEMD_UNIT=%n
Restart=on-failure
TimeoutStopSec=70
ExecStartPre=/bin/rm -f %t/container-web.pid %t/container-web.ctr-id
ExecStart=/usr/bin/podman container run \
–conmon-pidfile %t/container-web.pid \
–cidfile %t/container-web.ctr-id \
–cgroups=no-conmon \
–replace \
-d \
-t \
-p 80:80 \
–name web \
-v web-volume:/usr/local/apache2/htdocs/ \
docker.io/library/httpd:2.4
ExecStop=/usr/bin/podman container stop \
–ignore \
–cidfile %t/container-web.ctr-id \
-t 10
ExecStopPost=/usr/bin/podman container rm \
–ignore \
-f \
–cidfile %t/container-web.ctr-id
PIDFile=%t/container-web.pid
Type=forking
[Install]
WantedBy=multi-user.target default.target
Тепер видаліть поточний контейнер, скопіюйте файл у відповідний каталог systemd і запустіть службу.
# Remove the temporary container
$ sudo podman container rm -f web
# Copy the service file
$ sudo cp container-web.service /etc/systemd/system/container-web.service
# Reload systemd
$ sudo systemctl daemon-reload
# Enable and start the service
$ sudo systemctl enable –now container-web
# Another quick check
$ sudo podman container ls
$ sudo systemctl status container-web
Важливо! Тепер контейнером можна управляти тільки через systemd. Запуск і зупинка контейнера за допомогою команди podman може заважати роботі systemd.
Ручне автоматичне оновлення
Перше, на що варто звернути увагу — це автоматичні оновлення вручну. Звучить дивно? Ця функція дозволяє уникнути зайвих кроків, але при цьому ви повністю контролюєте час і дату поновлення контейнерів. Це дуже корисно, якщо ви хочете оновлювати їх тільки в період обслуговування або на вихідних.
Що потрібно робити?
Відредагуйте файл /etc/systemd/system/container-web.service і додайте до нього мітку:
–label “io.containers.autoupdate=registry”
У зміненому файлі буде розділ, схожий на цей:
…snip…
ExecStart=/usr/bin/podman container run \
–conmon-pidfile %t/container-web.pid \
–cidfile %t/container-web.ctr-id \
–cgroups=no-conmon \
–replace \
-d \
-t \
-p 80:80 \
–name web \
-v web-volume:/usr/local/apache2/htdocs/ \
–label “io.containers.autoupdate=registry” \
docker.io/library/httpd:2.4
…snip…
Тепер перезавантажте systemd і перезапустіть контейнерну службу, щоб зміни набрати чинності.
# Reload systemd
$ sudo systemctl daemon-reload
# Restart container-web service
$ sudo systemctl restart container-web
Після цих маніпуляцій ви зможете запустити просту команду, яка оновить об’єкт, що працює до останнього доступного образу.
Заплановане автооновлення
Podman також має модуль таймера systemd, який дозволяє оновлювати контейнери за розкладом. Не хочете самостійно обробляти оновлення або у вас невеликий домашній сервер? Ця функція стане вашим порятунком, адже ви будете отримувати останні оновлення, наприклад, щотижня.
Що робити?
Увімкніть таймер systemd для podman:
# Enable podman auto update timer unit
$ sudo systemctl enable –now podman-auto-update.timer
Created symlink /etc/systemd/system/timers.target.wants/podman-auto-update.timer → /usr/lib/systemd/system/podman-auto-update.timer.
Ви можете редагувати розклад таймера, якщо вам це потрібно. За замовчуванням оновлення буде запускатися щопонеділка вранці.
Відредагувати модуль таймера можна через цю команду:
$ sudo systemctl edit podman-auto-update.timer
Ось і все. Podman тепер подбає про оновлення, а також про видалення старих образів за розкладом.
Дещо важливе
Автоматизація здається ідеальним рішенням для оновлень контейнерів, але перед цим потрібно врахувати деякі моменти:
- уникайте використання тегу “latest”, оскільки він може містити основні оновлення,
- використовуйте теги “2” або “2.4”, якщо вони є у постачальника образів,
- попередньо протестуйте автооновлення,
- подумайте про створення резервних копій,
- зверніть увагу, що оновлення контейнера не тільки перезапускає його, але і видаляє старий образ,
- періодично перевіряйте, чи застосовуються оновлення.
Авторські курси системного адміністрування Linux у IT Education Center