提交 | 用户 | 时间
|
e7c126
|
1 |
package com.iailab.framework.xss.core.clean; |
H |
2 |
|
|
3 |
import org.jsoup.Jsoup; |
|
4 |
import org.jsoup.nodes.Document; |
|
5 |
import org.jsoup.safety.Safelist; |
|
6 |
|
|
7 |
/** |
|
8 |
* 基于 JSONP 实现 XSS 过滤字符串 |
|
9 |
*/ |
|
10 |
public class JsoupXssCleaner implements XssCleaner { |
|
11 |
|
|
12 |
private final Safelist safelist; |
|
13 |
|
|
14 |
/** |
|
15 |
* 用于在 src 属性使用相对路径时,强制转换为绝对路径。 为空时不处理,值应为绝对路径的前缀(包含协议部分) |
|
16 |
*/ |
|
17 |
private final String baseUri; |
|
18 |
|
|
19 |
/** |
|
20 |
* 无参构造,默认使用 {@link JsoupXssCleaner#buildSafelist} 方法构建一个安全列表 |
|
21 |
*/ |
|
22 |
public JsoupXssCleaner() { |
|
23 |
this.safelist = buildSafelist(); |
|
24 |
this.baseUri = ""; |
|
25 |
} |
|
26 |
|
|
27 |
/** |
|
28 |
* 构建一个 Xss 清理的 Safelist 规则。 |
|
29 |
* 基于 Safelist#relaxed() 的基础上: |
|
30 |
* 1. 扩展支持了 style 和 class 属性 |
|
31 |
* 2. a 标签额外支持了 target 属性 |
|
32 |
* 3. img 标签额外支持了 data 协议,便于支持 base64 |
|
33 |
* |
|
34 |
* @return Safelist |
|
35 |
*/ |
|
36 |
private Safelist buildSafelist() { |
|
37 |
// 使用 jsoup 提供的默认的 |
|
38 |
Safelist relaxedSafelist = Safelist.relaxed(); |
|
39 |
// 富文本编辑时一些样式是使用 style 来进行实现的 |
|
40 |
// 比如红色字体 style="color:red;", 所以需要给所有标签添加 style 属性 |
|
41 |
// 注意:style 属性会有注入风险 <img STYLE="background-image:url(javascript:alert('XSS'))"> |
|
42 |
relaxedSafelist.addAttributes(":all", "style", "class"); |
|
43 |
// 保留 a 标签的 target 属性 |
|
44 |
relaxedSafelist.addAttributes("a", "target"); |
|
45 |
// 支持img 为base64 |
|
46 |
relaxedSafelist.addProtocols("img", "src", "data"); |
|
47 |
|
|
48 |
// 保留相对路径, 保留相对路径时,必须提供对应的 baseUri 属性,否则依然会被删除 |
|
49 |
// WHITELIST.preserveRelativeLinks(false); |
|
50 |
|
|
51 |
// 移除 a 标签和 img 标签的一些协议限制,这会导致 xss 防注入失效,如 <img src=javascript:alert("xss")> |
|
52 |
// 虽然可以重写 WhiteList#isSafeAttribute 来处理,但是有隐患,所以暂时不支持相对路径 |
|
53 |
// WHITELIST.removeProtocols("a", "href", "ftp", "http", "https", "mailto"); |
|
54 |
// WHITELIST.removeProtocols("img", "src", "http", "https"); |
|
55 |
return relaxedSafelist; |
|
56 |
} |
|
57 |
|
|
58 |
@Override |
|
59 |
public String clean(String html) { |
|
60 |
return Jsoup.clean(html, baseUri, safelist, new Document.OutputSettings().prettyPrint(false)); |
|
61 |
} |
|
62 |
|
|
63 |
} |
|
64 |
|