赞
踩
前几天收到安全部门的邮件:你负责的项目有个XSS安全漏洞需要修复。我内心:安全知识倒是了解些,到底该怎么去修复,还是一头雾水。。。
什么是XSS呢?
XSS漏洞为跨站脚本漏洞,分为反射型、持久型、DOM型。反射型漏洞的触发是用户点击了被篡改的URL,篡改的数据经前端传到后端后展示在前端,并在前端执行,受影响的是指定浏览器;持久型漏洞是用户输入非法内容,经前端上传到后端,并入库,后经后端传给前端,在前端执行,受影响的是任何访问指定连接的浏览器;DOM型漏洞是用户点击了被篡改的url,篡改后的数据直接在浏览器执行。
具体XSS案例可以看看其它博客,都有明确讲述,不多BB,来先看下我司的奇安信代码卫视扫描出所负责的代码漏洞:
提示下方28行代码有问题:
下方这个提示 26,27行有问题:
再来看看给的修复建议:
- 为了避免反射型XSS攻击,建议采用以下方式进行防御:
- 1.对用户的输入进行合理验证(如年龄只能是数字),对特殊字符(如`<、>、'、"以及\<script\>、javascript`等进行过滤。
- 2.根据数据将要置于HTML上下文中的不同位置(HTML标签、HTML属性、JavaScript脚本、CSS、URL),对所有不可信数据进行恰当的输出编码。
- **例如**:采用OWASP ESAPI对数据输出HTML上下文中不同位置,编码方法如下。
- ```java
- //HTML encode
- ESAPI.encoder().encodeForHTML(inputData);
- //HTML attribute encode
- ESAPI.encoder().encodeForHTMLAttribute(inputData);
- //JavaScript encode
- ESAPI.encoder().encodeForJavaScript(inputData);
- //CSS encode
- ESAPI.encoder().encodeForCSS(inputData);
- //URL encode
- ESAPI.encoder().encodeForURL(inputData);
- ```
- 3.设置HttpOnly属性,避免攻击者利用跨站脚本漏洞进行Cookie劫持攻击。在Java EE中,给Cookie添加HttpOnly的代码如下:
- ```java
- ...
- response.setHeader("Set-Cookie","cookiename=cookievalue; path=/; Domain=domainvaule; Max-age=seconds; HttpOnly");
这修复建议看了后似乎对于上述没啥大的帮助啊。然后经过看别人博客和思考,用以下方式解决:
对于第一个案例:
- String serverName = req.getServerName();
- String host = HtmlUtils.htmlEscape(req.getHeader("host"));
- obj.addProperty("serverName", serverName);
- obj.addProperty("header-host", host);
因为项目使用的是Spring,便用Spring的HtmlUtils.htmlEscape 对request.getHeader("host")进行转译,防止host里面植入html或者sql语句,那如果host篡改呢,这就涉及到CSRF跨站攻击了,下次在写一篇实战解决CSRF跨站攻击案例,目前这段代码只是针对单个方法进行转译,那如果其它方法也有类似,不是要重复写很多?那我们可以用如下方案(因为项目使用springboot方式,直接用bean注入相应filter)
- public class XssSpringFilter implements Filter {
- @Override
- public void init(FilterConfig filterConfig) throws ServletException {
-
- }
-
- @Override
- public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain) throws IOException, ServletException {
- HttpServletRequest req = (HttpServletRequest) request;
- chain.doFilter(new XssSpringHttpServletRequestWrapper(req), response);
- }
-
- @Override
- public void destroy() {
-
- }
- }
- public class XssSpringHttpServletRequestWrapper extends HttpServletRequestWrapper {
-
- public XssSpringHttpServletRequestWrapper(HttpServletRequest request) {
- super(request);
- }
- /**
- * 对数组参数进行特殊字符过滤
- */
- @Override
- public String[] getParameterValues(String name) {
- String[] values = super.getParameterValues(name);
- if(values == null){
- return null;
- }
- String[] newValues = new String[values.length];
- for (int i = 0; i < values.length; i++) {
- //spring的HtmlUtils进行转义
- newValues[i] = HtmlUtils.htmlEscape(values[i]);
- }
- return newValues;
- }
-
- /**
- * 拦截参数,并对其进行字符转义
- */
- @Override
- public String getParameter(String name) {
- String value = super.getParameter(name);
- return HtmlUtils.htmlEscape(value);
- }
- /**
- * 拦截header,并对其进行字符转义
- */
- @Override
- public String getHeader(String name) {
- String value = super.getHeader(name);
- return HtmlUtils.htmlEscape(value);
- }
- @Configuration
- public class FilterConfig extends WebMvcConfigurerAdapter {
- @Bean
- public FilterRegistrationBean xssSpringFilter() {
- FilterRegistrationBean registration = new FilterRegistrationBean();
- registration.setFilter(new XssSpringFilter());
- registration.addUrlPatterns("/*");
- registration.setName("xssSpringFilter");
- registration.setOrder(-1);
- return registration;
- }
- }
对于第二个案例,因为url是通过我们内部服务获取的域名,获取的内容不会被篡改,所以也就不用改了,也不能全信代码扫描工具呀
Copyright © 2003-2013 www.wpsshop.cn 版权所有,并保留所有权利。