Что мне нужно экранировать при отправке запроса?
Вопрос
Когда вы выполняете запрос SQL, вам необходимо очистить строки, иначе пользователи могут выполнить вредоносный SQL на вашем веб-сайте.
Обычно у меня есть функция escape_string(blah), которая:
- Заменяет escape-коды (
\
) с двойными побегами (\\
). - Заменяет одинарные кавычки (
'
) с экранированной одинарной кавычкой (\'
).
Это адекватно?Есть ли дыра в моем коде?Есть ли библиотека, которая может сделать это быстро и надежно?
Мне бы хотелось увидеть изящные решения на Perl, Java и PHP.
Решение
Для максимальной безопасности, производительности и корректности используйте подготовленные операторы.Вот как это сделать, используя множество примеров на разных языках, включая PHP:
https://stackoverflow.com/questions/1973/what-is-the-best-way-to-avoid-sql-injection-attacks
Другие советы
Я бы также избегал комментариев (двойное тире)
--
Замечательная вещь для использования в PHP — это ПДО.Чтобы обеспечить безопасность вашего SQL (и всего вашего SQL-материала в целом), требуется много догадок.Он поддерживает подготовленные операторы, которые во многом помогают предотвратить атаки с использованием SQL-инъекций.
В книгу включен отличный учебник по PDO. Антология PHP: 101 важный совет, хитрость и хитрость от Дэйви Шафика и др.2-е изд..Упрощает обучение и отлично подходит в качестве справочного материала.Мне даже не нужно больше думать ни о чем, кроме самого SQL-запроса.
Какой язык используете?Кажется, что почти все они имеют встроенные escape-функции SQL, которые лучше использовать.
Например, PHP имеет mysql_real_escape_string и добавляет косую черту.
Лучше использовать подготовленные операторы с заполнителями.Используете ли вы PHP, .NET... в любом случае подготовленные операторы обеспечат большую безопасность, но я мог бы предоставить образец.
В PHP я использую этот вариант и буду признателен за каждый комментарий по этому поводу:
function quote_smart($valeur)
{
if (get_magic_quotes_gpc())
$valeur = stripslashes($valeur);
if (!is_numeric($valeur))
$valeur = mysql_real_escape_string($valeur);
return $valeur;
}
$IdS = quote_smart($_POST['theID']);
$sql = "
SELECT * FROM Students
WHERE IdStudent={$IdS};
";
Требуется еще одна проверка, если поле может иметь значение NULL:
$picture = NULL;
$theidyouwant = 7;
$Name = 'WOOD';
if(is_null($picture))
$p = 'NULL';
else
$p = "'".quote_smart($picture)."'";
$IdS = quote_smart($theidyouwant);
$requete = "SELECT * FROM Students
WHERE IdStudent={$IdS} AND
PictureStudent={$p} AND
NameStudent='{$Name}';
";
Вот и все, наслаждайтесь!(надеюсь, в сообщении будет правильно отправлено подчеркивание, а не _)
Используйте подготовленные/параметризованные запросы!
Используйте подготовленные утверждения.
В запросе MySQL при использовании LIKE также обязательно экранируйте символы «_», поскольку они не экранируются mysql_real_escape_string.
Для справки проверьте здесь
MySQL C API имеет свой собственный mysql_escape_string()
.Лучше всего использовать его или его эквивалент.
Я не уверен, поддерживает ли MySql параметризованные запросы, если да, то вам следует попытаться пойти по этому пути.Это гарантирует, что вводимые пользователем данные не смогут сделать ничего вредоносного.
В противном случае некоторыми «плохими» символами в дополнение к тем, что вы упомянули, будут точка с запятой (;) и комментарии (-- и /* */).