Home » Как защитить базы данных MySQL и MariaDB на VPS с Linux
Как защитить базы данных MySQL и MariaDB на VPS с Linux

Как защитить базы данных MySQL и MariaDB на VPS с Linux

Если вы работаете с веб-приложениями или любыми проектами, которые требуют хранения данных, то вопрос безопасности баз данных стоит остро. MySQL и MariaDB — это те решения, которые крутятся практически везде, от небольших блогов до крупных корпоративных порталов. Но по умолчанию они настроены не самым безопасным образом, и если не принять соответствующие меры, можно получить серьезные проблемы — от утечки данных до полного компрометирования сервера.

В этой статье мы разберем, как правильно защитить MySQL и MariaDB на VPS с Linux. Рассмотрим базовые и продвинутые методы защиты, настройки файрвола, аудита, бэкапов и мониторинга. Все примеры будут с реальными командами и конфигурациями, которые можно сразу применять в продакшене.

Как работает безопасность баз данных

Прежде чем погружаться в настройки, важно понимать основные векторы атак на базы данных:

  • Слабые пароли и учетные записи — самая частая причина взломов
  • SQL-инъекции — атаки через веб-приложения
  • Открытые порты — когда БД доступна извне без необходимости
  • Отсутствие шифрования — данные передаются в открытом виде
  • Логирование и мониторинг — никто не отслеживает подозрительную активность
  • Старые версии ПО — неустраненные уязвимости

Базовая настройка безопасности

Начнем с основ. Если у вас еще нет VPS, можете заказать VPS здесь или взять выделенный сервер для более серьезных нагрузок.

Установка и первоначальная настройка

После установки MySQL/MariaDB первым делом запускаем скрипт безопасности:

sudo mysql_secure_installation

Этот скрипт поможет:

  • Установить пароль для root
  • Удалить анонимные учетные записи
  • Запретить удаленный доступ для root
  • Удалить тестовую базу данных
  • Перезагрузить таблицы привилегий

Настройка конфигурационного файла

Редактируем основной конфиг (/etc/mysql/mysql.conf.d/mysqld.cnf для MySQL или /etc/mysql/mariadb.conf.d/50-server.cnf для MariaDB):

[mysqld]
# Привязка только к localhost
bind-address = 127.0.0.1

# Отключение загрузки локальных файлов
local-infile = 0

# Отключение символических ссылок
symbolic-links = 0

# Ограничение размера пакетов
max_allowed_packet = 16M

# Таймаут для неактивных соединений
wait_timeout = 600
interactive_timeout = 600

# Логирование медленных запросов
slow_query_log = 1
slow_query_log_file = /var/log/mysql/slow.log
long_query_time = 2

# Общий лог запросов (осторожно, много места!)
# general_log = 1
# general_log_file = /var/log/mysql/general.log

После изменений перезапускаем службу:

sudo systemctl restart mysql
# или для MariaDB
sudo systemctl restart mariadb

Управление пользователями и привилегиями

Никогда не используйте root-пользователя для приложений. Создавайте отдельные учетные записи с минимальными правами:

# Входим в MySQL
sudo mysql -u root -p

# Создаем пользователя для приложения
CREATE USER 'appuser'@'localhost' IDENTIFIED BY 'SuperSecurePassword123!';

# Создаем базу данных
CREATE DATABASE myapp_db;

# Даем права только на нужную базу
GRANT SELECT, INSERT, UPDATE, DELETE ON myapp_db.* TO 'appuser'@'localhost';

# Применяем изменения
FLUSH PRIVILEGES;

# Проверяем права
SHOW GRANTS FOR 'appuser'@'localhost';

Таблица рекомендуемых привилегий

Тип приложения Рекомендуемые привилегии Комментарий
Web-приложение SELECT, INSERT, UPDATE, DELETE Базовые операции CRUD
Система отчетов SELECT Только чтение данных
Миграции CREATE, ALTER, DROP, INDEX Структурные изменения
Бэкапы SELECT, LOCK TABLES Для mysqldump

Настройка файрвола

Если база данных используется только локально, блокируем внешние подключения:

# UFW (Ubuntu/Debian)
sudo ufw deny 3306
sudo ufw deny 3307

# Или для конкретного IP, если нужен удаленный доступ
sudo ufw allow from 192.168.1.100 to any port 3306

# iptables
sudo iptables -A INPUT -p tcp --dport 3306 -j DROP
sudo iptables -A INPUT -p tcp --dport 3306 -s 192.168.1.100 -j ACCEPT

# Сохраняем правила
sudo iptables-save > /etc/iptables/rules.v4

Включение SSL/TLS шифрования

Для защиты данных в transit настраиваем SSL:

# Генерируем сертификаты
sudo mysql_ssl_rsa_setup --uid=mysql

# Проверяем поддержку SSL
mysql -u root -p -e "SHOW VARIABLES LIKE '%ssl%';"

Обязательное использование SSL для пользователей:

# Создаем пользователя с требованием SSL
CREATE USER 'secureuser'@'%' IDENTIFIED BY 'password' REQUIRE SSL;

# Или изменяем существующего
ALTER USER 'appuser'@'localhost' REQUIRE SSL;

Аудит и мониторинг

Включаем аудит для отслеживания подозрительной активности:

# Для MariaDB устанавливаем аудит-плагин
INSTALL PLUGIN server_audit SONAME 'server_audit.so';

# Настраиваем параметры аудита
SET GLOBAL server_audit_logging=ON;
SET GLOBAL server_audit_events='CONNECT,QUERY,TABLE';
SET GLOBAL server_audit_file_path='/var/log/mysql/audit.log';

Для MySQL Enterprise доступен MySQL Enterprise Audit, но для Community версии можно использовать McAfee MySQL Audit Plugin.

Настройка ротации логов

Создаем конфиг для logrotate (/etc/logrotate.d/mysql-audit):

/var/log/mysql/audit.log {
    daily
    rotate 30
    compress
    missingok
    notifempty
    create 640 mysql mysql
    postrotate
        /bin/kill -HUP `cat /var/run/mysqld/mysqld.pid 2>/dev/null` 2>/dev/null || true
    endscript
}

Бэкапы и восстановление

Автоматизируем создание бэкапов:

#!/bin/bash
# /opt/mysql-backup.sh

BACKUP_DIR="/backup/mysql"
DATE=$(date +"%Y%m%d_%H%M%S")
MYSQL_USER="backupuser"
MYSQL_PASS="BackupPassword123!"
DATABASES="myapp_db"

mkdir -p $BACKUP_DIR

for DB in $DATABASES; do
    mysqldump -u$MYSQL_USER -p$MYSQL_PASS \
        --single-transaction \
        --routines \
        --triggers \
        --events \
        $DB > $BACKUP_DIR/${DB}_${DATE}.sql
    
    # Сжимаем бэкап
    gzip $BACKUP_DIR/${DB}_${DATE}.sql
done

# Удаляем старые бэкапы (старше 7 дней)
find $BACKUP_DIR -name "*.sql.gz" -mtime +7 -delete

Добавляем в cron:

# Ежедневный бэкап в 2:00
0 2 * * * /opt/mysql-backup.sh

Защита от SQL-инъекций на уровне БД

Помимо защиты в приложении, можно настроить дополнительную защиту в MySQL:

# Ограничиваем количество одновременных подключений
CREATE USER 'webapp'@'localhost' IDENTIFIED BY 'password'
WITH MAX_CONNECTIONS_PER_HOUR 1000
MAX_QUERIES_PER_HOUR 10000
MAX_USER_CONNECTIONS 10;

# Включаем SQL_MODE для строгой проверки
SET GLOBAL sql_mode = 'STRICT_TRANS_TABLES,NO_ZERO_DATE,NO_ZERO_IN_DATE,ERROR_FOR_DIVISION_BY_ZERO';

Мониторинг производительности и безопасности

Создаем скрипт мониторинга:

#!/bin/bash
# /opt/mysql-monitor.sh

# Проверка подозрительных соединений
mysql -u root -p -e "SELECT USER, HOST, DB, COMMAND, TIME, STATE, INFO FROM INFORMATION_SCHEMA.PROCESSLIST WHERE COMMAND != 'Sleep' AND TIME > 60;"

# Проверка неудачных попыток входа
tail -n 100 /var/log/mysql/error.log | grep -i "access denied"

# Проверка медленных запросов
mysql -u root -p -e "SELECT * FROM mysql.slow_log ORDER BY start_time DESC LIMIT 10;"

Дополнительные инструменты безопасности

Fail2ban для MySQL

Настраиваем защиту от брутфорса:

# /etc/fail2ban/jail.local
[mysqld-auth]
enabled = true
filter = mysqld-auth
port = 3306
logpath = /var/log/mysql/error.log
maxretry = 3
bantime = 3600

Создаем фильтр (/etc/fail2ban/filter.d/mysqld-auth.conf):

[Definition]
failregex = ^%(__prefix_line)s.*\[ERROR\] Access denied for user.*.*$
ignoreregex =

Использование AppArmor/SELinux

Для Ubuntu/Debian с AppArmor:

# Проверяем статус профиля MySQL
sudo aa-status | grep mysql

# Переводим в режим enforce
sudo aa-enforce /etc/apparmor.d/usr.sbin.mysqld

Тестирование безопасности

Регулярно тестируем конфигурацию:

# Сканирование портов
nmap -p 3306 localhost

# Проверка SSL
mysql -u root -p -e "SHOW STATUS LIKE 'Ssl_cipher';"

# Тест подключения без SSL (должен быть запрещен)
mysql -u secureuser -p --ssl-mode=DISABLED

Сравнение инструментов безопасности

Инструмент Функциональность Сложность настройки Производительность
MySQL Enterprise Audit Полный аудит Низкая Высокая
MariaDB Audit Plugin Базовый аудит Средняя Высокая
Fail2ban Защита от брутфорса Средняя Минимальное влияние
AppArmor/SELinux Системная защита Высокая Минимальное влияние

Автоматизация и скрипты

Создаем комплексный скрипт проверки безопасности:

#!/bin/bash
# /opt/mysql-security-check.sh

echo "=== MySQL Security Check ==="

# Проверка версии
mysql -V

# Проверка пользователей без пароля
mysql -u root -p -e "SELECT User, Host FROM mysql.user WHERE authentication_string = '';"

# Проверка пользователей с административными правами
mysql -u root -p -e "SELECT User, Host FROM mysql.user WHERE Super_priv = 'Y';"

# Проверка SSL
mysql -u root -p -e "SHOW VARIABLES LIKE '%ssl%';"

# Проверка логирования
mysql -u root -p -e "SHOW VARIABLES LIKE '%log%';"

# Проверка сетевых настроек
mysql -u root -p -e "SHOW VARIABLES LIKE 'bind_address';"

echo "=== Security Check Complete ==="

Интересные факты и нестандартные решения

Несколько полезных трюков для продвинутых пользователей:

  • Honeypot-пользователи — создавайте пользователей-приманки для отслеживания атак
  • Использование ProxySQL для дополнительной защиты и балансировки нагрузки
  • Шифрование данных в покое — используйте InnoDB encryption для критичных данных
  • Настройка MySQL в Docker с дополнительными мерами безопасности

Пример настройки InnoDB encryption

# В конфигурации MySQL
[mysqld]
default_table_encryption=ON
innodb_encrypt_tables=ON
innodb_encryption_threads=4

# Создание keyring
early-plugin-load=keyring_file.so
keyring_file_data=/var/lib/mysql-keyring/keyring

Заключение и рекомендации

Безопасность баз данных — это не разовая настройка, а постоянный процесс. Основные принципы, которые стоит соблюдать:

  • Минимизация привилегий — давайте пользователям только те права, которые действительно нужны
  • Регулярные обновления — следите за выходом патчей безопасности
  • Мониторинг — настройте систему алертов для подозрительной активности
  • Бэкапы — регулярно создавайте и проверяйте резервные копии
  • Документирование — ведите документацию по всем изменениям

Помните, что безопасность — это баланс между защитой и удобством использования. Не стоит перегибать палку и усложнять систему до состояния, когда с ней невозможно работать. Начните с базовых настроек, описанных в этой статье, а затем постепенно добавляйте более сложные меры защиты по мере необходимости.

Для серьезных проектов рекомендую также рассмотреть возможность использования выделенных серверов вместо VPS — это даст дополнительный уровень изоляции и контроля над инфраструктурой.

Удачи в настройке безопасности ваших баз данных!


В этой статье собрана информация и материалы из различных интернет-источников. Мы признаем и ценим работу всех оригинальных авторов, издателей и веб-сайтов. Несмотря на то, что были приложены все усилия для надлежащего указания исходного материала, любая непреднамеренная оплошность или упущение не являются нарушением авторских прав. Все упомянутые товарные знаки, логотипы и изображения являются собственностью соответствующих владельцев. Если вы считаете, что какой-либо контент, использованный в этой статье, нарушает ваши авторские права, немедленно свяжитесь с нами для рассмотрения и принятия оперативных мер.

Данная статья предназначена исключительно для ознакомительных и образовательных целей и не ущемляет права правообладателей. Если какой-либо материал, защищенный авторским правом, был использован без должного упоминания или с нарушением законов об авторском праве, это непреднамеренно, и мы исправим это незамедлительно после уведомления. Обратите внимание, что переиздание, распространение или воспроизведение части или всего содержимого в любой форме запрещено без письменного разрешения автора и владельца веб-сайта. Для получения разрешений или дополнительных запросов, пожалуйста, свяжитесь с нами.

Leave a reply

Your email address will not be published. Required fields are marked