Про 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

Залишити відповідь

Дякуємо, що поділились