一.簡介
CSRF的全稱是(Cross Site Request Forgery),可譯為跨域請求僞造,是一種利用使用者帶登入态的cookie進行安全操作的攻擊方式。CSRF實際并不難防,但常常被系統開發者忽略而埋下巨大的安全隐患。
二.實戰
CookieCsrfTokenRepository方式
它将CsrfToken值存儲在使用者的cookie内。首先,減少了伺服器HttpSession存儲的記憶體消耗;其次,當用cookie存儲CsrfToken值時,前端可以用JavaScript讀取(需要設定該cookie的httpOnly屬性為false),而不需要伺服器注入參數,在使用方式上更加靈活。
存儲在cookie上,不就可以被CSRF利用了嗎?事實上并不可以。cookie隻有在同域的情況下才能被讀取,是以杜絕了第三方站點跨域擷取CsrfToken值的可能。CSRF攻擊本身不知道cookie内容的,隻是利用了當請求自動攜帶cookie時可以通過身份驗證的漏洞。但伺服器對CsrfToken值的校驗并非取自cookie,而是需要前端手動将CsrfToken值作為參數攜帶在請求裡,是以cookie内的CsrfToken值并沒有被校驗的作用,僅僅作為一個存儲容器使用。
修改Spring Security的csrfTokenRepository。
@Override
protected void configure(HttpSecurity http) throws Exception{
http.authorizeRequests()
.antMatchers("/admin/api/**").hasRole("ADMIN")
.antMatchers("/user/api/**").hasRole("USER")
.antMatchers("/app/api/**").permitAll()
.anyRequest().authenticated()
.and()
.csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse())// CSRF配置
.and()
.formLogin()
.and()
.sessionManagement()
// 最大會話數設定
.maximumSessions(1)
// 阻止新會話登入
.maxSessionsPreventsLogin(true);
}
相關代碼:https://github.com/o99o/SpringSecurity/tree/master/SpringSecurity_13_CSRF