Предотвращение атак CSRF, XSS и SQL-инъекций в JSF - PullRequest
53 голосов
/ 11 октября 2011

У меня есть веб-приложение, построенное на JSF с MySQL в качестве БД.Я уже реализовал код для предотвращения CSRF в своем приложении.

Теперь, поскольку моя базовая структура - JSF, я думаю, мне не нужно обрабатывать XSS-атаку, поскольку она уже обрабатывается UIComponent.Я не использую JavaScript ни на одной из страниц просмотра.Даже если я использую, действительно ли мне нужно реализовать код для предотвращения XSS-атак?

Для БД мы используем подготовленные операторы и хранимые процедуры во всех взаимодействиях с БД.обрабатывается для предотвращения этих 3 распространенных атак?Я уже прошел через сайт OWASP и их шпаргалки .

Нужно ли мне позаботиться о любых других потенциальных векторах атаки?

Ответы [ 2 ]

105 голосов
/ 11 октября 2011

XSS

JSF имеет встроенную функцию предотвращения XSS. Вы можете безопасно снова отобразить все вводимые пользователем данные (заголовки запросов (включая файлы cookie!), Параметры запросов (также те, которые сохраняются в БД!) И тела запросов (загруженные текстовые файлы и т. Д.)), Используя любой Компонент JSF.

<h:outputText value="#{user.name}" />
<h:outputText value="#{user.name}" escape="true" />
<h:inputText value="#{user.name}" />
etc...

Обратите внимание, что когда вы используете JSF 2.0 в Facelets, вы можете использовать EL в тексте шаблона следующим образом:

<p>Welcome, #{user.name}</p>

Это также неявно будет экранировано. Вам не обязательно нужен <h:outputText> здесь.

Только , когда вы явно неэкранируете управляемый пользователем ввод с использованием escape="false":

<h:outputText value="#{user.name}" escape="false" />

тогда у вас есть потенциальная дыра в атаке XSS!

Если вы хотите снова отобразить контролируемый пользователем ввод в виде HTML, в котором вы хотите разрешить только определенное подмножество тегов HTML, таких как <b>, <i>, <u> и т. Д., То вам необходимо санировать ввод белый список. Анализатор HTML Jsoup очень полезен в этом.

itemLabelEscaped ошибка в Мохарре <2.2.6 </h3> В старых версиях Mojarra до 2.2.6 была ошибка, из-за которой <f:selectItems itemLabel> неверно отображал метку без экранирования, когда предоставлялось List<T> через <f:selectItems var> вместо List<SelectItem> или SelectItem[] как значения ( выпуск 3143 ). Другими словами, если вы повторно отображаете данные, контролируемые пользователем, в качестве меток элементов через List<T>, то у вас есть потенциальная дыра в XSS. Если обновление по крайней мере до Mojarra 2.2.6 не вариант, вам нужно явно установить атрибут itemLabelEscaped в true, чтобы предотвратить это. <f:selectItems value="#{bean.entities}" var="entity" itemValue="#{entity}" itemLabel="#{entity.someUserControlledProperty}" itemLabelEscaped="true" /> CSRF JSF 2.x уже имеет встроенную функцию предотвращения CSRF в виде скрытого поля javax.faces.ViewState в форме при использовании сохранения состояния на стороне сервера. В JSF 1.x это значение было довольно слабым и слишком легко предсказуемым (фактически оно никогда не предназначалось для предотвращения CSRF). В JSF 2.0 это было улучшено за счет использования длинного и сильного автоматически сгенерированного значения вместо довольно предсказуемого значения последовательности и, таким образом, превращения его в надежное предотвращение CSRF. В JSF 2.2 это еще более улучшилось, сделав его обязательной частью спецификации JSF вместе с настраиваемым ключом AES для шифрования состояния на стороне клиента, если включено сохранение состояния на стороне клиента. См. Также JSF spec проблема 869 и Повторное использование значения ViewState в другом сеансе (CSRF) . Новое в JSF 2.2 - защита CSRF для запросов GET по <protected-views>. Только когда вы используете представления без сохранения состояния, как в <f:view transient="true">, или если в приложении есть дыра для атаки XSS, у вас есть потенциальная дыра для атаки CSRF. SQL-инъекция Это не является обязанностью JSF. Как это предотвратить, зависит от используемого вами API персистентности (необработанный JDBC, современный JPA или хороший старый Hibernate), но все сводится к тому, что вы должны никогда объединять контролируемый пользователем ввод в строки SQL, как String sql = "SELECT * FROM user WHERE username = '" + username + "' AND password = md5(" + password + ")"; String jpql = "SELECT u FROM User u WHERE u.username = '" + username + "' AND u.password = md5('" + password + "')"; Представьте, что произойдет, если конечный пользователь выберет следующее имя: x'; DROP TABLE user; -- Вы должны всегда использовать параметризованные запросы, где это применимо. String sql = "SELECT * FROM user WHERE username = ? AND password = md5(?)"; String jpql = "SELECT u FROM User u WHERE u.username = ?1 AND u.password = md5(?2)"; В простом JDBC вам нужно использовать PreparedStatement для заполнения значений параметров, а в JPA (и Hibernate) объект Query также предлагает для этого сеттеры.

8 голосов
/ 11 октября 2011

Я не использую JavaScript ни на одной из страниц просмотра. Даже если я использую, действительно ли мне нужно реализовать код для обхода атаки XSS.

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

Каждый раз, когда вы делаете что-то вроде

response.write("<b>" + x + "</b>")

если злоумышленник может заставить x содержать HTML-код, содержащий JavaScript, тогда вы уязвимы для XSS.

Решение обычно состоит в том, чтобы не писать большие объемы кода. Обычно решение заключается в кодировании $x и любых других значений, контролируемых злоумышленником, перед включением их в создаваемый вами HTML-код.

response.write("<b>" + escapePlainTextToHtml(x) + "</b>")

Фильтрация или дезинфекция входных данных может помочь обеспечить дополнительный уровень защиты.

<shameless-plug>

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

Шаблон закрытия является одним из таких вариантов для Java.

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

EDIT

Поскольку вы используете JSF, вы должны прочитать о XSS-смягчении в JSF :

Выходной текст выхода

<h:outputText/> и <h:outputLabel/> по умолчанию имеют атрибут escape, установленный в True. Используя этот тег для отображения выходных данных, вы можете уменьшить большинство уязвимостей XSS.

SeamTextParser и <s:formattedText/>

Если вы хотите разрешить пользователям использовать некоторые основные теги html для настройки своих входных данных, JBoss Seam предоставляет тег <s:formattedText/>, который позволяет использовать некоторые основные теги html и стили, указанные пользователями.

...