Java 如何解决SAST检查后API控制器中的XSRF跨站点请求伪造(CSRF)

Java 如何解决SAST检查后API控制器中的XSRF跨站点请求伪造(CSRF),java,spring-boot,csrf,checkmarx,secure-coding,Java,Spring Boot,Csrf,Checkmarx,Secure Coding,我已经用Checkmarx工具扫描了我的项目javaspringboot。 该工具发现约23个XSRF OCcorrence,严重程度中等 发现的问题标记在@RequestBody列表列表上的Rest API方法帖子上 在所附的描述结果屏幕截图中: @RequestMapping(value=“/rules/lineup/{ruleMode}”,method=RequestMethod.POST,products=MediaType.APPLICATION\u JSON\u value) pu

我已经用Checkmarx工具扫描了我的项目javaspringboot。 该工具发现约23个XSRF OCcorrence,严重程度中等

发现的问题标记在
@RequestBody列表列表上的Rest API方法帖子上

在所附的描述结果屏幕截图中:

@RequestMapping(value=“/rules/lineup/{ruleMode}”,method=RequestMethod.POST,products=MediaType.APPLICATION\u JSON\u value)
public ResponseEntity GetRulesByRuleMode和Lineup(@PathVariable Integer ruleMode,
@RequestBody列表(列表)引发异常{
LOGGER.info(“[getRulesByRuleModeAndLineup]输入类型:“+ruleMode+”列表:“+lineups”);
ResponseEntity输出=null;
列表规则=新建ArrayList();
试一试{
用于(字符串排列:排列){
字符串lineupSanitized=htmlitls.htmlEscape(lineup);
rules.addAll(uiService.getRulesByRuleModeAndLineup(ruleMode,lineupsanized));
}
输出=新响应性(规则,HttpStatus.OK);
}捕获(例外e){
记录器错误(e,e);
输出=新响应属性(“发生错误:”+e.getMessage()+“”,
HttpStatus.INTERNAL_SERVER_ERROR);
}
返回输出;
}

是否有解决此问题的示例修复程序?

您可以选择对该字段进行验证。 这里有两种选择:

  • 使用一个已经内置了这个功能的框架,我推荐spring 为此:
  • 如果需要,请尝试将希望在api上接受的字符串列为白名单 我能做到

  • 第二点意味着你有责任使你的列表保持最新。

    我试图实现你在回答中提到的第一点,就像下面的代码一样

    后端侧面:

        import org.apache.logging.log4j.LogManager;
        import org.apache.logging.log4j.Logger;
        import org.springframework.context.annotation.Configuration;
        import org.springframework.security.config.annotation.web.builders.HttpSecurity;
        import org.springframework.security.config.annotation.web.configuration.EnableWebSecurity;
        import org.springframework.security.config.annotation.web.configuration.WebSecurityConfigurerAdapter;
        import org.springframework.security.web.csrf.CookieCsrfTokenRepository;
    
        @Configuration
        @EnableWebSecurity
        public class SecurityConfig extends WebSecurityConfigurerAdapter {
        
            private static final Logger LOGGER = LogManager.getLogger(SecurityConfig.class);
        
            
            @SuppressWarnings("javadoc")
            @Override
            protected void configure(HttpSecurity http) throws Exception {
                
                http.authorizeRequests().antMatchers("/**").permitAll().anyRequest().authenticated();
                
                http.csrf().csrfTokenRepository(CookieCsrfTokenRepository.withHttpOnlyFalse());
                
                http.headers().httpStrictTransportSecurity();
            }
        
        }
    
    前端侧面

    我在以下代码中实现了一个xhrRequestHandler文件名js:

    XMLHttpRequest.prototype.origOpen = XMLHttpRequest.prototype.open;
    XMLHttpRequest.prototype.open = function () {
        this.origOpen.apply(this, arguments);
        if (document.cookie) {
            var csrfToken = document.cookie.match(new RegExp(`XSRF-TOKEN=([^;]+)`))[1];
            if (csrfToken) {
                this.setRequestHeader("X-XSRF-TOKEN", csrfToken);
            }
        }
        if (arguments[1].includes("socket/info")) {
            this.setRequestHeader('X-Requested-With', 'XMLHttpRequest');
        }
    };
    
    <script src="<c:url value="/resources/js/xhrRequestHandler.js"/>"></script>
    
    在index.jsp上

    我导入了上面定义的js文件,代码如下:

    XMLHttpRequest.prototype.origOpen = XMLHttpRequest.prototype.open;
    XMLHttpRequest.prototype.open = function () {
        this.origOpen.apply(this, arguments);
        if (document.cookie) {
            var csrfToken = document.cookie.match(new RegExp(`XSRF-TOKEN=([^;]+)`))[1];
            if (csrfToken) {
                this.setRequestHeader("X-XSRF-TOKEN", csrfToken);
            }
        }
        if (arguments[1].includes("socket/info")) {
            this.setRequestHeader('X-Requested-With', 'XMLHttpRequest');
        }
    };
    
    <script src="<c:url value="/resources/js/xhrRequestHandler.js"/>"></script>
    
    
    
    并添加了元名称行:

    <meta name="_csrf" content="${_csrf.token}"/>
        <meta name="_csrf_header" content="${_csrf.headerName}"/>
    
    
    
    但我没有解决这个问题


    有什么问题吗?

    这条消息似乎很好地解释了这个问题:有一个用户提供的参数似乎在该方法中被不安全地使用。您如何安全地使用它或放弃错误?只有您才能知道,因为只有您才能看到处理它的方法的源代码。如果您不向我们展示这段代码,读者就无能为力。