1200字范文,内容丰富有趣,写作的好帮手!
1200字范文 > Springboot结合ESAPI——配置XSS防御过滤

Springboot结合ESAPI——配置XSS防御过滤

时间:2021-09-03 10:24:49

相关推荐

Springboot结合ESAPI——配置XSS防御过滤

本文链接:/jxwen1/article/details/83183632

本文来源与几篇优秀文章的整合,但整合后真实可用, 在此记录以便往后使用

文章地址:/frog4/article/details/81876462

/julycaka/article/details/78467291/fengyao1995/article/details/81290547

框架:前后端分离、Spring Boot + mybatis

1. 使用的是maven项目;在pom.xml 中加入依赖:

<!-- 预防XSS攻击工具 -->

<dependency>

<groupId>org.owasp.esapi</groupId>

<artifactId>esapi</artifactId>

<version>2.1.0</version>

</dependency>

<dependency>

<groupId>org.jsoup</groupId>

<artifactId>jsoup</artifactId>

<version>1.9.2</version>

</dependency>

2. 在classpath下加入配置文件:validation.properties和ESAPI.properties

ESAPI.properties

# 是否要打印配置属性,默认为true

ESAPI.printProperties=true

ESAPI.AccessControl=org.owasp.esapi.reference.DefaultAccessController

ESAPI.Authenticator=org.owasp.esapi.reference.FileBasedAuthenticator

ESAPI.Encoder=org.owasp.esapi.reference.DefaultEncoder

ESAPI.Encryptor=org.owasp.esapi.reference.crypto.JavaEncryptor

ESAPI.Executor=org.owasp.esapi.reference.DefaultExecutor

ESAPI.HTTPUtilities=org.owasp.esapi.reference.DefaultHTTPUtilities

ESAPI.IntrusionDetector=org.owasp.esapi.reference.DefaultIntrusionDetector

ESAPI.Logger=org.owasp.esapi.reference.JavaLogFactory

ESAPI.Randomizer=org.owasp.esapi.reference.DefaultRandomizer

ESAPI.Validator=org.owasp.esapi.reference.DefaultValidator

#===========================================================================

# ESAPI Encoder

Encoder.AllowMultipleEncoding=false

Encoder.AllowMixedEncoding=false

Encoder.DefaultCodecList=HTMLEntityCodec,PercentCodec,JavaScriptCodec

#===========================================================================

# ESAPI 加密模块

Encryptor.PreferredJCEProvider=

Encryptor.EncryptionAlgorithm=AES

Encryptor.CipherTransformation=AES/CBC/PKCS5Padding

bined_modes=GCM,CCM,IAPM,EAX,OCB,CWC

Encryptor.cipher_modes.additional_allowed=CBC

Encryptor.EncryptionKeyLength=128

Encryptor.ChooseIVMethod=random

Encryptor.fixedIV=0x000102030405060708090a0b0c0d0e0f

Encryptor.CipherText.useMAC=true

Encryptor.PlainText.overwrite=true

Encryptor.HashAlgorithm=SHA-512

Encryptor.HashIterations=1024

Encryptor.DigitalSignatureAlgorithm=SHA1withDSA

Encryptor.DigitalSignatureKeyLength=1024

Encryptor.RandomAlgorithm=SHA1PRNG

Encryptor.CharacterEncoding=UTF-8

Encryptor.KDF.PRF=HmacSHA256

#===========================================================================

# ESAPI Http工具

HttpUtilities.UploadDir=C:\\ESAPI\\testUpload

HttpUtilities.UploadTempDir=C:\\temp

# Force flags on cookies, if you use HttpUtilities to set cookies

HttpUtilities.ForceHttpOnlySession=false

HttpUtilities.ForceSecureSession=false

HttpUtilities.ForceHttpOnlyCookies=true

HttpUtilities.ForceSecureCookies=true

# Maximum size of HTTP headers

HttpUtilities.MaxHeaderSize=4096

# File upload configuration

HttpUtilities.ApprovedUploadExtensions=.zip,.pdf,.doc,.docx,.ppt,.pptx,.tar,.gz,.tgz,.rar,.war,.jar,.ear,.xls,.rtf,.properties,.java,.class,.txt,.xml,.jsp,.jsf,.exe,.dll

HttpUtilities.MaxUploadFileBytes=500000000

# Using UTF-8 throughout your stack is highly recommended. That includes your database driver,

# container, and any other technologies you may be using. Failure to do this may expose you

# to Unicode transcoding injection attacks. Use of UTF-8 does not hinder internationalization.

HttpUtilities.ResponseContentType=text/html; charset=UTF-8

# This is the name of the cookie used to represent the HTTP session

# Typically this will be the default "JSESSIONID"

HttpUtilities.HttpSessionIdName=JSESSIONID

#===========================================================================

# ESAPI Executor

Executor.WorkingDirectory=

Executor.ApprovedExecutables=

#===========================================================================

# ESAPI Logging

# Set the application name if these logs are combined with other applications

Logger.ApplicationName=ExampleApplication

# If you use an HTML log viewer that does not properly HTML escape log data, you can set LogEncodingRequired to true

Logger.LogEncodingRequired=false

# Determines whether ESAPI should log the application name. This might be clutter in some single-server/single-app environments.

Logger.LogApplicationName=true

# Determines whether ESAPI should log the server IP and port. This might be clutter in some single-server environments.

Logger.LogServerIP=true

# LogFileName, the name of the logging file. Provide a full directory path (e.g., C:\\ESAPI\\ESAPI_logging_file) if you

# want to place it in a specific directory.

Logger.LogFileName=ESAPI_logging_file

# MaxLogFileSize, the max size (in bytes) of a single log file before it cuts over to a new one (default is 10,000,000)

Logger.MaxLogFileSize=10000000

#===========================================================================

# ESAPI Intrusion Detection

IntrusionDetector.Disable=false

IntrusionDetector.event.test.count=2

IntrusionDetector.event.test.interval=10

IntrusionDetector.event.test.actions=disable,log

.owasp.esapi.errors.IntrusionException.count=1

.owasp.esapi.errors.IntrusionException.interval=1

.owasp.esapi.errors.IntrusionException.actions=log,disable,logout

.owasp.esapi.errors.IntegrityException.count=10

.owasp.esapi.errors.IntegrityException.interval=5

.owasp.esapi.errors.IntegrityException.actions=log,disable,logout

.owasp.esapi.errors.AuthenticationHostException.count=2

.owasp.esapi.errors.AuthenticationHostException.interval=10

.owasp.esapi.errors.AuthenticationHostException.actions=log,logout

#===========================================================================

# ESAPI 校验器

#校验器的配置文件

Validator.ConfigurationFile=validation.properties

# Validators used by ESAPI

Validator.AccountName=^[a-zA-Z0-9]{3,20}$

Validator.SystemCommand=^[a-zA-Z\\-\\/]{1,64}$

Validator.RoleName=^[a-z]{1,20}$

#the word TEST below should be changed to your application

#name - only relative URL's are supported

Validator.Redirect=^\\/test.*$

# Global HTTP Validation Rules

# Values with Base64 encoded data (e.g. encrypted state) will need at least [a-zA-Z0-9\/+=]

Validator.HTTPScheme=^(http|https)$

Validator.HTTPServerName=^[a-zA-Z0-9_.\\-]*$

Validator.HTTPParameterName=^[a-zA-Z0-9_]{1,32}$

Validator.HTTPParameterValue=^[a-zA-Z0-9.\\-\\/+=@_ ]*$

Validator.HTTPCookieName=^[a-zA-Z0-9\\-_]{1,32}$

Validator.HTTPCookieValue=^[a-zA-Z0-9\\-\\/+=_ ]*$

# Note that max header name capped at 150 in SecurityRequestWrapper!

Validator.HTTPHeaderName=^[a-zA-Z0-9\\-_]{1,50}$

Validator.HTTPHeaderValue=^[a-zA-Z0-9()\\-=\\*\\.\\?;,+\\/:&_ ]*$

Validator.HTTPContextPath=^\\/?[a-zA-Z0-9.\\-\\/_]*$

Validator.HTTPServletPath=^[a-zA-Z0-9.\\-\\/_]*$

Validator.HTTPPath=^[a-zA-Z0-9.\\-_]*$

Validator.HTTPQueryString=^[a-zA-Z0-9()\\-=\\*\\.\\?;,+\\/:&_ %]*$

Validator.HTTPURI=^[a-zA-Z0-9()\\-=\\*\\.\\?;,+\\/:&_ ]*$

Validator.HTTPURL=^.*$

Validator.HTTPJSESSIONID=^[A-Z0-9]{10,30}$

# Validation of file related input

Validator.FileName=^[a-zA-Z0-9!@#$%^&{}\\[\\]()_+\\-=,.~'` ]{1,255}$

Validator.DirectoryName=^[a-zA-Z0-9:/\\\\!@#$%^&{}\\[\\]()_+\\-=,.~'` ]{1,255}$

# Validation of dates. Controls whether or not 'lenient' dates are accepted.

# See DataFormat.setLenient(boolean flag) for further details.

Validator.AcceptLenientDates=false

validation.properties

# 校验某个字段的正则表达式

Validator.SafeString=^[.\\p{Alnum}\\p{Space}]{0,1024}$

Validator.Email=^[A-Za-z0-9._%'-]+@[A-Za-z0-9.-]+\\.[a-zA-Z]{2,4}$

Validator.IPAddress=^(?:(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)\\.){3}(?:25[0-5]|2[0-4][0-9]|[01]?[0-9][0-9]?)$

Validator.URL=^(ht|f)tp(s?)\\:\\/\\/[0-9a-zA-Z]([-.\\w]*[0-9a-zA-Z])*(:(0-9)*)*(\\/?)([a-zA-Z0-9\\-\\.\\?\\,\\:\\'\\/\\\\\\+=&amp;%\\$#_]*)?$

Validator.CreditCard=^(\\d{4}[- ]?){3}\\d{4}$

Validator.SSN=^(?!000)([0-6]\\d{2}|7([0-6]\\d|7[012]))([ -]?)(?!00)\\d\\d\\3(?!0000)\\d{4}$

过滤器:在项目包下创建类 XssFilter实现Filter接口

import java.io.IOException;

import javax.servlet.Filter;

import javax.servlet.FilterChain;

import javax.servlet.FilterConfig;

import javax.servlet.ServletException;

import javax.servlet.ServletRequest;

import javax.servlet.ServletResponse;

import javax.servlet.annotation.WebFilter;

import javax.servlet.http.HttpServletRequest;

import org.slf4j.Logger;

import org.slf4j.LoggerFactory;

/**

* 描述 : 跨站请求防范

*

* @author

*

*/

@WebFilter(filterName = "xssFilter", urlPatterns = "/*", asyncSupported = true)

public class XssFilter implements Filter {

/**

* 描述 : 日志

*/

private static final Logger LOGGER = LoggerFactory.getLogger(XssFilter.class);

@Override

public void init(FilterConfig filterConfig) throws ServletException {

}

@Override

public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)

throws IOException, ServletException {

XssHttpServletRequestWrapper xssRequest = new XssHttpServletRequestWrapper((HttpServletRequest) request);

//System.out.println("进入XSS过滤器............");

chain.doFilter(xssRequest, response);

//System.out.println("过滤器XSS执行完......................");

}

@Override

public void destroy() {

}

}

敏感字符转换类:HttpServletRequestWrapper

import java.util.regex.Pattern;

import javax.servlet.http.HttpServletRequest;

import javax.servlet.http.HttpServletRequestWrapper;

import org.owasp.esapi.ESAPI;

public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper {

public XssHttpServletRequestWrapper(HttpServletRequest servletRequest) {

super(servletRequest);

}

public String[] getParameterValues(String parameter) {

String[] values = super.getParameterValues(parameter);

if (values == null) {

return null;

}

int count = values.length;

String[] encodedValues = new String[count];

for (int i = 0; i < count; i++) {

encodedValues[i] = cleanXSS(values[i]);

}

return encodedValues;

}

public String getParameter(String parameter) {

String value = super.getParameter(parameter);

if (value == null) {

return null;

}

return cleanXSS(value);

}

public String getHeader(String name) {

String value = super.getHeader(name);

if (value == null)

return null;

return cleanXSS(value);

}

// private String cleanXSS(String value) {

//

// //You'll need to remove the spaces from the html entities below

//

// value = value.replaceAll("<", "& lt;").replaceAll(">", "& gt;");

//

// value = value.replaceAll("\\(", "& #40;").replaceAll("\\)", "& #41;");

//

// value = value.replaceAll("'", "& #39;");

//

// value = value.replaceAll("eval\\((.*)\\)", "");

//

// value = value.replaceAll("[\\\"\\\'][\\s]*javascript:(.*)[\\\"\\\']", "\"\"");

//

// value = value.replaceAll("script", "");

//

// return value;

//

// }

private String cleanXSS(String value) {

if (value != null) {

// 推荐使用ESAPI库来避免脚本攻击

value = ESAPI.encoder().canonicalize(value);

// 避免空字符串

value = value.replaceAll("", "");

// 避免script 标签

Pattern scriptPattern = pile("<script>(.*?)</script>", Pattern.CASE_INSENSITIVE);

value = scriptPattern.matcher(value).replaceAll("");

// 避免src形式的表达式

scriptPattern = pile("src[\r\n]*=[\r\n]*\\\'(.*?)\\\'", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

scriptPattern = pile("src[\r\n]*=[\r\n]*\\\"(.*?)\\\"", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

// 删除单个的 </script> 标签

scriptPattern = pile("</script>", Pattern.CASE_INSENSITIVE);

value = scriptPattern.matcher(value).replaceAll("");

// 删除单个的<script ...> 标签

scriptPattern = pile("<script(.*?)>", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 eval(...) 形式表达式

scriptPattern = pile("eval\\((.*?)\\)", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 e­xpression(...) 表达式

scriptPattern = pile("expression\\((.*?)\\)", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 javascript: 表达式

scriptPattern = pile("javascript:", Pattern.CASE_INSENSITIVE);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 vbscript: 表达式

scriptPattern = pile("vbscript:", Pattern.CASE_INSENSITIVE);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 οnlοad= 表达式

scriptPattern = pile("onload(.*?)=", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

// 避免 onXX= 表达式

scriptPattern = pile("on.*(.*?)=", Pattern.CASE_INSENSITIVE | Pattern.MULTILINE | Pattern.DOTALL);

value = scriptPattern.matcher(value).replaceAll("");

}

return value;

}

}

创建配置类:XSSFilterConfig

import mon.xssfilter.XssFilter;

import org.springframework.boot.web.servlet.FilterRegistrationBean;

import org.springframework.context.annotation.Bean;

import org.springframework.context.annotation.Configuration;

import javax.servlet.Filter;

/**

* @author jxwen

* @create -10-19 9:14

* @desc

**/

@Configuration

public class XSSFilterConfig {

@Bean

public FilterRegistrationBean filterRegistrationBean() {

FilterRegistrationBean registration = new FilterRegistrationBean();

registration.setFilter(xssFilter());

registration.addUrlPatterns("/*");

registration.addInitParameter("paramName", "paramValue");

registration.setName("xssFilter");

return registration;

}

/**

* 创建一个bean

* @return

*/

@Bean(name = "xssFilter")

public Filter xssFilter() {

return new XssFilter();

}

}

配置完成, 架构如下:

END!!!!!!!

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。