diff --git a/pom.xml b/pom.xml index f944d7b9..31d1bbe4 100644 --- a/pom.xml +++ b/pom.xml @@ -29,7 +29,6 @@ 3.9.1 2.5 1.3.3 - 1.11.3 3.17 1.7 @@ -148,13 +147,6 @@ ${commons.fileupload.version} - - - org.jsoup - jsoup - ${jsoup.version} - - org.apache.poi diff --git a/ruoyi-common/pom.xml b/ruoyi-common/pom.xml index fe5fc81c..2eb06d1a 100644 --- a/ruoyi-common/pom.xml +++ b/ruoyi-common/pom.xml @@ -77,12 +77,6 @@ commons-fileupload - - - org.jsoup - jsoup - - org.apache.poi diff --git a/ruoyi-common/src/main/java/com/ruoyi/common/utils/html/EscapeUtil.java b/ruoyi-common/src/main/java/com/ruoyi/common/utils/html/EscapeUtil.java new file mode 100644 index 00000000..9b6e1587 --- /dev/null +++ b/ruoyi-common/src/main/java/com/ruoyi/common/utils/html/EscapeUtil.java @@ -0,0 +1,152 @@ +package com.ruoyi.common.utils.html; + +import com.ruoyi.common.utils.StringUtils; + +/** + * 转义和反转义工具类 + * + * @author ruoyi + */ +public class EscapeUtil +{ + public static final String RE_HTML_MARK = "(<[^<]*?>)|(<[\\s]*?/[^<]*?>)|(<[^<]*?/[\\s]*?>)"; + + private static final char[][] TEXT = new char[64][]; + + static + { + for (int i = 0; i < 64; i++) + { + TEXT[i] = new char[] { (char) i }; + } + + // special HTML characters + TEXT['\''] = "'".toCharArray(); // 单引号 + TEXT['"'] = """.toCharArray(); // 单引号 + TEXT['&'] = "&".toCharArray(); // &符 + TEXT['<'] = "<".toCharArray(); // 小于号 + TEXT['>'] = ">".toCharArray(); // 大于号 + } + + /** + * 转义文本中的HTML字符为安全的字符 + * + * @param text 被转义的文本 + * @return 转义后的文本 + */ + public static String escape(String text) + { + return encode(text); + } + + /** + * 还原被转义的HTML特殊字符 + * + * @param content 包含转义符的HTML内容 + * @return 转换后的字符串 + */ + public static String unescape(String content) + { + return decode(content); + } + + /** + * 清除所有HTML标签,但是不删除标签内的内容 + * + * @param content 文本 + * @return 清除标签后的文本 + */ + public static String clean(String content) + { + return content.replaceAll(RE_HTML_MARK, ""); + } + + /** + * Escape编码 + * + * @param text 被编码的文本 + * @return 编码后的字符 + */ + private static String encode(String text) + { + int len; + if ((text == null) || ((len = text.length()) == 0)) + { + return StringUtils.EMPTY; + } + StringBuilder buffer = new StringBuilder(len + (len >> 2)); + char c; + for (int i = 0; i < len; i++) + { + c = text.charAt(i); + if (c < 64) + { + buffer.append(TEXT[c]); + } + else + { + buffer.append(c); + } + } + return buffer.toString(); + } + + /** + * Escape解码 + * + * @param content 被转义的内容 + * @return 解码后的字符串 + */ + public static String decode(String content) + { + if (StringUtils.isEmpty(content)) + { + return content; + } + + StringBuilder tmp = new StringBuilder(content.length()); + int lastPos = 0, pos = 0; + char ch; + while (lastPos < content.length()) + { + pos = content.indexOf("%", lastPos); + if (pos == lastPos) + { + if (content.charAt(pos + 1) == 'u') + { + ch = (char) Integer.parseInt(content.substring(pos + 2, pos + 6), 16); + tmp.append(ch); + lastPos = pos + 6; + } + else + { + ch = (char) Integer.parseInt(content.substring(pos + 1, pos + 3), 16); + tmp.append(ch); + lastPos = pos + 3; + } + } + else + { + if (pos == -1) + { + tmp.append(content.substring(lastPos)); + lastPos = content.length(); + } + else + { + tmp.append(content.substring(lastPos, pos)); + lastPos = pos; + } + } + } + return tmp.toString(); + } + + public static void main(String[] args) + { + String html = ""; + System.out.println(EscapeUtil.clean(html)); + System.out.println(EscapeUtil.escape(html)); + System.out.println(EscapeUtil.unescape(html)); + } +} diff --git a/ruoyi-common/src/main/java/com/ruoyi/common/xss/XssHttpServletRequestWrapper.java b/ruoyi-common/src/main/java/com/ruoyi/common/xss/XssHttpServletRequestWrapper.java index be125f24..516db0a9 100644 --- a/ruoyi-common/src/main/java/com/ruoyi/common/xss/XssHttpServletRequestWrapper.java +++ b/ruoyi-common/src/main/java/com/ruoyi/common/xss/XssHttpServletRequestWrapper.java @@ -2,8 +2,7 @@ package com.ruoyi.common.xss; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletRequestWrapper; -import org.jsoup.Jsoup; -import org.jsoup.safety.Whitelist; +import com.ruoyi.common.utils.html.EscapeUtil; /** * XSS过滤处理 @@ -31,7 +30,7 @@ public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper for (int i = 0; i < length; i++) { // 防xss攻击和过滤前后空格 - escapseValues[i] = Jsoup.clean(values[i], Whitelist.relaxed()).trim(); + escapseValues[i] = EscapeUtil.clean(values[i]).trim(); } return escapseValues; }