? ? jsoup 是一款非常优秀的处理HTML的java工具,最大的特点就是拥有类似jquery的select操作。使用非常简单,但是最近本人在使用过程中,由于不熟悉踩了一个坑,记录已备忘。
?
代码如下: ? ?
public static void main(String[] args) {
String content = "<a href=\"test.html\" title=\"men tshirt\" >men tshirt</a>";
try {
Document document = Jsoup.parse(content);
Elements links = document.select("a");
for (Element link : links) {
link.attr("clickdata", "adfafgadsfaf");
if (!link.hasClass("click-target-with-quot")) {
link.addClass("click-target-with-quot");
}
}
System.out.println(document.html());// 错误代码
System.out.println(document.body().html());//正确代码
} catch (Exception e) {
}
}
?
需求也很简单,将一个HTML片段中的所有的<a>标签,增加一个class,和一个自定义属性。
代码中红色标注了错误和正确的代码,区别在于错误的代码会返回添加了<html>等头尾的标签。
?
<html> <head></head> <body> <a href="test.html" title="men tshirt" clickdata="adfafgadsfaf" class=" click-target-with-quot">men tshirt</a> </body> </html>
?
正确的如下:
<a href="test.html" title="men tshirt" clickdata="adfafgadsfaf" class=" click-target-with-quot">men tshirt</a>
?
原因在于:在 Jsoup.parse解析的时候在类HtmlTreeBuilderState类中会判断是否属于BeforeHtml,BeforeHead等等状态,如果满足的话会被强制添加<html>标签。
具体代码如下:
BeforeHtml { boolean process(Token t, HtmlTreeBuilder tb) { if (t.isDoctype()) { tb.error(this); return false; } else if (t.isComment()) { tb.insert(t.asComment()); } else if (isWhitespace(t)) { return true; // ignore whitespace } else if (t.isStartTag() && t.asStartTag().name().equals("html")) { tb.insert(t.asStartTag()); tb.transition(BeforeHead); } else if (t.isEndTag() && (StringUtil.in(t.asEndTag().name(), "head", "body", "html", "br"))) { return anythingElse(t, tb); } else if (t.isEndTag()) { tb.error(this); return false; } else { return anythingElse(t, tb); } return true; } private boolean anythingElse(Token t, HtmlTreeBuilder tb) { tb.insert("html"); tb.transition(BeforeHead); return tb.process(t); } }
?
?
?
?
本站支持?pay for your wishes