Являются ли очистка ввода и параметризованные запросы взаимоисключающими?

Я работаю над обновлением устаревшего кода, который неправильно обрабатывает пользовательский ввод. Код выполняет минимальную дезинфекцию, но не охватывает все известные угрозы.

Наш новый код использует параметризованные запросы. Насколько я понимаю, запросы предварительно компилируются, а ввод обрабатывается просто как данные, которые не могут быть выполнены. В этом случае санитарная обработка не требуется. Это правильно?

Иными словами, если я параметризую запросы в этом унаследованном коде, можно ли исключить очистку, которую он выполняет в настоящее время? Или я упускаю какое-то дополнительное преимущество дезинфекции помимо параметризации?


person Bruce Alderman    schedule 25.06.2010    source источник


Ответы (6)


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

Но некоторые компоненты SQL-запросов не могут быть параметризованы. Например. имена таблиц, имена столбцов, ключевые слова SQL.

$sql = "SELECT * FROM MyTable ORDER BY {$columnname} {$ASC_or_DESC}";

Таким образом, есть несколько примеров динамического содержимого, которое вам может потребоваться проверить перед интерполяцией в SQL-запрос. Внесение значений в белый список также является хорошей техникой.

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

  • Предположим, вы храните номер кредитной карты. Существуют допустимые шаблоны для номеров кредитных карт и библиотеки для распознавания действительных номеров от недействительных.

  • Или как насчет того, когда пользователь определяет свой пароль? Вы можете захотеть обеспечить достаточную надежность пароля или убедиться, что пользователь ввел одну и ту же строку в два поля ввода пароля.

  • Или, если они заказывают определенное количество товаров, вам может потребоваться сохранить количество как целое число, но вы должны убедиться, что оно больше нуля, и, возможно, если оно больше 1000, вы захотите перепроверить у пользователя, что они правильно ввели.

person Bill Karwin    schedule 25.06.2010
comment
я надеюсь, что эти $columnname и $ASC_OR_DESC не исходят от пользователя! это должны быть жесткие константы в вашем коде, и сделайте полную проверку пути данных от константы через переменную до SQL, чтобы убедиться, что это одна из ваших переменных. (проще, если этот путь очень короткий, поэтому это только параметр на очень низком уровне, на более высоком уровне это должны быть разные вызовы функций без какого-либо параметра, который заканчивался бы кодом SQL) - person Javier; 25.06.2010
comment
@Javier: Разве это не обычная функция пользовательского интерфейса, позволяющая пользователю щелкнуть заголовок столбца для сортировки по этому столбцу? Но да, вы хотели бы проверить, соответствует ли ввод пользовательского интерфейса имени столбца, используя белый список или какую-либо карту. Значение в пользовательском интерфейсе даже не обязательно должно быть буквальным именем столбца, это может быть значение, которое ваш код может связать с записью в списке допустимых имен столбцов. - person Bill Karwin; 25.06.2010

Параметризованные запросы помогут предотвратить SQL-инъекции, но они бесполезны против межсайтовых сценариев. Вам нужны другие меры, такие как кодирование HTML или обнаружение/проверка HTML, чтобы предотвратить это. Если все, что вам нужно, это SQL-инъекция, вероятно, будет достаточно параметризованных запросов.

person tvanfosson    schedule 25.06.2010

Существует много разных причин для очистки и проверки, в том числе предотвращение межсайтовых сценариев и простое желание получить правильное содержимое для поля (без имен в телефонных номерах). Параметризованные запросы устраняют необходимость ручной очистки или защиты от SQL-инъекций.

См. один из мои предыдущие ответы по этому поводу.

person Matthew Flaschen    schedule 25.06.2010
comment
Другими словами, санация все же может быть полезна по другим причинам, не связанным с SQL-инъекциями? - person Bruce Alderman; 25.06.2010

Вы правы, параметры SQL не являются исполняемым кодом, поэтому вам не нужно об этом беспокоиться.

Тем не менее, вы все равно должны сделать небольшую проверку. Например, если вы ожидаете varchar(10), а пользователь вводит что-то более длинное, вы получите исключение.

person Hugo Migneron    schedule 25.06.2010

Короче нет. Очистка ввода и использование параметризованных запросов не исключают друг друга, они независимы: вы можете не использовать ни то, ни другое по отдельности, или оба. Они предотвращают различные типы атак. Использование обоих - лучший курс.

person Stephen C. Steel    schedule 25.06.2010

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

person Yellowfog    schedule 25.06.2010