2014-11-28 2 views
2

Я пытаюсь реализовать пружинный безопасности (версия 3.2.3) CSRF токен в моем проекте, ссылаясь ниже ссылкиSpring Security CSRF маркер не работает с AJAX вызова и отправки формы в той же JSP

http://docs.spring.io/autorepo/docs/spring-security/4.0.0.CI-SNAPSHOT/reference/htmlsingle/#csrf http://docs.spring.io/autorepo/docs/spring-security/4.0.0.CI-SNAPSHOT/reference/htmlsingle/#the-csrfmetatags-tag

Я могу интегрировать токен CSRF в JSP успешно без вызова AJAX. Но когда я пробовал JSP с вызовом AJAX, получаю «недопустимое исключение токена CSRF». После моего анализа я нашел для обоих сообщений AJAX & с помощью того же токена из-за этого я получаю «недопустимое исключение CSRF-токена».

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

security.xml

<access-denied-handler ref="accessDenied" /> 

    <intercept-url pattern="/**" access="ROLE_1" /> 

    <form-login default-target-url='/loginUser.htm' always-use-default-target='true' authentication-failure-url='/forms/common/login.jsp?error=true' /> 

    <logout logout-success-url="/forms/common/logout.jsp" invalidate-session="true" delete-cookies="JSESSIONID" /> 

    <session-management invalid-session-url="/forms/common/sessionexpired.jsp" session-authentication-error-url="/forms/common/login.jsp?Error=alreadyLoggedin" > 

     <concurrency-control expired-url="/forms/common/sessionexpired.jsp" max-sessions="1" error-if-maximum-exceeded="true" /> 

    </session-management> 

    <csrf request-matcher-ref="csrfSecurityRequestMatcher"/> 
</http> 

<beans:bean class="com.concerto.pg.login.security.CsrfSecurityRequestMatcher" id="csrfSecurityRequestMatcher"/> 

JSP

<head> 

<sec:csrfMetaTags /> 

<script type="text/javascript" charset="utf-8"> 

function changeList(id,option){ 

    var csrfParameter = $("meta[name='_csrf_parameter']").attr("content"); 
    var csrfToken = $("meta[name='_csrf']").attr("content"); 

    var institution = document.getElementById("institutionId").value; 
    var data = {}; 

    data[csrfParameter] = csrfToken; 
    data["institutionId"] = option; 

if(id=="institutionId"){ 

    var result =''; 

       $.ajax({ 
        type: "GET", 
        async: false, 
         url: './getMerchantByInstitution.htm', 
        data: data,//"institutionId=" + option, 
        dataType:'json', 
        success: function (res) { 
        result = res;  
         var htmlVar = ''; 
          for (var i=0; i<result.length; i++){ 
           htmlVar += '<option 
           value="'+result[i]+'">'+result[i]+'</option>';        
          } 
          htmlVar += '<option value="ALL">ALL</option>'; 
          $('#merchantId').html(htmlVar); 
        } 
       }); 



    } 

} 

</script> 
</head> 
added below < input type="hidden" name="${_csrf.parameterName}" value="${_csrf.token}" /> statement in form tag

Благодарности & С уважением, Siva

ответ

7

Я надеюсь, что это ниже ответ поможет. сделать эти изменения

var csrfParameter = $("meta[name='_csrf_parameter']").attr("content"); 
var csrfToken = $("meta[name='_csrf']").attr("content"); 
var csrfHeader = $("meta[name='_csrf_header']").attr("content"); // THIS WAS ADDED 

и после

data[csrfParameter] = csrfToken; 
data["institutionId"] = option; 
headers[csrfHeader] = csrfToken; // THIS WAS ADDED 

окончательно изменить в вызове Ajax:

url: './getMerchantByInstitution.htm', 
headers: headers, // THIS WAS ADDED 
data: data,//"institutionId=" + option, 
dataType:'json', 

Позвольте мне знать, если это работает.

+1

Если я не ошибаюсь, Spring даже не проверяет тег CSRF для методов GET ...? –

+1

Это зависит от того, как вы его настраиваете, кодирование - это искусство, так же как и наука – Aeseir

14

Чтобы сделать запрос AJAX/JSON с включенным CSRF, вы должны передать токен CSRF в качестве HTTP-запроса Заголовок, а не параметр или другие данные.

На странице, ваши мета-теги должны выглядеть эти:

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

Затем готовят значения где-то в коде JS:

var token = $("meta[name='_csrf']").attr("content"); 
var header = $("meta[name='_csrf_header']").attr("content"); 

передать маркер CSRF как заголовок:

$.ajax({ 
     type: "GET", 
     async: false, 
     url: './getMerchantByInstitution.htm', 
     data: "institutionId=" + option, 
     beforeSend: function(xhr) { 
      // here it is 
      xhr.setRequestHeader(header, token); 
     }, 
     success: function(obj) { 
      // .... 
     }, 
     .... 

Хотя это полностью зависит от вас, я бы рекомендовал использовать что-то вроде JSON.stringify для передачи данные, но это зависит, конечно.

Ссылки здесь:

http://docs.spring.io/spring-security/site/docs/3.2.0.CI-SNAPSHOT/reference/html/csrf.html#csrf-include-csrf-token-ajax

Надеется, что это помогает.

Смежные вопросы