Ручне встановлення

Повністю ручне встановлення: від щойно придбаного VPS до робочої панелі, крок за кроком. Підготовка сервера, створення сайту, база даних, config.php і SSL описані тут. Команди для кожного інструмента безпеки та для cron — у FAQ-довіднику, посилання далі за текстом.

Головне правило: змінюючи SSH або фаєрвол, не закривайте поточне підключення, доки не перевірите нове в окремому вікні. Якщо доступ усе ж втрачено — майже всі хостери надають аварійну консоль (VNC/Recovery) у панелі керування.

01. Придбали VPS з Ubuntu/Debian — з чого почати

Після придбання хостер надсилає: IP-адресу, ім'я користувача (зазвичай root) і пароль (або SSH-ключ). Цього достатньо для входу. Порядок дій (кожен крок — розділ нижче):

  1. Підключитися до сервера через SSH;
  2. Оновити систему, задати ім'я хоста і часовий пояс;
  3. Створити звичайного користувача з правами sudo (не працювати під root);
  4. Налаштувати вхід за SSH-ключем і вимкнути вхід за паролем;
  5. Увімкнути файрвол і автозахист;
  6. (за бажанням) встановити панель керування HestiaCP — вебсервер, БД, пошта «з коробки».

02. Перше підключення через SSH

SSH — це захищений термінал до сервера. Підставте свій IP замість 203.0.113.10.

203.0.113.10 — це приклад, неіснуюча адреса (зарезервована для документації). Не вводьте її як є — замініть на справжній IP вашого сервера з листа хостера. Інакше підключення не буде.

Windows 10/11: відкрийте PowerShell або «Термінал» і скористайтеся вбудованим ssh (або клієнтами PuTTY / MobaXterm).
macOS / Linux: відкрийте «Термінал».

# Вхід під root (пароль надіслав хостер): ssh root@203.0.113.10 # Якщо хостер надав файл-ключ замість пароля: ssh -i шлях/до/ключа root@203.0.113.10
Під час першого підключення SSH запитає про «authenticity of host» — введіть yes. Пароль під час введення не відображається (це нормально). Якщо хостер надав тимчасовий пароль — змініть його командою passwd.

03. Оновлення системи та базове налаштування

Найперше — оновити всі пакети й задати ім’я хоста та часовий пояс.

# Оновити систему: apt update && apt upgrade -y # Базові утиліти: apt install -y curl wget ufw fail2ban unattended-upgrades # Часовий пояс (приклад) та ім’я хоста: timedatectl set-timezone Europe/Kyiv hostnamectl set-hostname myserver # Автоматичні оновлення безпеки: dpkg-reconfigure -plow unattended-upgrades
Список часових поясів — timedatectl list-timezones. Якщо наприкінці оновлення з’явиться синє вікно «Daemons using outdated libraries» — позначте всі служби (Пробіл) і натисніть OK, це безпечно.

04. Створення користувача з sudo

Постійно працювати під root небезпечно. Створіть звичайного користувача й надайте йому права sudo (запуск команд від адміністратора за потреби). Замініть deploy на будь-яке ім’я.

# Створити користувача (задасть пароль і запитає дані — можна Enter): adduser deploy # Додати до групи sudo: usermod -aG sudo deploy # Перевірити (під root): su - deploy sudo whoami # має вивести: root exit
Далі входьте на сервер уже під цим користувачем: ssh deploy@203.0.113.10, а команди адміністратора запускайте з префіксом sudo.

05. SSH-ключі та вимкнення входу за паролем

Вхід за ключем надійніший за пароль: пароль можна підібрати, ключ — практично ні. Спершу створюємо ключ на своєму комп'ютері, копіюємо його на сервер, перевіряємо вхід — і лише потім вимикаємо пароль.

Крок 1. Створити ключ на своєму комп'ютері (Windows PowerShell / macOS / Linux):

ssh-keygen -t ed25519 -C "my-laptop" # Enter на всі питання (ключ ляже в ~/.ssh/id_ed25519)

Крок 2. Скопіювати публічний ключ на сервер:

# macOS / Linux: ssh-copy-id deploy@203.0.113.10 # Windows (PowerShell): type $env:USERPROFILE\.ssh\id_ed25519.pub | ssh deploy@203.0.113.10 "mkdir -p ~/.ssh && chmod 700 ~/.ssh && cat >> ~/.ssh/authorized_keys && chmod 600 ~/.ssh/authorized_keys"

Крок 3. Перевірити вхід за ключем у новому вікні — має пускати без пароля:

ssh deploy@203.0.113.10
Не виконуйте Варіант B, доки вхід за ключем не перевірено й не працює (Кроки 1–3), і не закривайте робочу сесію. Він вимикає вхід за паролем для всіх користувачів, включно з root. Без робочого ключа ви повністю втратите доступ до сервера — повернути його можна буде лише через консоль хостингу. Немає ключа — беріть Варіант A.

Крок 4. Посилити доступ по SSH. Налаштування кладемо в окремий файл, основний конфіг не чіпаємо. Виберіть варіант за ситуацією:

Варіант A — лише закрити root, пароль залишити. Ключ не потрібен, доступ не втратите:

echo 'PermitRootLogin no' | sudo tee /etc/ssh/sshd_config.d/00-hardening.conf >/dev/null sudo systemctl restart ssh

Варіант B — повний hardening. Вимкнути вхід за паролем і залишити root лише за ключем. Виконуйте, тільки переконавшись, що вхід за ключем працює:

sudo tee /etc/ssh/sshd_config.d/00-hardening.conf >/dev/null <<'EOF' PubkeyAuthentication yes PasswordAuthentication no PermitRootLogin prohibit-password KbdInteractiveAuthentication no EOF sudo systemctl restart ssh
В обох варіантах root за паролем закрито. PermitRootLogin no забороняє root повністю, prohibit-password — залишає вхід лише за ключем (для адміністрування входьте під deploy і використовуйте sudo). Якщо хочете змінити порт SSH — додайте рядок Port 2222, але спершу відкрийте новий порт у файрволі (наступний розділ) і перевірте вхід, інакше закриєте собі доступ.

06. Базовий фаєрвол і автозахист

Закрийте все зайве фаєрволом і ввімкніть fail2ban (банить перебір паролів по SSH). Спершу дозвольте SSH, інакше після ввімкнення UFW втратите доступ.

# Дозволити SSH (або ваш порт, якщо змінювали) і веб: sudo ufw allow OpenSSH sudo ufw allow 80,443/tcp # Увімкнути фаєрвол: sudo ufw enable sudo ufw status verbose # fail2ban — захист SSH від перебору (базовий профіль активний одразу): sudo systemctl enable --now fail2ban sudo fail2ban-client status sshd
Це мінімум. Робочі налаштування fail2ban, блок-лист ipsum, розширений UFW та інші інструменти — у групі «Інструменти безпеки» довідника. Сама панель Arcivéo Monitor наочно покаже статус усього цього.

07. Встановлення панелі HestiaCP (опційно)

HestiaCP — безкоштовна панель керування хостингом: встановлює й налаштовує вебсервер (nginx + apache), PHP, базу даних (MariaDB), пошту, DNS та SSL-сертифікати, надає вебінтерфейс для сайтів. Зручна, якщо не хочеться налаштовувати все вручну й ви плануєте розміщувати сайти (зокрема саму панель Arcivéo Monitor).

Встановлюйте HestiaCP на чистий сервер (свіжа підтримувана Ubuntu/Debian, щонайменше ~1–2 ГБ RAM), до встановлення інших вебсерверів і БД — інакше виникнуть конфлікти. Встановлення триває 10–20 хвилин і перезавантажить сервер.
# Завантажити інсталятор і запустити: wget https://raw.githubusercontent.com/hestiacp/hestiacp/release/install/hst-install.sh sudo bash hst-install.sh

Інсталятор запитає email та ім'я хоста, потім встановить увесь стек. Після перезавантаження панель доступна за адресою https://YOUR_IP:8083 (логін і пароль інсталятор покаже наприкінці).

HestiaCP сама керує UFW і fail2ban — окремо їх налаштовувати не потрібно, вона підхопить. SSH-ключі та вимкнення пароля (попередній розділ) все одно виконайте.

08. Системні вимоги та ionCube

Панель — це PHP-застосунок на типовому стеку LAMP/LEMP:

  • ОС: Linux (рекомендовано Ubuntu/Debian);
  • Вебсервер: nginx або Apache з PHP-FPM;
  • PHP 8.0+ з розширеннями: pdo_mysql, openssl, curl, json, mbstring;
  • ionCube Loader — розширення PHP, потрібне для роботи панелі;
  • БД: MySQL 5.7+ або MariaDB 10.3+;
  • HTTPS — обов'язково (вхід і WebAuthn працюють лише через https);
  • sudo для користувача вебсервера (вузький набір — крок 13).
# Перевірити версію PHP і розширення: php -v php -m | grep -iE 'pdo_mysql|openssl|curl|mbstring|ioncube'

Встановлення ionCube Loader (якщо ще не встановлено). На хостингу з панеллю (HestiaCP, cPanel) ionCube вмикається прапорцем у налаштуваннях PHP. Вручну на Ubuntu/Debian:

# Дізнатися версію PHP і каталог розширень: php -v EXTDIR=$(php -r 'echo ini_get("extension_dir");'); PHPVER=$(php -r 'echo PHP_MAJOR_VERSION.".".PHP_MINOR_VERSION;') # Завантажити й розпакувати лоадери (64-bit): cd /tmp wget -q https://downloads.ioncube.com/loader_downloads/ioncube_loaders_lin_x86-64.tar.gz tar xzf ioncube_loaders_lin_x86-64.tar.gz # Скопіювати лоадер під вашу версію PHP до каталогу розширень: sudo cp ioncube/ioncube_loader_lin_${PHPVER}.so "$EXTDIR"/ # Підключити (CLI + PHP-FPM) і перезапустити: echo "zend_extension=ioncube_loader_lin_${PHPVER}.so" | sudo tee /etc/php/${PHPVER}/mods-available/ioncube.ini sudo phpenmod ioncube sudo systemctl restart php${PHPVER}-fpm # Перевірка — у виводі з'явиться рядок "with the ionCube PHP Loader": php -v
Версія лоадера має збігатися з версією PHP (наприклад ioncube_loader_lin_8.1.so для PHP 8.1). Якщо використовуєте кілька версій PHP — підключіть лоадер для кожної.

09. Домен і DNS

Щоб відкривати панель за адресою на кшталт monitor.example.com та отримати безкоштовний SSL — потрібен домен, що вказує на ваш сервер. У панелі керування DNS створіть A-запис:

Тип: A Ім'я: monitor (піддомен → monitor.example.com) або @ (корінь домену → example.com) Значення: 203.0.113.10 ← IP вашого сервера TTL: 3600

За кілька хвилин перевірте, що домен вказує на сервер:

dig +short monitor.example.com # має повернути ваш IP # або, якщо dig немає: getent hosts monitor.example.com
SSL-сертифікат Let's Encrypt видається лише на домен — DNS має вказувати на сервер до випуску сертифіката.

10. Створення сайту та завантаження файлів панелі

Apache: DocumentRoot — на корінь панелі, НЕ на public/. Стилі (CSS/JS), sw.js, manifest.json лежать у assets/ поруч із public/ та запитуються від кореня сайту. Кореневий .htaccess — фронт-контролер. Якщо під Apache вказати DocumentRoot на public/ — панель відкриється без стилів. Для чистого nginx — навпаки: за корінь береться public/, а assets/ віддаються окремим правилом (див. блок nginx нижче).
Файли панелі (архів дистрибутива) завантажуються після покупки в кабінеті my.arciveo.com«Завантаження». Розпакуйте архів перед завантаженням.

1) Створіть каталог панелі та завантажте в нього вміст дистрибутива (щоб усередині опинилися public/, assets/, config.php тощо):

sudo mkdir -p /var/www/monitor # потім залити файли дистрибутива у /var/www/monitor (FileZilla / WinSCP / scp)

2) Налаштуйте вебсервер. Apache: DocumentRoot — на корінь панелі (НЕ на /public); AllowOverride All обов’язковий. Шлях до сокета PHP-FPM визначається автоматично. Блок вставляється в термінал цілком:

PHPSOCK=$(ls -1 /run/php/php*-fpm.sock 2>/dev/null | head -1) # авто-визначення сокета PHP-FPM sudo tee /etc/apache2/sites-available/monitor.conf > /dev/null <<'EOF' <VirtualHost *:80> ServerName monitor.example.com DocumentRoot /var/www/monitor <Directory /var/www/monitor> AllowOverride All Require all granted </Directory> <FilesMatch \.php$> SetHandler "proxy:unix:__PHPSOCK__|fcgi://localhost" </FilesMatch> </VirtualHost> EOF sudo sed -i "s#__PHPSOCK__#${PHPSOCK}#" /etc/apache2/sites-available/monitor.conf sudo a2dissite 000-default.conf sudo a2ensite monitor.conf sudo apache2ctl configtest sudo systemctl reload apache2

nginx: у nginx немає .htaccess, тому за корінь беремо public/, а assets/, sw.js, manifest.json (рівнем вище) віддаємо окремим правилом:

PHPSOCK=$(ls -1 /run/php/php*-fpm.sock 2>/dev/null | head -1) # авто-визначення сокета PHP-FPM sudo tee /etc/nginx/sites-available/monitor.conf > /dev/null <<'EOF' server { listen 80; server_name monitor.example.com; root /var/www/monitor/public; index index.php; # assets, service worker та manifest лежать на рівень вище public/ location ~ ^/(assets/|sw\.js|manifest\.json) { root /var/www/monitor; } location / { try_files $uri $uri/ /index.php?$query_string; } location ~ \.php$ { include snippets/fastcgi-php.conf; fastcgi_pass unix:__PHPSOCK__; } } EOF sudo sed -i "s#__PHPSOCK__#${PHPSOCK}#" /etc/nginx/sites-available/monitor.conf sudo ln -s /etc/nginx/sites-available/monitor.conf /etc/nginx/sites-enabled/ sudo nginx -t && sudo systemctl reload nginx

Завантаження файлів — SFTP/SCP (FileZilla, WinSCP) або scp:

# Приклад через scp з локального комп’ютера: scp -r ./monitor/* deploy@203.0.113.10:/var/www/monitor/
Виставте права на файли — це обов’язковий крок. Якщо заливали під root або через SFTP, файли належать root, і вебсервер (www-data) не зможе їх прочитати — панель відкриється порожньою або з помилкою 403 (у лозі: .htaccess unreadable / directory not executable). Команда нижче це виправляє:
# Нормалізуємо права всього вебрута: каталог, створений root, недоступний # вебсерверу (www-data) — без цього панель віддає порожню сторінку або 403. # Apache працює під www-data; якщо у вас інший вебкористувач — замініть. cd /var/www/monitor # Робочі папки створюємо ДО chown — інакше нові каталоги залишаться root:root # і при chmod 750 вебсервер (www-data) не зможе в них писати. sudo mkdir -p data/lynis data/logwatch tmp logs sudo chown -R www-data:www-data /var/www/monitor sudo find /var/www/monitor -type d -exec chmod 755 {} \; sudo find /var/www/monitor -type f -exec chmod 644 {} \; sudo chmod 640 /var/www/monitor/config.php sudo chmod 750 data tmp logs

3) Відкрийте собі завантаження файлів через SFTP. Після наведеної команди всі файли належать www-data, а FileZilla / WinSCP підключаються під вашим власним користувачем — завантаження тоді завершиться помилкою SSH_FX_PERMISSION_DENIED (Permission denied). Заходити під root для завантаження не можна — вхід root вимкнено на кроці 05. Оберіть один із двох варіантів.

Варіант A — ACL лише для вашого користувача (рекомендовано). Право запису отримуєте тільки ви; вебсервер так само не може перезаписати код панелі:

sudo apt install -y acl # Право запису вашому користувачеві на весь каталог панелі: sudo setfacl -R -m u:deploy:rwX /var/www/monitor # Те саме правило за замовчуванням — для файлів і тек, створених пізніше: sudo setfacl -R -d -m u:deploy:rwX /var/www/monitor

Варіант B — через групу www-data. Простіший, але право запису у файли панелі отримує й вебсервер: за наявності вразливості в PHP код можна буде підмінити. Порядок команд важливий — config.php і робочі теки закриваються останніми:

sudo usermod -aG www-data deploy # Запис для групи + setgid (біт 2): файли, завантажені через SFTP, лишаються # у групі www-data — інакше панель не зможе їх перезаписати. sudo find /var/www/monitor -type d -exec chmod 2775 {} \; sudo find /var/www/monitor -type f -exec chmod 664 {} \; sudo chmod 640 /var/www/monitor/config.php sudo chmod 2750 /var/www/monitor/data /var/www/monitor/tmp /var/www/monitor/logs
Після варіанта B перепідключіться у FileZilla (Сервер → Відключитися, потім увійти знову) — нова група застосовується лише при новому вході, до того прав усе одно не буде. Перевірка: id deploy — у списку груп має з'явитися www-data; ls -ld /var/www/monitor — права drwxrwsr-x, літера s замість x означає, що setgid встановлено.

11. База даних

Створіть базу та користувача, потім імпортуйте схему. Блок вставляється в термінал цілком. monitor_db та monitor_user — імена для прикладу, можете задати будь-які свої; запам’ятайте ім’я бази, користувача та пароль — впишете їх у config.php на наступному кроці:

# 1. База даних. Пароль задається ОДИН раз у DBPASS і підставляється в усі рядки. # Блок вставляється в термінал ЦІЛКОМ; sudo mysql входить root по unix-сокету # (пароль root не потрібен). НЕ використовуйте інтерактивний `sudo mysql -u root -p` # з копіпастом — під час вставки SQL-рядки підуть у запит пароля і зникнуть. DBPASS='CHOOSE_A_PASSWORD' # ← змініть лише цей рядок sudo mysql <<SQL CREATE DATABASE IF NOT EXISTS monitor_db CHARACTER SET utf8mb4; CREATE USER IF NOT EXISTS 'monitor_user'@'localhost' IDENTIFIED BY '$DBPASS'; GRANT ALL ON monitor_db.* TO 'monitor_user'@'localhost'; FLUSH PRIVILEGES; SQL # Перевірка (має показати monitor_db): mysql -u monitor_user -p"$DBPASS" -e "SHOW DATABASES;" # Цей самий пароль впишіть у config.php → DB_PASS.
Схему імпортувати не потрібно — панель сама створює таблиці та обліковий запис admin під час першого входу в браузері (з database/db.sql), якщо БД порожня. Ручний імпорт схеми потрібен, лише якщо автоініціалізація не спрацювала.
Якщо використовували браузерний встановлювач public/start_db.phpвидаліть його одразу після встановлення: він дозволяє без авторизації перестворити базу. Поки файл лежить у корені панелі або в public/, панель показує червоне попередження.

12. Налаштування config.php

config.php у корені панелі (/var/www/monitor/config.php) — єдиний файл, який потрібно відредагувати вручну. Усі налаштування панелі задано в ньому константами define(). Відкрийте його в редакторі:

sudo nano /var/www/monitor/config.php

Підставте свої значення в підсвічені місця; решту залиште як є:

// --- База даних (з кроку 11) --- define('DB_HOST', 'localhost'); // залишити define('DB_NAME', 'db_name'); // що створили на кроці 11 define('DB_USER', 'user'); // що створили на кроці 11 define('DB_PASS', 'db_password'); // що задали на кроці 11 define('DB_CHARSET', 'utf8mb4'); // залишити // --- Застосунок --- define('APP_URL', 'https://monitor.example.com'); // адреса панелі, без слеша в кінці define('TIMEZONE', 'Europe/Kyiv'); // ваш часовий пояс // --- Час сесії --- define('SESSION_LIFETIME', 28800); // простій до повторного входу, сек (28800 = 8 год)

Що змінювати:

  • DB_NAME, DB_USER, DB_PASS — точно ті самі ім’я бази, користувач і пароль, які ви задали під час створення БД на кроці 11 (якщо залишили приклади — monitor_db / monitor_user). DB_HOST і DB_CHARSET не чіпайте.
  • APP_URL — повна адреса панелі з https://, без слеша в кінці й без www. Має збігатися з доменом, на який активуєте ліцензію (крок 16), інакше ключ буде відхилено.
  • TIMEZONE — ваш часовий пояс (список — timedatectl list-timezones). Впливає лише на те, як панель показує дати; на час запуску cron-завдань не впливає (там діє пояс системи).
  • SESSION_LIFETIME — через скільки секунд бездіяльності панель попросить увійти знову (типово 8 годин). Напр. 3600 = 1 година, 86400 = доба.
  • Блок логування помилок (display_errors, log_errors, error_log) — залиште типовим.

Збережіть файл (Ctrl+O, Enter, потім Ctrl+X) і перезапустіть PHP-FPM — інакше через OPcache зміни не застосуються:

sudo systemctl restart php*-fpm
config.php — секретний файл (у ньому пароль БД). Він лежить у корені панелі, який і є вебкоренем, але закритий: права 640 (виставлені на кроці 10) і явна заборона в кореневому .htaccess. Не викладайте його в публічні репозиторії й не передавайте у підтримку з реальним паролем.
Докладний розбір усіх параметрів — у FAQ: «Файл config.php — усі налаштування панелі».

13. Налаштування sudo для веб-сервера

PHP виконується від імені користувача веб-сервера, який не має прав на системні команди. Доступ надається вузько: точковий sudo на конкретні утиліти та читання логів через групи (без sudo). Злам веб-шару не дає root.

У прикладах www-data — стандартний користувач Apache. Якщо у вас інший (у деяких панелях PHP працює від окремого користувача) — замініть всюди. Дізнатися: ps -o user= -C php-fpm | sort -u.

1. Створіть /etc/sudoers.d/monitor через sudo visudo -f /etc/sudoers.d/monitor і вставте (приберіть рядки невикористовуваних модулів):

# UFW — статус і правила (сторінка «Брандмауер») www-data ALL=(ALL) NOPASSWD: /usr/sbin/ufw status, /usr/sbin/ufw status verbose, /usr/sbin/ufw status numbered www-data ALL=(ALL) NOPASSWD: /usr/sbin/ufw allow [0-9]*, /usr/sbin/ufw deny [0-9]*, /usr/sbin/ufw --force delete [0-9]* # Fail2ban — статус, бан і розбан (banned віддає бани всіх jail'ів однією командою; # ban/unban потрібні кнопкам панелі) www-data ALL=(ALL) NOPASSWD: /usr/bin/fail2ban-client status, /usr/bin/fail2ban-client status *, /usr/bin/fail2ban-client banned, /usr/bin/fail2ban-client set * banip *, /usr/bin/fail2ban-client set * unbanip * # Оновлення безпеки (картка «Оновлення»). Тільки читання, але саме від root: # кеш apt (~70 МБ) доступний лише root'у, не-root перезбирає його на кожен виклик # (4.2 с CPU проти 0.01 с). Без wildcard — рівно ця одна команда, нічого не встановлює. www-data ALL=(ALL) NOPASSWD: /usr/bin/apt list --upgradable # IPset (карта атак, дашборд) www-data ALL=(ALL) NOPASSWD: /usr/sbin/ipset list -t ipsum # CrowdSec www-data ALL=(ALL) NOPASSWD: /usr/bin/cscli decisions list *, /usr/bin/cscli alerts list *, /usr/bin/cscli bouncers list *, /usr/bin/cscli scenarios list * # Auditd — пошук подій + читання останніх рядків журналу (точний шлях) www-data ALL=(ALL) NOPASSWD: /usr/sbin/ausearch -m * www-data ALL=(ALL) NOPASSWD: /usr/bin/tail -n 300 /var/log/audit/audit.log # Monit / ModSecurity / AppArmor / PSAD www-data ALL=(ALL) NOPASSWD: /usr/bin/monit status www-data ALL=(ALL) NOPASSWD: /usr/sbin/apache2ctl -M www-data ALL=(ALL) NOPASSWD: /usr/local/bin/monitor-modsec www-data ALL=(ALL) NOPASSWD: /usr/sbin/aa-status www-data ALL=(ALL) NOPASSWD: /usr/sbin/psad --Status # Відкриті порти (журнали ядра/SSH/Falco читаються БЕЗ sudo — через групу # systemd-journal, див. п.2; sudo для journalctl давати НЕ потрібно і небезпечно) www-data ALL=(ALL) NOPASSWD: /usr/bin/ss -tuln, /usr/sbin/ss -tuln, /bin/ss -tuln # PostgreSQL (тільки якщо використовуєте) — фіксований read-only скрипт, # створити за FAQ «PostgreSQL не відображається»; без нього рядок видаліть www-data ALL=(ALL) NOPASSWD: /usr/local/bin/monitor-pgstat
sudo chmod 440 /etc/sudoers.d/monitor sudo visudo -c # має бути "parsed OK"

2. Доступ до логів і журналу systemd. Модулі читають /var/log/fail2ban.log, auth.log, ufw.log, apache2/*, aide напряму (на Debian/Ubuntu ці логи в групі adm). Події ядра, SSH і Falco беруться з journald командою journalctl без sudo, через групу systemd-journal. Додайте веб-користувача в обидві групи та перезапустіть PHP-FPM:

sudo usermod -aG adm,systemd-journal www-data sudo systemctl restart php*-fpm # обов'язково, інакше групи не застосуються

3. Якщо ClamAV чи Suricata пишуть логи не в групу adm (буває root:root) — надайте доступ через ACL:

sudo apt install acl sudo setfacl -R -m u:www-data:rX /var/log/clamav /var/log/suricata 2>/dev/null sudo setfacl -d -m u:www-data:rX /var/log/clamav /var/log/suricata 2>/dev/null

4. Обгортка ModSecurity. Аудит-лог WAF (/var/log/apache2/modsec_audit.log) належить root з правами 640, читати його напряму веб-користувач не може. Сторінка ModSecurity бере режим рушія, події та список активних правил через фіксований read-only скрипт — саме він і дозволений у sudoers рядком вище:

sudo tee /usr/local/bin/monitor-modsec >/dev/null <<'EOF' #!/bin/sh echo "ENGINE=$(grep -hE '^SecRuleEngine[[:space:]]+' /etc/modsecurity/*.conf 2>/dev/null | tail -1 | awk '{print $2}')" echo "---LOG---" tail -n 3000 /var/log/apache2/modsec_audit.log 2>/dev/null echo "---RULES---" for f in /etc/modsecurity/crs/rules/*.conf /usr/share/modsecurity-crs/rules/*.conf /etc/modsecurity/custom-rules.conf; do [ -f "$f" ] && { echo "===FILE:$(basename "$f")==="; cat "$f"; } done EOF sudo chown root:root /usr/local/bin/monitor-modsec sudo chmod 755 /usr/local/bin/monitor-modsec
Без файлу /etc/modsecurity/modsecurity.conf сам WAF не працює: пакет кладе лише modsecurity.conf-recommended, і рушій правил залишається вимкненим — як увімкнути, див. FAQ → «Встановлення ModSecurity».
Користувач у всіх рядках sudoers має збігатися з користувачем FPM-пулу: на звичайному Apache/Debian це www-data, у HestiaCP пул сайту працює від власника сайту (наприклад, admin) — перевірте grep -E '^user' /etc/php/*/fpm/pool.d/monitor.example.com.conf.

5. Якщо перед Apache стоїть Nginx (HestiaCP, ISPmanager та інші панелі — там Nginx проксує PHP в Apache, а статику віддає сам). Службові каталоги закриті файлами .htaccess, але Nginx їх не читає: будь-який статичний файл (.json, .txt, .log, .dat) він віддасть напряму, в обхід Apache. Назовні витечуть кеші панелі та дані — наприклад tmp/modsec_cache.json з подіями WAF та IP-адресами зловмисників. Додайте заборону в конфіг сайту Nginx:

location ^~ /data/ { deny all; } location ^~ /tmp/ { deny all; } location ^~ /logs/ { deny all; } location ^~ /includes/ { deny all; } location ^~ /cron/ { deny all; } location ^~ /database/ { deny all; } location = /config.php { deny all; }
Префікс ^~ обов'язковий: він вибирається раніше за регулярне правило для статики всередині location /, інакше заборона не спрацює.
У HestiaCP кладіть це окремим файлом /home/<user>/conf/web/<domain>/nginx.ssl.conf_denynginx.conf_deny для HTTP) — конфіг сайту підключає nginx.ssl.conf_* і при перезбиранні такі файли не затирає. Застосувати: sudo nginx -t && sudo systemctl reload nginx.
Перевірка: curl -s -o /dev/null -w '%{http_code}\n' https://monitor.example.com/tmp/modsec_cache.json — має бути 403. Якщо Apache працює без Nginx (слухає 80/443 сам), нічого додавати не потрібно — .htaccess достатньо.
Шляхи до бінарників перевірте через which (наприклад which ufw cscli ausearch ss). Редагуйте sudoers лише через visudo. Список усіх баз MySQL вмикається окремим GRANT (FAQ → «Видно лише одну БД»).

14. Обмеження доступу за IP

Обмежте доступ до монітора за IP-адресою — навіть якщо URL стане відомим, сторінка входу не відкриється. Можна на рівні вебсервера (приклад для nginx нижче) або в самій панелі («Налаштування» → «Обмеження доступу за IP»). Якщо у вас Apache, користуйтеся обмеженням у панелі.

Якщо сайт nginx уже налаштовано за кроком 10, не додавайте другий location / — впишіть рядки allow/deny у вже наявний блок. Два однакові location / в одному server { } — помилка конфігурації, nginx не перезапуститься.
# У конфізі nginx (усередині server { }): # ACME-шлях Let's Encrypt тримаємо відкритим в обхід IP-обмеження — # щоб випуск і автопродовження SSL (крок 15) не залежали від IP-фільтра. location ^~ /.well-known/acme-challenge/ { allow all; } location / { allow 203.0.113.10; # ← впишіть свій IP allow 10.0.0.0/8; # локальна мережа (якщо потрібно) deny all; try_files $uri $uri/ /index.php?$query_string; } # Перезавантажити nginx: sudo nginx -t && sudo systemctl reload nginx

15. Випустити SSL (HTTPS)

Панель працює лише через HTTPS. Сесія входу використовує захищений cookie, а WebAuthn (2FA) працює тільки на HTTPS. Через http:// увійти неможливо.

Сертифікат безкоштовний (Let's Encrypt). DNS домену вже має вказувати на сервер. Команда залежить від вебсервера:

# Apache: sudo certbot --apache -d monitor.example.com # nginx — ТІЛЬКИ якщо у вас саме nginx. На Apache НЕ запускайте: # apt притягне nginx і займе порт 80, конфлікт з Apache. # sudo apt install python3-certbot-nginx # sudo certbot --nginx -d monitor.example.com # certbot сам пропише HTTPS у конфіг і налаштує автопродовження
Що запитає certbot: e-mail → згода з Terms (Y) → передача e-mail до EFF (на ваш розсуд). Потім сам випустить сертифікат, пропише <VirtualHost *:443>, налаштує редирект http→https і автопродовження.
DNS має вказувати на сервер ДО запуску certbot (перевірка володіння через 80-й порт). Перевірка: dig +short monitor.example.com → IP сервера. Порти 80/443 відкриті: sudo ufw allow 80,443/tcp.

Після випуску: https://monitor.example.com відкривається із замком, http:// редиректить на https:// (APP_URL у config.php уже задано в кроці 12).

16. Вхід і початкове налаштування

Відкрийте https://monitor.example.com, увійдіть admin / useradmin і пройдіть чекліст:

  1. Змінити пароль admin — розділ «Користувачі» в меню.
  2. Увімкнути WebAuthn (2FA) — «Ключі WebAuthn» → зареєструвати ключ/passkey (потребує HTTPS). Зареєструйте одразу два: у разі втрати єдиного ключа вхід за ним буде неможливий. Докладніше.
  3. Обмежити доступ за IP — «Налаштування» → «Обмеження доступу за IP» (впишіть свою IP-адресу перед увімкненням, інакше закриєте собі доступ).
  4. Ввести ліцензію — код ARCIVEO-… з кабінету активуйте на свій домен і вставте ключ у «Налаштування» → «Ліцензія». Докладніше.
  5. Налаштувати сповіщення — Telegram та/або Email у «Налаштування». Докладніше.
  6. Видалити інсталятор public/start_db.php, якщо він залишився (крок 11).

17. Інструменти безпеки (опційно)

Панель уже працює. Інструменти встановлюються за бажанням — що потрібно, те й ставите, панель одразу покаже статус. Команди встановлення кожного — у довіднику (окремі розділи по інструментах):

18. Cron і обслуговування

Налаштовується один раз, теж опційно, але рекомендовано. Докладні команди — у довіднику:

  1. Cron-завдання (звіти, оновлення списків, перевірки);
  2. Резервне копіювання;
  3. Оновлення та перенесення панелі;
  4. Відновлення доступу — на випадок втрати ключа/пароля.
Щось не працює або показує «немає даних»? Загляньте до групи «Діагностика» довідника.
Arcivéo - Security Monitor © 2026