在Form中,爲了防止csrf攻擊,通常會使用csrf token進行防禦,在後臺使用$this->security->checkToken()進行檢測,但在ajax進行POST提交時,如果不做一些額外的操作,會導致ajax第二次提交時csrf token驗證不過。
原因:由於csrf token是每次提交後自動更新的,ajax在第一次提交後,在服務後端csrf token其實已經變了,所以再用原來的key就無法驗證通過。
解決方式:需要對頁面中的csrf token也進行更新才行。
示例:
後臺代碼:
public function xxx()
{
$this->view->disable();
if ($this->security->checkToken()) {
echo json_encode(
[
'csrfToken' => [
'key' => $this->security->getTokenKey(),
'token' => $this->security->getToken()
]
]
);
}
}
前端代碼:
<button id="haha" key="{{ security.getTokenKey() }}" token="{{ security.getToken() }}" class="btn btn-default">
test
</button>
<script type="application/javascript">
$("#haha").click(function () {
var key = $("#haha").attr('key');
var token = $("#haha").attr('token');
var post_data = {};
post_data[key] = token;
console.log(post_data);
$.ajax({
type: 'POST',
url: '{{ url('xxx/xxx') }}',
data: post_data,
dataType: 'JSON',
success: function (result) {
var res = result['csrfToken'];
$("#haha").attr('key', res.key);
$("#haha").attr('token', res.token);
console.log(res);
}
});
return false;
})
</script>
前端在進行提交後,後臺會返回下一次要用的token,前端要更新相應的token數據,以便於下一次正確提交!