Cockpit чи Webmin: що обрати для Ubuntu VPS
Порівняння Cockpit і Webmin для Ubuntu VPS: що змінює кожна панель, як працює вхід, чому не можна відкривати їхні порти публічно та коли не потрібна жодна.
Cockpit проти Webmin: коротка відповідь
Cockpit і Webmin — це вебпанелі для керування Linux-сервером через браузер, але вони відповідають на різні потреби. Cockpit постачається у власному репозиторії вашого дистрибутива та отримує дані про систему через systemd, journald, polkit і udisks. Він показує стан сервера, яким ви й надалі керуєте через SSH. Webmin старіший і має значно ширші можливості: він записує конфігураційні файли для Apache, BIND, Postfix, MariaDB та десятків інших сервісів, яких Cockpit не налаштовує. Для цього Webmin запускає власний вебсервер від імені root.
Встановлюйте Cockpit, якщо вам потрібен актуальний стан одного сервера, перегляд журналів і аварійний термінал. Встановлюйте Webmin, якщо вам потрібен редактор на основі форм для сервісу, який ви не хочете налаштовувати вручну. Не розміщуйте жодну з цих панелей на публічному порту з автентифікацією лише за паролем. Якщо у вас уже більше двох або трьох серверів, чесна відповідь часто буде «жодну». Для масштабування зв’язка SSH і Ansible зазвичай краща за будь-яку панель.
Що насправді можна змінити в кожній панелі
Базове встановлення Cockpit невелике, а більшість функцій надається окремими пакетами, які можна не встановлювати:
- служби й таймери systemd: запускати, зупиняти, вмикати та переглядати unit-файл
- журнал, відфільтрований за unit і пріоритетом, який
journalctlіз вибором дати - локальні облікові записи, членство в групах і авторизовані ключі SSH
- сховище за допомогою
cockpit-storaged: розділи, групи томів LVM, файлові системи й точки монтування - контейнери за допомогою
cockpit-podman, який керує лише Podman - оновлення пакетів за допомогою
cockpit-packagekit - графіки використання CPU, пам’яті, диска й мережі за допомогою
cockpit-pcp - термінал root у вкладці браузера
Дві функції на Ubuntu VPS можуть виглядати непрацюючими, хоча це не так. Сторінка Networking у Cockpit є інтерфейсом для NetworkManager, а серверні образи Ubuntu використовують netplan із systemd-networkd, тому сторінка відсутня або порожня. Не встановлюйте NetworkManager на віддалений сервер лише для того, щоб повернути цю функцію, оскільки він перебере керування інтерфейсом, а помилка через це також призведе до втрати SSH-сеансу. Керування firewall у Cockpit є інтерфейсом для firewalld, а Ubuntu використовує ufw, тому елементи керування firewall взагалі не відображаються. Натомість ви й далі виконуєте sudo ufw status у терміналі.
Webmin охоплює значно більше функцій, оскільки складається з модулів для окремих служб, а не є однією програмою:
- налаштування Apache, nginx, BIND, Postfix, Dovecot, MariaDB, PostgreSQL і Samba через форми
- користувачі, групи й дискові квоти
- завдання cron і системний час
- оновлення пакетів, а також файловий менеджер із можливістю завантаження й вивантаження файлів
- інтерфейси для керування firewall, зокрема окремі для iptables і firewalld
- резервні копії конфігураційних файлів і модулі кластеризації, які передають одну зміну на інші сервери Webmin
Webmin редагує фактичні файли в /etc. За формами немає прихованої бази даних, тому якщо /etc перебуває під керуванням системи контролю версій, sudo git -C /etc diff після збереження форми точно показує, що записав модуль. Це найшвидший спосіб зрозуміти, що насправді робить будь-яка сторінка Webmin. У докладному описі встановлення Webmin і першого входу розглянуто дерево модулів. Virtualmin і Usermin — окремі продукти, побудовані на тому самому рушії: Virtualmin призначений для shared hosting, а Usermin — для кінцевих користувачів. Усе сказане тут про доступність із мережі стосується і їх.
Як кожен із них виконує автентифікацію
Cockpit не має власної бази користувачів. Його сторінка входу запускає стек PAM (підключуваних модулів автентифікації) у /etc/pam.d/cockpit, тому облікові записи — це ваші Unix-облікові записи, а паролі — ваші Unix-паролі. Обліковий запис root за замовчуванням відхиляється, оскільки його вказано у /etc/cockpit/disallowed-users. Привілейовані дії виконуються через polkit, а інтерфейс повторно запитує пароль перед внесенням змін. Тому в заголовку сторінки може відображатися "Limited access", доки ви не підвищите рівень доступу.
Ця схема має один наслідок, з яким стикаються на захищених серверах. Якщо ви налаштували вхід до SSH лише за ключем із вимкненою автентифікацією за паролем, обліковий запис може взагалі не мати придатного для використання пароля. У такому разі вхід до Cockpit відхиляється, хоча ssh і далі працює. Перевірте це на сервері:
sudo passwd -S deployРезультат, що починається з deploy L, означає, що пароль заблоковано. PAM не має що прийняти, тому жоден введений вами пароль не спрацює. P означає, що встановлено придатний для використання пароль. Власна сторінка входу Cockpit не приймає ключі SSH. Ключі використовуються лише тоді, коли Cockpit підключається далі з комп’ютера, на якому ви увійшли, до іншого вузла.
Webmin зберігає власних користувачів у /etc/webmin/miniserv.users окремо від /etc/passwd і також може виконувати автентифікацію через Unix-облікові записи. Користувач Webmin, якому надано доступ до всіх модулів, має права root на цій машині, незалежно від того, що вказано в його оболонці входу. Webmin має власну підтримку TOTP (одноразових паролів на основі часу) і власне блокування хостів після повторних невдалих спроб входу. Обидві функції вмикаються в Webmin Configuration. Cockpit отримує другий фактор лише після додавання відповідного модуля до PAM, наприклад за допомогою libpam-google-authenticator.
Як оновлюється кожен із них
Cockpit пакується вашим дистрибутивом. В Ubuntu 24.04 він надходить з архіву, а upstream-проєкт рекомендує pocket backports для новішої збірки:
. /etc/os-release
sudo apt update
sudo apt install -t ${VERSION_CODENAME}-backports cockpit
sudo systemctl status cockpit.socket
apt policy cockpitapt policy виводить установлену версію та репозиторій, з якого її отримано. Якщо backports не містить новішої збірки, apt використовує версію з архіву, і це нормально. cockpit.socket має вивести active (listening). Після цього виправлення безпеки надходитимуть під час того самого запуску unattended-upgrades, що й оновлення kernel, від видавця, якому ви вже довіряєте.
Webmin відсутній в архіві Ubuntu. Офіційний спосіб установлення спочатку додає власний репозиторій Webmin і signing key:
curl -o webmin-setup-repo.sh https://raw.githubusercontent.com/webmin/webmin/master/webmin-setup-repo.sh
sudo sh webmin-setup-repo.sh
sudo apt-get install webmin --install-recommendsПеред запуском прочитайте цей script, оскільки він виконується від імені root. Відтоді кожен apt upgrade на сервері також отримуватиме пакети з репозиторію Webmin. Отже, ви додали другого видавця, якому на цьому сервері надано довіру на рівні root. Це реальна вартість Webmin, і її варто пояснити на конкретному прикладі: CVE-2019-15107 була backdoor у кількох пакетах версії 1.9x, яка давала змогу виконувати команди без автентифікації. Вона стала доступною користувачам через компрометацію build host проєкту, а не його source repository. Пакування дистрибутивом не усуває таку можливість. Проте воно додає етапи збирання та перевірки, які вам не потрібно підтримувати самостійно.
Чому жодну з них не слід відкривати на публічному порту
Cockpit прослуховує TCP-порт 9090, а Webmin — TCP-порт 10000. Обидва використовують TLS (transport layer security) із самопідписаним сертифікатом, тому першою з’являється попередження браузера. У статті Створення та довіряння самопідписаному сертифікату пояснюється, про що це попередження свідчить, а про що — ні. Обидва порти постійно сканують, а обидві панелі надають доступ до root. Тому вгаданий або повторно використаний пароль означає повний компроміс сервера.
Безпечний варіант — прив’язати панель до localhost і підключатися до неї через SSH-тунель. Для Cockpit перевизначте socket unit:
sudo systemctl edit cockpit.socket[Socket]
ListenStream=
ListenStream=127.0.0.1:9090Порожній ListenStream= в окремому рядку обов’язковий. systemd додає значення до параметрів-списків. Без нього unit зберігає початковий 0.0.0.0:9090 і додає нову адресу, тому панель усе ще залишається доступною ззовні. Застосуйте перевизначення та перевірте, що прослуховується:
sudo systemctl daemon-reload
sudo systemctl restart cockpit.socket
sudo ss -lntp | grep 9090У виведенні має бути 127.0.0.1:9090. Адреса *:9090 або 0.0.0.0:9090 означає, що перевизначення не застосувалося. Тепер відкрийте тунель зі свого комп’ютера та перейдіть до https://localhost:9090:
ssh -N -L 9090:127.0.0.1:9090 deploy@203.0.113.10Локальний порт має збігатися з віддаленим портом. Cockpit порівнює заголовок Origin браузера з адресою, на якій, на його думку, працює сервіс. Тому тунель із локальним портом 9999 завантажує сторінку входу, але потім вхід завершується помилкою, а journalctl -u cockpit фіксує відхилене джерело. Якщо потрібен інший локальний порт, укажіть його в /etc/cockpit/cockpit.conf:
[WebService]
Origins = https://localhost:9999 https://127.0.0.1:9999Перезапустіть сервіс за допомогою sudo systemctl restart cockpit.socket, щоб застосувати це значення. Для Webmin відповідний параметр міститься в /etc/webmin/miniserv.conf:
bind=127.0.0.1sudo systemctl restart webmin
sudo ss -lntp | grep 10000
ssh -N -L 10000:127.0.0.1:10000 deploy@203.0.113.10Webmin також перевіряє заголовок Referer у POST-запитах форм, і відхиляє запити, які, на його думку, надходять з іншого хоста. Саме це ламає першу спробу налаштувати reverse proxy. Рядок referers= у тому самому файлі визначає, де дозволити ім’я хоста проксі, а webprefix= задає шлях, за яким Webmin доступний.
Інший варіант — reverse proxy з автентифікацією: nginx спереду, а вхід виконує шар єдиного входу Authentik. Це працює, але є другим за безпечністю варіантом. Панель усе одно працює від імені root за проксі, а вам доводиться підтримувати дві точки входу замість однієї. Тунель взагалі не додає сервісів, що прослуховують порти в інтернеті, і повторно використовує SSH-ключ, який ви вже захищаєте.
Яку панель обрати для сервера, на якому вже працюють production-сервіси
Cockpit — з двох причин, важливих, коли від сервера залежать інші люди. Він активується через socket, тому cockpit-ws працює лише під час відкритої сесії, а постійного root daemon, який очікує підключень на порту, немає. Cockpit нічим не керує поза собою: після видалення пакета всі сервіси продовжують працювати так само, оскільки Cockpit не зберігає власної конфігурації. miniserv.pl Webmin продовжує працювати у фоновому режимі незалежно від того, чи хтось увійшов у систему. Перевірте, скільки пам’яті споживає ваш процес, за допомогою systemctl status webmin. Команда виводить resident memory запущеного процесу.
Якщо вам потрібні DNS- або mail-модулі Webmin, виділіть для них окремий сервер. Webmin на сервері, який виконує лише одне завдання й прив’язаний до 127.0.0.1, створює обмежений ризик. Webmin на тому самому хості, що й застосунок, доступний клієнтам, — ні. Виконайте базове налаштування до встановлення будь-якої панелі: у матеріалі перші десять хвилин на новому VPS описано non-root користувача та firewall, які обидві панелі припускають як уже налаштовані.
Коли відповідь — не Cockpit
Панель працює для одного сервера та потребує ручних дій. Вона не зберігає відомості про те, що саме змінилося і чому. Для одного сервера цього достатньо. На п’яти серверах ви повторюєте ті самі дії, а на двадцяти вже складно визначити, на якому сервері зміна не застосувалася. Cockpit може додавати інші хости до одного сеансу через SSH, але в останніх версіях це вимкнено за замовчуванням. Для цього потрібно налаштувати AllowMultiHost=yes у /etc/cockpit/cockpit.conf. Навіть тоді вам доведеться п’ять разів натискати ті самі елементи керування.
Альтернатива — звичайний SSH і конфігурація в git-репозиторії. У матеріалі Керування кількома Linux-серверами з одного місця описано структуру такого підходу. У першому Ansible playbook одне правило firewall застосовується до кожного хоста з одного файла, зміни в якому можна переглянути як diff. Робота з контейнерами організовується так само: docker compose up -d через SSH із файла в git, як описано в посібнику з основ Docker Compose, практичніша за роботу в будь-якій панелі. До того ж Cockpit взагалі не керує Docker.
Використовуйте панель для завдань, з якими термінал працює незручно, наприклад для перегляду графіка метрик або пошуку одного з сорока unit, який завершився помилкою. Для всього, що ви виконуватимете більше двох разів, використовуйте код.
Причини збоїв і повідомлення, які ви побачите
Cockpit відхиляє пароль, який приймає SSH. Для цього облікового запису дозволено вхід лише за ключем. sudo passwd -S alice виводить L у другому полі, тому PAM не має пароля для перевірки. Задайте пароль за допомогою sudo passwd alice або залиште цей обліковий запис для SSH, а до Cockpit входьте як інший користувач.
Cockpit не допускає root навіть із правильним паролем. /etc/cockpit/disallowed-users містить root. Увійдіть як звичайний користувач із правами sudo. Це передбачений спосіб, оскільки polkit тоді записує, який користувач виконав підвищення привілеїв.
У Cockpit немає сторінки Networking або Firewall. Для цих сторінок потрібні NetworkManager і firewalld. Ubuntu VPS використовує netplan із systemd-networkd та ufw, тому ці сторінки не з’являються. Це не означає, що щось зламано. Продовжуйте використовувати ufw через SSH.
Сторінка входу Cockpit завантажується через тунель, але вхід завершується помилкою. Локальний порт відрізняється від віддаленого, тому перевірка Origin завершується помилкою, і journalctl -u cockpit показує це. Зрівняйте порти або задайте Origins у /etc/cockpit/cockpit.conf.
Надсилання форм Webmin завершується помилкою після розміщення панелі за проксі. Перевірка Referer відхиляє такі запити. Додайте ім’я хоста проксі до referers= у /etc/webmin/miniserv.conf і задайте webprefix=, якщо панель доступна за шляхом.
Ви не впевнені, чи доступна панель із зовнішньої мережі. sudo ss -lntp | grep -E '9090|10000' дає відповідь на це безпосередньо із сервера, а Webmin записує кожну спробу входу до /var/webmin/miniserv.log. Цей журнал варто переглянути після будь-якої зміни параметрів прослуховування.
FAQ
Що краще для одного Ubuntu VPS: Cockpit чи Webmin?
Для більшості користувачів — Cockpit, оскільки він постачається з власного репозиторію Ubuntu, оновлюється разом з іншими компонентами системи й працює лише під час відкритої сесії браузера. Обирайте Webmin, якщо вам потрібен редактор служб на основі форм, які Cockpit не підтримує, наприклад BIND або Postfix. У такому разі врахуйте, що його вебсервер постійно працює від імені root, а оновлення надходять із власного репозиторію Webmin.
Чи можна запускати Cockpit і Webmin на одному сервері?
Так. Вони використовують різні порти: 9090 і 10000. Конфлікту немає, оскільки кожна панель безпосередньо редагує систему, а не керує нею одноосібно. Проте це невигідний компроміс. Кожна панель створює окремий логін із можливістю роботи від імені root на тому самому комп’ютері, тому ви подвоюєте площу атаки заради кількох додаткових натискань. Якщо встановлюєте обидві панелі, прив’яжіть їх до 127.0.0.1 і підключайтеся до них через SSH-тунель.
Чи безпечно відкривати порт 9090 або 10000 в інтернет?
Ні, якщо використовується вхід за паролем. Обидві панелі надають доступ до root, а обидва порти виявляються під час звичайного сканування протягом кількох годин після відкриття. Прив’яжіть панель до 127.0.0.1, потім виконайте ssh -N -L 9090:127.0.0.1:9090 user@host і відкрийте https://localhost:9090 у браузері. Перевірте результат за допомогою sudo ss -lntp | grep 9090. Команда має показати 127.0.0.1:9090, а не 0.0.0.0:9090. Другим прийнятним варіантом є reverse proxy з автентифікацією.
Чому не вдається ввійти до Cockpit, хоча SSH із ключем працює?
Cockpit виконує автентифікацію через PAM за допомогою пароля Unix. Сторінка входу не приймає SSH-ключі. На захищеному сервері обліковий запис часто не має придатного для використання пароля. Виконайте sudo passwd -S youruser. Значення L у другому полі означає, що пароль заблокований, тому PAM не має що приймати й кожна спроба входу відхиляється. Установіть пароль за допомогою sudo passwd youruser або використовуйте для панелі інший обліковий запис.
Чи керує Cockpit контейнерами Docker?
Ні. Сторінка контейнерів у Cockpit походить із cockpit-podman і керує Podman. Старий модуль Docker вилучили багато років тому, і його не повернуть. Якщо ваші служби працюють у Docker, керуйте ними за допомогою compose-файлу у системі контролю версій через SSH, а Cockpit використовуйте для керування системою навколо них, наприклад журналом і дисками.