Настройка безопасности MySQL

Настройки сервера

Начнем с глобальных настроек. В случае, если Web и MySQL сервера работают на одном компьютере (что обычно для небольших проектов), то имеет смысл заставить MySQL слушать (bind-address) только интерфейс локальной петли (127.0.0.1), или вообще работать через Unix сокеты(socket).
Это исключит возможность соединения с MySQL сервером потенциального злоумышленника. В случае, если MySQL-сервер и Web-сервер находятся на разных машинах, придется производить настройку брандмауэра, что мы не будем рассматривать в рамках этой статьи.
Также можно изменить стандартный порт соединения с MySQL сервером (port,в случае работы через TCP/IP) - это не сильно поможет против злоумышленника, который задался целью взлома, но очень затруднит работу всякого рода ботам.

bind-address = 127.0.0.1
socket = /var/run/mysqld/mysql.sock
port = 3307

Также следует упомянуть параметры, которые не относятся напрямую к MySQL серверу, но влияют на возможность соединения с ним PHP скриптов. Речь о параметрах default_host, default_user и default_password секции [MySQL] конфигурационного файла PHP (php.ini). Эти опции задают параметры по умолчанию для соединения скриптов с MySQL сервером. Т.е. при использовании этих опций, любой PHP скрипт сможет соединиться с базой данных без указания имени пользователя и пароля. Поэтому использовать эти параметры не рекомендуется.

Теперь перейдем к привилегиям базы данных

Установка привилегий базы данных

Доступ пользователей к базам данных MySQL сервера регламентируется привилегиями разного уровня. Информация о привилегиях хранится в базе данных mysql, в таблицах user, db, host, а также tables_priv и columns_priv.
Таблица user отвечает за пользователей и их глобальные привилегии (распространяются на все таблицы всех баз данных). Клиент (соединяющийся с БД пользователь) определяется полями Host (адрес узла клиента) и User(имя пользователя), т.е. для клиента с одним и тем же именем могут быть разные пароли и разные привилегии, в зависимости от того, с какого узла клиент соединяется с сервером баз данных. Можно также указать возможность соединения с любого хоста, но такого лучше не делать из соображений безопасности. Для каждой пары Host + User устанавливается пароль, хранящийся в поле Password в зашифрованном виде. Оставшиеся поля данной таблицы отвечают за предоставленные клиенту привилегии и доступные ресурсы сервера.

# Создание пользователя test_user для локального соединения с паролем test_passw
CREATE USER "test_user"@"localhost" IDENTIFIED BY "test_passw";
# Предоставление созданному пользователю глобальных привилегий на выборку,
# вставку, обновление и неограниченное количество ресурсов сервера
GRANT SELECT, INSERT, UPDATE ON * . * TO "test_user"@"localhost" 
    IDENTIFIED BY "test_passw" WITH MAX_QUERIES_PER_HOUR 0 MAX_CONNECTIONS_PER_HOUR 0
    MAX_UPDATES_PER_HOUR 0 MAX_USER_CONNECTIONS 0;

Таблица db отвечает за привилегии пользователей по отношению к различным базам данных. Структура таблицы db практически идентична таблице user, отсутствует описание количества доступных ресурсов и поле пароля. Вместо этого есть поле Db, которое задает имя базы данных, для которой описываются привилегии. Каждый пользователь должен иметь доступ из минимально необходимого набора привилегий и только к тем базам, которые ему необходимы для работы.

# предоставление нашему пользователю test_user прав на выборку из БД test_db
GRANT SELECT ON `test_db`.* TO "test_user"@"localhost";

Таблица host задает задает права доступа для различных хостов к базе. Таблица по структуре похожа на вышеописанные.
И наконец, таблицы tables_priv и columns_priv отвечают за доступ к конкретной таблице базы или конкретному столбцу таблицы соответственно.

# предоставление пользователю прав на чтение столбцов col_1, col_1 
# из таблицы test_table базы данных test_db
GRANT SELECT (`col_1`, `col_2`) ON `test_db`.`test_table` TO "test_user"@"localhost"

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

Итак, подведем итоги.

- Никогда не используем настройки сервера по умолчанию (доходит до того, что некоторые инсталляции по умолчанию имеют пустой root пароль к серверу)
- Не устанавливаем параметры соединения с сервером в конфигурационных файлах PHP
- Никогда не используем пользователей с высоким уровнем привилегий в ваших скриптах, а тем более пользователя root
- Не позволяем (или сильно ограничиваем) возможность удаленного подключения к базе данных
- Для каждой базы создаем своего пользователя, который не имеет прав доступа к другим базам данных
- Разграничиваем пользователей, имеющих права на модификацию данных (INSERT, UPDATE, DELETE) и только на выборку (SELECT)
- У вас не должно быть пользователей, имеющих привилегии на работу со структурой базы данных или административных привилегий
- Соблюдение всех этих правил и рекомендаций не являются панацеей в плане безопасности, но позволяют в разы уменьшить уязвимость любого проекта.

URL: https://visavi.net/articles/348