Безопасность входных данных пользователя PHP

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

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

Когда я вывожу данные в виде обычного html из базы данных, как лучше всего это сделать, чтобы скрипты и тому подобное не запускались?

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

mysql_real_escape_string(); 

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

И на данный момент я использую

stripslashes(nl2br(htmlentities())) 

(в большинстве случаев) для вывода данных. Я считаю, что они отлично работают для того, для чего я их обычно использую, однако я столкнулся с проблемой с htmlentities, я хочу иметь возможность выводить некоторые теги html соответственно, например:

<ul></ul><li></li><bold></bold> 

д., но я не могу.

любая помощь будет здорово, спасибо.


person Dylan Cross    schedule 09.08.2012    source источник
comment
Вы можете проверить bobby-tables.com   -  person irrelephant    schedule 10.08.2012
comment
Спасибо, но да, я смотрел на это раньше, и это не имеет для меня особого смысла. :\   -  person Dylan Cross    schedule 10.08.2012


Ответы (3)


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

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

В своем вопросе вы упоминаете два вида проблем с безопасностью. Во-первых, это SQL-инъекция. Эта уязвимость является «решенной проблемой». То есть, если вы используете параметризованные запросы и никогда не передаете предоставленные пользователем данные как что-либо, кроме параметра, база данных будет делать «правильные вещи» для вас, что бы ни случилось. Для многих баз данных, если вы используете параметризованные запросы, нет возможности внедрения, потому что данные фактически не отправляются встроенными в SQL — данные передаются без экранирования в префиксе длины или подобном большом двоичном объекте по сети. Это значительно более эффективно, чем функции выхода из базы данных, и может быть безопаснее. (Примечание: если вы используете хранимые процедуры, которые генерируют динамический SQL в базе данных, у них также могут быть проблемы с внедрением!)

Вторая проблема, которую вы упомянули, — это проблема межсайтового скриптинга. Если вы хотите разрешить пользователю предоставлять HTML без предварительного экранирования объекта, эта проблема является открытым вопросом исследования. Достаточно сказать, что если вы разрешаете пользователю передавать некоторые виды HTML, вполне вероятно, что ваша система в какой-то момент столкнется с проблемой XSS для решительного злоумышленника. В настоящее время современным решением этой проблемы является «фильтрация» данных на сервере с использованием таких библиотек, как HTMLPurifier. Злоумышленники могут регулярно взламывать эти фильтры; но пока никто не нашел лучшего способа защитить приложение от подобных вещей. Возможно, вам будет лучше разрешить только определенный белый список HTML-тегов и кодирование всего остального.

person Billy ONeal    schedule 10.08.2012

Это одна из самых проблемных задач на сегодняшний день :)

Вам нужно знать, как работают SQL-инъекции и другие методы злоумышленников. Очень подробное объяснение каждого метода есть в https://www.owasp.org/index.php/Main_Page, а также вся система безопасности для PHP.

Использование определенных библиотек безопасности из некоторых фреймворков также является хорошим выбором, например, в CodeIgniter или Zend.

Затем используйте REGEXP настолько часто, насколько это возможно, и придерживайтесь шаблонных правил для определенного формата ввода.

Используйте подготовленные операторы или класс активных записей вашего фреймворка.

Всегда вводите ввод с помощью (int)$_GET['myvar'], если вам действительно нужны числовые значения.

Существует так много других правил и методов для защиты вашего приложения, но есть одно золотое правило: «никогда не доверяйте вводу пользователя».

person mikikg    schedule 10.08.2012
comment
Нет! Не проверяйте пользовательский ввод с помощью регулярных выражений в качестве средства предотвращения SQL-инъекций. Люди найдут способы сломать ваши фильтры или использовать ошибки в механизмах регулярных выражений. Используйте экранирование (фу) или параметризованные запросы (ура), чтобы предотвратить такого рода атаки; это то, для чего они предназначены. Обратите внимание, что вы не ответили на XSS-часть вопроса пользователя. - person Billy ONeal; 10.08.2012

В вашей конфигурации php параметр magic_quotes_gpc должен быть отключен. Так что stripslashes вам не понадобится.

Для SQL взгляните на подготовленные операторы PDO.

А для ваших пользовательских тегов, поскольку их всего три, вы можете выполнить вызов preg_replace после вызова htmlentities, чтобы преобразовать их обратно, прежде чем вставлять их в базу данных.

person Jill-Jênn Vie    schedule 10.08.2012
comment
Спасибо за ваш ответ, что касается magic_quotes_gpc и stripslashes, мне нужны stripslashes, потому что я использую jQuery Serialize при отправке своих форм, так что, очевидно, это делает то же самое, что и magic_quotes. - person Dylan Cross; 10.08.2012
comment
@Dylan: Тогда вы должны сделать stripslashes до того, как данные попадут в базу данных. К содержимому в базе данных никогда не должны применяться соображения уровня представления (например, полосы косой черты) — вы никогда не знаете, собираетесь ли вы использовать те же данные в чем-то, что не является HTML-страницей где-то в будущем, и пытаетесь сделать это везде болит шея. - person Billy ONeal; 10.08.2012