Решите это с помощью OWASP и ESAPI

Вектор атаки: java.io.PrintWriter.write

Описание. Этот вызов java.io.PrintWriter.write () содержит ошибку межсайтового скриптинга (XSS). Приложение заполняет HTTP-ответ введенными пользователем данными, позволяя злоумышленнику внедрить вредоносный контент, такой как код Javascript, который будет выполняться в контексте браузера жертвы. Уязвимости XSS обычно используются для кражи файлов cookie или манипулирования ими, изменения представления контента и компрометации конфиденциальной информации, при этом регулярно обнаруживаются новые векторы атак. Первый аргумент функции write () содержит испорченные данные. Испорченные данные возникли в результате более раннего вызова javax.servlet.servletrequest.getparameter. Испорченные данные направляются в выходной поток, возвращаемый org.apache.jasper.runtime.pagecontextimpl.getout.

Это первый аргумент кода writer.write (arg1). Пожалуйста, помогите мне в этом


person Kunal Ganatra    schedule 28.12.2015    source источник


Ответы (1)


Я думаю, это относится к тому факту, что вы можете использовать ввод пользователя, который не подвергается дезинфекции.

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

http://xxx/servlet/vulnerable?someuserinput=Bob

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

http://xxx/servlet/vulnerable?someuserinput=alert («Здравствуйте! Я что-то делаю противный!!");

Эмпирическое правило - всегда дезинфицировать вводимые данные

@WebServlet(name = "vulnerable", urlPatterns = {"/vulnerable"})
public class NewServlet extends HttpServlet {

    protected void processRequest(HttpServletRequest request, HttpServletResponse response)
            throws ServletException, IOException {
        response.setContentType("text/html;charset=UTF-8");
        String someUserInput = request.getParameter("someuserinput");

        try (PrintWriter out = response.getWriter()) {

            out.write("<!DOCTYPE html>");
            out.write("<html>");
            out.write("<head>");       
            out.write("</head>");
            out.write("<body>");
            out.write("<h1>Hello " + someUserInput + "</h1>");//something bad can happen here 
            out.write("</body>");
            out.write("</html>");
        }
    }

Я знаю, что вы спрашиваете о ESAPI, но в OWASP есть HTML simple Sanitizer.

https://github.com/OWASP/java-html-sanitizer

ESAPI в контексте HTML (как указано выше)

String safer = ESAPI.encoder().encodeForHTML( request.getParameter( "someuserinput" ) );

ESAPI в контексте Javascript

String safer = ESAPI.encoder().encodeForJavaScript( request.getParameter( "someuserinput" ) );
person rjdkolb    schedule 28.12.2015
comment
Это сработает ... если контекст - HTML. Если параметр будет использоваться фреймворком javascript, скажем, AngularJS или просто старым простым javascript, тогда вы захотите использовать encodeForJavaScript() - person avgvstvs; 29.12.2015
comment
И семантически ... не используйте слово безопасный при работе с пользовательским вводом. Вы же не хотите, чтобы люди теряли бдительность в отношении своего кода. - person avgvstvs; 29.12.2015
comment
Ага . Спасибо ! Но если я хочу закодировать Writer.write (somearg), то какую кодировку мне следует использовать для предотвращения межсайтового скриптинга. - person Kunal Ganatra; 30.12.2015
comment
Я кодирую следующее, используя writer.write (encoder.encodeForHTMLAttribute (output.toString ())); Это верно . ? - person Kunal Ganatra; 30.12.2015
comment
@Kunal Ganatra, я думаю, это зависит от того, где вы используете вывод. Это будет зависеть от вашего варианта использования. Так что, если вы используете значение для поиска атрибута, тогда да. encodeForHTML хорошо подойдет для приведенного мной примера. - person rjdkolb; 30.12.2015