What is XSS prevent
Cross-SiteScripting (XSS) attacks occur when:
跨站脚本攻击发生在以下情况:
1. Data enters a Web applicationthrough an untrusted source, most frequently a web request.
2. The data is included in dynamiccontent that is sent to a web user without being validated for maliciouscontent.
数据从一个不可信的来源进入到Web应用程序中(大多数通过web请求),并包含动态恶意内容而未经验证许可。
The malicious content sent to the web browser often takes theform of a segment of JavaScript, but may also include HTML, Flash, or any othertype of code that the browser may execute. The variety of attacks based on XSSis almost limitless, but they commonly include transmitting private data, likecookies or other session information, to the attacker, redirecting the victimto web content controlled by the attacker, or performing other maliciousoperations on the user's machine under the guise of the vulnerable site.
发送给浏览器的恶意内容通常携带了一段Javascript,同时包含HTML,Flash,或者其他可执行的代码。XSS的攻击方式是多种多样的,但他们基本都会盗取隐私数据,像Cookie或Session等信息,可以把受害者跳转至攻击者控制的网页或实施其他的恶意操作。(数据区域未经净化感染程序区域)
prevent XSS using servlet request filter.
config web.xml
<filter>
<filter-name>XSSFilter</filter-name>
<filter-class> com.synnex.cis.web.util.XSSFilter</filter-class>
</filter>
<filter-mapping>
<filter-name>XSSFilter</filter-name>
<url-pattern>/*</url-pattern>
</filter-mapping>
create XSSFilter.java
package com.synnex.cis.web.util;
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.http.HttpServletRequest;
public class XSSFilter implements Filter {
@Override
public void init(FilterConfig filterConfig) throws ServletException {
}
@Override
public void destroy() {
}
@Override
public void doFilter(ServletRequest request, ServletResponse response, FilterChain chain)
throws IOException, ServletException {
XSSRequestWrapper xssRequest = new XSSRequestWrapper((HttpServletRequest) request);
chain.doFilter(xssRequest, response);
}
}
create XSSRequestWrapper.java
package com.synnex.cis.web.util;
import java.util.regex.Pattern;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletRequestWrapper;
public class XSSRequestWrapper extends HttpServletRequestWrapper {
HttpServletRequest orgRequest = null;
public XSSRequestWrapper(HttpServletRequest request) {
super(request);
orgRequest = request;
}
@Override
public String getParameter(String name) {
String value = super.getParameter(xssEncode(name));
if (value != null) {
value = xssEncode(value);
}
return value;
}
@Override
public String getHeader(String name) {
String value = super.getHeader(xssEncode(name));
if (value != null) {
value = xssEncode(value);
}
return value;
}
public static String escape(String value) {
value = notNull(value);
if (value.equals(""))
return "";
StringBuffer result = new StringBuffer();
for (int i = 0; i < value.length(); i++) {
char ch = value.charAt(i);
if (ch == '<')
result.append("<");
else if (ch == '>')
result.append(">");
else if (ch == '&')
result.append("&");
else if (ch == '"')
result.append(""");
else if (ch == '\r')
result.append("<BR>");
else if (ch == '\n') {
if (value.charAt(i - 1) == '\r') {
} else
result.append("<BR>");
} else if (ch == '\t')
result.append("  ");
else if (ch == ' ')
result.append(" ");
else
result.append(ch);
}
return result.toString();
}
public static String notNull(String s) {
if (s == null || s.toString().trim().equals("")) {
return "";
} else {
return s.toString().trim();
}
}
public String xssEncode(String s) {
if (s == null || "".equals(s.trim())) {
return s;
}
String result = stripXSS(s);
if (null != result) {
result = escape(result);
}
return result;
}
private String stripXSS(String value) {
if (value != null) {
value = value.replaceAll("", "");
Pattern scriptPattern = Pattern.compile("<script>(.*?)</script>",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("src[\r\n]*=[\r\n]*\\\'(.*?)\\\'",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("src[\r\n]*=[\r\n]*\\\"(.*?)\\\"",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("</script>",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("<script(.*?)>",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("eval\\((.*?)\\)",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("expression\\((.*?)\\)",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("javascript:",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("vbscript:",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("onload(.*?)=",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("<iframe>(.*?)</iframe>",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("</iframe>",
Pattern.CASE_INSENSITIVE);
value = scriptPattern.matcher(value).replaceAll("");
scriptPattern = Pattern.compile("<iframe(.*?)>",
Pattern.CASE_INSENSITIVE | Pattern.MULTILINE
| Pattern.DOTALL);
value = scriptPattern.matcher(value).replaceAll("");
}
return value;
}
/**
* get request
*
* @return
*/
public HttpServletRequest getOrgRequest() {
return orgRequest;
}
/**
* get orignal request
*
* @return
*/
public static HttpServletRequest getOrgRequest(HttpServletRequest req) {
if (req instanceof XSSRequestWrapper) {
return ((XSSRequestWrapper) req).getOrgRequest();
}
return req;
}
}
这里推荐一个抓包工具:
上述代码有时候全局处理一些请求是不能有效防止XSS的, 比如这种 window.location.href="<%= url%>"; 是无法被filter 过滤到,也就是为什么其他的url都已经转义了,这里没有被转义的原因。这种情况的可以自己再单独转义。