:: DEVELOPER ZONE
С данным разделом должны ознакомиться все, кто использует MySQL на компьютерах, подключенных к Internet, - чтобы избежать наиболее распространенных ошибок, приводящих к нарушению безопасности системы.
При обсуждении вопросов безопасности мы акцентируем внимание на необходимости защиты всего серверного хоста (а не одного лишь сервера MySQL) от всех возможных типов атак: перехвата, внесения изменений, считывания и отказа в обслуживании. Данный раздел не охватывает всех аспектов готовности к работе и отказоустойчивости.
Используемая в MySQL система безопасности для всех подключений, запросов и иных операций, которые может пытаться выполнить пользователь, базируется на списках контроля доступа ACLs (Access Control Lists). Обеспечивается также некоторая поддержка SSL-соединений между клиентами и серверами MySQL. Многие из рассматриваемых здесь концепций не относятся исключительно к MySQL; те же общие соображения применимы практически ко всем приложениям.
При работе в MySQL старайтесь следовать приведенным ниже инструкциям:
Не предоставляйте никому (за исключением пользователя mysql
под именем root
) доступа к таблице user
в базе данных mysql
! Это чрезвычайно важно. В MySQL зашифрованный пароль является реальным паролем. Узнав
пароль, занесенный в таблицу user
, и имея доступ к удаленному
компьютеру, занесенному в соответствующую учетную запись, войти в систему под именем зарегистрированного владельца пароля легко может кто угодно.
Изучите систему прав доступа MySQL. Для управления доступом к MySQL
служат команды GRANT
и REVOKE
. Предоставляйте ровно столько прав,
сколько необходимо, и не больше. Никогда не предоставляйте права всем
хостам. Полезно проводить следующие контрольные проверки:
Выполните команду mysql -u root
. Если удается успешно установить
соединение с сервером без получения запроса пароля, значит, у вас
имеются проблемы. Это означает, что кто угодно может
подсоединиться к вашему серверу MySQL как клиент MySQL под именем
root
, получая таким образом право неограниченного доступа!
Проанализируйте инструкцию по инсталляции MySQL, обращая особое
внимание на ту часть, которая касается задания пароля
пользователя root
.
С помощью команды SHOW GRANTS
проверьте, кто и к каким ресурсам
имеет доступ. Воспользуйтесь командой REVOKE
, отмените права
доступа, которые не являются необходимыми.
Не храните в базе данных незашифрованных паролей. Если злоумышленнику
удастся получить доступ на ваш компьютер, то в его руках окажется
полный список паролей, которыми он может воспользоваться. Применяйте
для шифрования MD5()
, SHA1()
или другие односторонние хеш-функции.
Не используйте в качестве пароля слова из словарей. Для взлома такого рода паролей имеются специальные программы. Даже слова типа ``xfish98'' - это очень плохие пароли. Куда лучше ``duag98'': здесь используется то же слово ``fish'', но при этом буквы в нем заменены ближайшими к ним слева буквами клавиатуры QWERTY. Еще один метод - составить парольное слово из первых букв слов какого либо словосочетания, например ``Mhall'' - по фразе ``Mary had a little lamb.'' Такой пароль легко запоминается и его легко вводить. А вот разгадать его тому, кто не знает ключевой фразы, будет непросто.
Приобретите брандмауэр. Эта мера обеспечит защиту как минимум от половины всех видов несанкционированного использования любого ПО, с которым вы работаете. Разместите MySQL за брандмауэром или в демилитаризованной зоне (demilitarised zone - DMZ). Полезно проводить следующие контрольные проверки:
Попробуйте просканировать ваши порты из Internet с помощью
утилиты типа nmap
. MySQL использует по умолчанию порт 3306. Этот
порт должен быть недоступен с неблагонадежных компьютеров. Еще
один простой способ проверить, открыт или нет ваш MySQL-порт, -
попытаться выполнить с какой либо удаленной машины следующую
команду, где server_host
- имя хоста, на котором установлен ваш
сервер MySQL:
shell> telnet server_host 3306
Если соединение будет установлено, и вы получите какие-либо бессмысленные
символы, это будет означать, что порт открыт, и его нужно закрыть на
брандмауэре или маршрутизаторе (если, конечно, нет действительно веских
причин держать его открытым). Если же telnet
просто зависнет или в
подсоединении будет отказано, тогда все в порядке: порт заблокирован.
Не доверяйте никаким данным, которые вводят пользователи. Возможны
попытки перехитрить вашу программу путем ввода последовательностей
специальных или экранированных символов в веб-формы, URL-ы или любое
приложение, созданное вами. Убедитесь, что защита вашего приложения не
будет нарушена, если пользователь введет что-нибудь типа "'; DROP DATABASE mysql;
''. Это крайний случай, но действия хакеров,
использующих подобную технологию, могут привести к потере информации и
появлению брешей в системе безопасности, если вы не готовы к ним. Не
следует также забывать о необходимости проверки цифровых данных
(распространенной ошибкой является защита только строк). Некоторые
полагают, что если в базе данных хранятся только открытые данные, то в
ее защите нет необходимости. Это неверно. Такие базы могут стать
объектом успешных атак типа отказа от обслуживания. Простейший способ
защиты от взломов такого типа - заключать числовые константы в
кавычки: SELECT * FROM table WHERE ID='234'
, а не SELECT * FROM table WHERE ID=23
4. MySQL автоматически преобразует эту строку в число и
выбросит из нее все нецифровые символы. Полезно проводить следующие
контрольные проверки:
Для всех веб-приложений:
Попробуйте ввести во все ваши веб-формы одинарные и двойные
кавычки - ''
' и '"
'. Если MySQL выдаст любое сообщение об
ошибке, немедленно разберитесь, в чем дело.
Попробуйте видоизменять динамические URL, добавляя в них %22
('"
'), %23
('#
'), и %27
(''
').
Попробуйте модифицировать типы данных в динамических URL - замените числовые на символьные, используя символы из предыдущих примеров. Ваше приложение должно быть устойчиво к подобного рода атакам.
Попробуйте вводить в числовые поля вместо цифр буквы, пробелы и специальные символы. Ваше приложение должно либо удалять их до передачи в MySQL, либо выдавать сообщение об ошибке. Пропускать в MySQL значения без проверки очень опасно!
Проверяйте размер данных перед тем, как они будут переданы в MySQL.
При подключении приложения к базе данных лучше использовать имя пользователя, отличное от того, которое вы используете для целей администрирования. Не предоставляйте своим приложениям больше прав доступа, чем это необходимо.
Пользователям PHP:
Проверьте функцию addslashes()
. Что касается PHP 4.0.3, то в
нем имеется функция mysql_escape_string()
, базирующаяся на
функции с тем же именем из MySQL C API.
Пользователям MySQL C API:
Проверьте API-вызов mysql_real_escape_string()
.
Пользователям MySQL++:
Проверьте такие модификаторы, как escape
и quote
, - для
потоков запросов.
Пользователям Perl DBI:
Проверьте метод quote()
или используйте для проверки
заполнители.
Пользователям Java JDBC:
Используйте для проверки объект PreparedStatement
и
символы-заполнители.
Не передавайте по Internet открытые (незашифрованные) данные. Они могут оказаться у кого угодно, имеющего достаточно времени и возможностей для того, чтобы перехватить их и использовать в своих целях. Используйте вместо этого протоколы с шифрованием данных, такие как SSL и SSH. MySQL, начиная с версии 4.0.0, поддерживает собственные SSL-соединения. Пересылка по SSH (SSH Port Forwarding) может быть использована для создания туннеля передачи данных с шифрованием и сжатием.
Научитесь пользоваться утилитами tcpdump
и strings
. В большинстве
случаев проверить, являются ли потоки данных MySQL зашифрованными,
можно с помощью команды, подобной той, которая приведена ниже:
shell> tcpdump -l -i eth0 -w - src or dst port 3306 | strings
(Она работает под Linux, и будет, с незначительными изменениями, работать под другими системами.) Предупреждение: если вы не видите данных, это еще не гарантирует того, что они зашифрованы. Если требуется высокий уровень безопасности, обратитесь к экспертам в этой области.
© 1995-2005 MySQL AB. All rights reserved.