安全顶部

我刚宣布了新的学习春天安全课程,包括完整的材料集中在新的OAuth2堆栈在Spring Security 5:

>>查看课程

1.概述

在构建Spring web应用程序时,关注安全性非常重要。跨站点脚本(XSS)是对网络安全最关键的攻击之一。

防止XSS攻击是春季应用中的挑战。Spring提供了一些帮助,但我们需要实施额外的代码以进行完整的保护。

在本教程中,我们将使用可用的Spring Security特性,并添加自己的XSS过滤器。

2.什么是跨站脚本(XSS)攻击?

2.1。问题的定义

XSS是一种常见的注射攻击。在XSS中,攻击者尝试在Web应用程序中执行恶意代码。他们通过Web浏览器或HTTP客户端工具与其交互邮递员

有两种类型的XSS攻击:

  • 反射或非XSS
  • 存储或持久XSS

在反射或非XSS中,不受信任的用户数据被提交到Web应用程序,该Web应用程序在响应中立即返回,将不可信的内容添加到页面。Web浏览器假定代码来自Web服务器并执行它。这可能允许黑客向您发送链接,即在遵循后,导致浏览器从您使用的网站检索您的私人数据,然后使浏览器将其转发到黑客服务器。

在存储或持久XSS中,攻击者的输入被web服务器存储。随后,任何未来的访问者都可能执行该恶意代码。

2.2。防御攻击

防止XSS攻击的主要策略是清除用户输入。

在Spring web应用程序中,用户的输入是一个HTTP请求。为了防止攻击,我们应该检查HTTP请求的内容,并删除任何可能被服务器或浏览器执行的内容。

对于常规的Web应用程序,通过Web浏览器访问,我们可以使用newbee赞助雷竞技 内置功能(反射XSS)。对于公开API的Web应用程序,Spring Security不提供任何功能,并且必须实现自定义XSS过滤器以防止存储的XSS。

3.使用Spring Security制作应用程序XSS安全

Spring Security默认提供了多个安全标头。它包括这一点X-XSS-Protection标题。X-XSS-Protection告诉浏览器阻止看起来像xss的内容。Spring Security可以自动将此安全标题添加到响应中。要激活此功能,我们将在Spring Security Configuration类中配置XSS支持。

使用此功能,浏览器在检测到XSS尝试时不会呈现。但是,某些Web浏览器还没有实现XSS审核员。在这种情况下,他们没有利用X-XSS-Protection标题要克服这个问题,我们也可以使用内容安全策略(CSP)特性。

CSP是一个添加的安全层,有助于缓解XS和数据注入攻击。要启用它,我们需要将应用程序配置为返回aContent-Security-Policy头,提供WebSecurityConfigurerAdapter豆:

@Configuration public class SecurityConf extends WebSecurityConfigurerAdapter {@Override protected void configure(HttpSecurity http) throws Exception {http .headers() .xssProtection() .and() .contentSecurityPolicy("script-src 'self'");}}

这些标头确实可以保护REST API从存储XSS。为了解决这个问题,我们可能还需要实现一个XSS过滤器。

4.创建XSS过滤器

4.1。使用XSS过滤器

为了防止XSS攻击,我们将在将请求传递给请求之前从请求内容中删除所有可疑字符串RestController

HTTP请求内容包括以下部分:

  • 标题
  • 参数
  • 身体

一般来说,我们应该从标题,参数和尸体中剥离恶意代码对于每一个请求。

我们将创建一个过滤器,用于评估请求的值。XSS过滤器检查请求的参数,标题和正文。

让我们通过实现XSS过滤器来创建XSS过滤器过滤器界面:

@Component @Order(order.highest_precedence) public class XSSFilter implements Filter {@Override public void doFilter(ServletRequest request, ServletRequest response, FilterChain chain) throws IOException, ServletException {XSSRequestWrapper wrappedRequest = new XSSRequestWrapper((HttpServletRequest) request);链。doFilter (wrappedRequest、响应);} //其他方法}

我们应该将XSS过滤器配置为Spring应用程序中的第一个过滤器。因此,我们将过滤器的顺序设置为最高_precedence.

要添加到我们的请求中的数据清理,我们将创建一个子类httpservletrequestwrapper.被称为Xssrequestwrapper,哪个覆盖了GetParametervalues.getParameter, 和Getheaders.在向控制器提供数据之前执行XSS检查的方法。

4.2。从请求参数中剥离XSS

现在,让我们实现GetParametervalues.getParameter我们请求包装的方法:

public class XSSRequestWrapper extends HttpServletRequestWrapper {@Override public String[] getParameterValues(String parameter) {String[] values = super.getParameterValues(parameter);If (values == null){返回null;} int count = values.length;String[] encodedValues = new String[count];For (int I = 0;我<数;i++) {encodedValues[i] = stripXSS(值[i]);}返回encodedValues;} @Override public String getParameter(String parameter) {String value = super.getParameter(parameter);返回stripXSS(价值); } }

我们写astripxs.函数处理每个值。我们很快就会实现它。

4.3。从请求头剥离XSS

我们还需要从请求头中去除XSS。作为Getheaders.返回A.枚举我们需要生成一个新列表,清除每个标题:

@Override public Enumeration getHeaders(String name) {List result = new ArrayList<>();枚举头= super.getHeaders(name);while (headers.hasMoreElements()) {String header = headers.nextElement();String[] tokens = header.split(",");for (String token: tokens) {result.add(stripXSS(token));}} return Collections.enumeration(result);}

4.4。从请求体中剥离XSS

我们的过滤器需要从请求体中删除危险内容。我们已经有了一个WrapkedRequest.有一个莫制品InputStream,让我们扩展代码来处理正文并重置值InputStream清洁后:

@override public void dofilter(servletrequest请求,servletresponse响应,filterchain链)抛出IoException,servletException {xssrequestwrapper wrappedrequest = new xssrequestwrapper((httpservletrequest)请求);string body = ioutils.tostring(wrappedrequest.getReader());if(!stryutils.isblank(body)){body = xssutils.stripxss(body);wrappedrequest.resetInputStream(body.getBytes());链条.Dofilter(WrappedRequest,响应);}

5.使用外部库进行数据清理

读取请求的所有代码现在都执行stripxs.在任何用户提供的内容上的功能。现在让我们创建该功能来执行XSS检查。

首先,此方法将获得请求的值并计算它。对于这一步,我们使用esapi.。ESAPI是OWASP提供的开源web应用安全控制库。

其次,我们将根据XSS模式检查请求的值。如果值是可疑的,它将被设置为一个空字符串。为此,我们将使用Jsoup,它提供了一些简单的清理函数。如果我们想要更多的控制,我们可以构建自己的正则表达式,但这可能比使用标准库更容易出错。

5.1。依赖关系

首先,我们添加esapiMaven依赖于我们的pom.xml.文件:

 org.owasp.esapi esapi 2.2.2.0 

此外,我们需要jsoup

<依赖项>  org.jsoup   JSOUP   1.13.1  

5.2。实现它

现在,让我们创造stripxs.方法:

公共静态字符串Stripxss(String值){if(value == null){return null;} value = esapi.encoder().canonicalize(值).replaceall(“\ 0”,“”);返回jsoup.clean(值,whitelist.none());}

这里我们设置了Jsoup白名单没有一个只允许文本节点。这样,所有的HTML都将被剥离。

6.测试XSS预防

6.1。手动测试

现在让我们使用邮递员向我们的应用程序发送可疑请求。我们会向URI发送发布消息/ personService /人。此外,我们将包含一些可疑的标题和参数。

下图显示了请求头和参数:

随着我们的服务接受JSON数据,让我们向请求正文添加一些可疑的JSON内容:

由于我们的测试服务器返回清理的响应,让我们来检查发生的情况:

标题和参数值用空字符串替换。此外,响应体表明我们的可疑价值被剥夺了。

6.2。自动化测试

现在让我们为我们的XSS过滤写一个自动测试:

//声明所需的变量personjsonObject.put(“ID”,1);personjsonobject.put(“firstname”,“b雷竞技app下载官方版isoaeldung