@parkito

Почему не работает защита от межсайтового скриптинга в spring security?

Здравствуйте. Помогите, пожалуйста, решить проблему. Настроил спринг секьюрити. Все работает. Авторизация проходит хорошо. Но вот когда я аджаксом пытаюсь выполнить запрос, то получаю
org.springframework.web.servlet.PageNotFound Request method 'POST' not supported at org.springframework.web.servlet.mvc.support.DefaultHandlerExceptionResolver.handleHttpRequestMethodNotSupported(DefaultHandlerExceptionResolver.java:215)

Т.е. ajax не возбуждает сервлет.

ajax

function popBox(num1, num2) {
   x = confirm('Are you sure? ');
   if (x == true) {
     var xhr = new XMLHttpRequest();
    xhr.open("POST", "userChangeTariff?tariffId=" + num1 + "&contractNumber=" + num2, false);
   xhr.send();
}


сервлет

@RequestMapping(value = "/userChangeTariff", method = RequestMethod.POST)
    public String changeTariff(HttpServletRequest request, Locale locale, Model model,
                               @RequestParam(value = "tariffId") String tariffId,
                               @RequestParam(value = "contractNumber") String contractNumber) {
        int tariffID = Integer.parseInt(tariffId);
        Contract contract = contractService.getContractByNumber(contractNumber);
        Tariff tariff = tariffService.getEntityById(tariffID);
        contract.setTariff(tariff);
        contractService.updateEntity(contract);
        return "user/userTariffs";
    }


Самое интерересное, то что когда я выключаю csrf ( ) все начинает работать.

На странице размещен токен

<input type="hidden" name="<c:out value="${_csrf.parameterName}"/>"
    value="<c:out value="${_csrf.token}"/>"/>


Почему csrf отрубает мне сервлет? Как это можно исправить?
  • Вопрос задан
  • 327 просмотров
Решения вопроса 1
sergey-gornostaev
@sergey-gornostaev Куратор тега Java
Седой и строгий
Всё правильно, вы в ajax-запросе не передаёте csrf-token, соответственно, он выглядит как злономеренный и не обрабатывается. Про это есть в документации.

<html>
    <head>
        <meta name="_csrf" content="${_csrf.token}"/>
        <meta name="_csrf_header" content="${_csrf.headerName}"/>
        ...
    </head>
    ...
</html>


var csrfHeaderName = "X-CSRF-TOKEN";
var csrfTokenValue;

var metaTags = document.getElementsByTagName('meta'); 
for(var i = 0; i < metaTags.length; i++) {
    var metaTagName = metaTags[i].getAttribute("name");
    if(metaTagName === "_csrf_header")
        csrfHeaderName = metaTags[i].getAttribute("content");
    if(metaTagName === "_csrf")
        csrfTokenValue = metaTags[i].getAttribute("content");
}

...
var xhr = new XMLHttpRequest();
xhr.open("POST", "userChangeTariff?tariffId=" + num1 + "&contractNumber=" + num2, false);
xhr.setRequestHeader(csrfHeaderName, csrfTokenValue);
xhr.send();
Ответ написан
Пригласить эксперта
Ваш ответ на вопрос

Войдите, чтобы написать ответ

Похожие вопросы