【问题标题】:Jsoup.clean without adding html entitiesJsoup.clean 不添加 html 实体
【发布时间】:2012-01-30 18:23:20
【问题描述】:

我正在使用清除不需要的 HTML 标记(例如 <script>)中的一些文本

String clean = Jsoup.clean(someInput, Whitelist.basicWithImages());

问题在于它用å 替换了例如å(这给我带来了麻烦,因为它不是“纯xml”)。

例如

Jsoup.clean("hello å <script></script> world", Whitelist.basicWithImages())

产量

"hello &aring;  world"

但我愿意

"hello å  world"

有没有简单的方法来实现这一点? (即比在结果中将&amp;aring; 转换回å 更简单。)

【问题讨论】:

    标签: java html jsoup html-entities


    【解决方案1】:

    您可以配置 Jsoup 的转义模式:使用 EscapeMode.xhtml 将为您提供不带实体的输出。

    这是一个完整的 sn-p,它接受 str 作为输入,并使用 Whitelist.simpleText() 清理它:

    // Parse str into a Document
    Document doc = Jsoup.parse(str);
    
    // Clean the document.
    doc = new Cleaner(Whitelist.simpleText()).clean(doc);
    
    // Adjust escape mode
    doc.outputSettings().escapeMode(EscapeMode.xhtml);
    
    // Get back the string of the body.
    str = doc.body().html();
    

    【讨论】:

    【解决方案2】:

    Jsoup 的网站上已经有功能请求。您可以通过添加新的空 Map 和新的转义类型来自己扩展源代码。如果您不想这样做,可以使用 apache commons 中的 StringEscapeUtils。

    public static String getTextOnlyFromHtmlText(String htmlText){
        Document doc = Jsoup.parse( htmlText );
        doc.outputSettings().charset("UTF-8");
        htmlText = Jsoup.clean( doc.body().html(), Whitelist.simpleText() );
        htmlText = StringEscapeUtils.unescapeHtml(htmlText);
        return htmlText;
    }
    

    【讨论】:

    • StringEscapeUtils 方法 Frank 的优点。非常有用,不仅在这种情况下
    • @frandevel 这将是一个非常糟糕的主意。如果输入的是&amp;lt;script&amp;gt;alert('Hello');&amp;lt;/script&amp;gt;,你实际上会注入不安全的HTML并允许XSS攻击。
    • 这个功能现在已经在 J​​soup 中实现了。请参阅 Parser.unescapeEntities,jsoup.org/apidocs/org/jsoup/parser/Parser.html
    • @GuillaumePolet 有趣的一点,那么你如何清理像这样&amp;lt;script&amp;gt;alert('Hello');&amp;lt;/script&amp;gt; 的输入?
    【解决方案3】:

    &bmoc 的回答工作正常,但您可以使用更短的解决方案:

    // Clean html
    Jsoup.clean(someInput, "yourBaseUriOrEmpty", Whitelist.simpleText(), new OutputSettings().escapeMode(EscapeMode.xhtml))
    

    【讨论】:

      【解决方案4】:

      更简单的方法是

      // clean the html
      String output = Jsoup.clean(html, Whitelist.basicWithImages());
      
      // Parse string into a document
      Document doc = Jsoup.parse(output);
      
      // Adjust escape mode
      doc.outputSettings().escapeMode(EscapeMode.xhtml);
      
      // Get back the string
      System.out.println(doc.body().html());
      

      我已经测试过了,它可以工作

      【讨论】:

        【解决方案5】:

        接受的答案是使用Jsoup.parse,在快速浏览源代码后,它似乎比Jsoup.clean 中发生的事情更重要。

        我复制了Jsoup.clean(...)的源代码并添加了设置转义模式的行。这应该避免 parse 方法完成一些不必要的步骤,因为它不必解析整个 html 文档而只需处理一个片段。

        private String clean(String html, Whitelist whitelist) {
            Document dirty = Jsoup.parseBodyFragment(html, "");
            Cleaner cleaner = new Cleaner(whitelist);
            Document clean = cleaner.clean(dirty);
            clean.outputSettings().escapeMode(EscapeMode.xhtml);
            return clean.body().html();
        }
        

        【讨论】:

          【解决方案6】:

          简单的方法:

          EscapeMode em = EscapeMode.xhtml;
          em.getMap().clear();
          
          doc.outputSettings().escapeMode(em);
          

          这将删除 ALL html 实体,包括:'、"、&、EscapeMode.xhtml 允许这些实体。

          【讨论】:

            【解决方案7】:

            将 HTML 解析为 Document,然后使用 Cleaner 清理文档并生成另一个,获取文档的 outputSettings 并将相应的字符集和转义模式设置为 xhtml,然后将文档转换为 String。未经测试,但应该可以工作。

            【讨论】:

              猜你喜欢
              • 1970-01-01
              • 2023-04-01
              • 1970-01-01
              • 2016-06-04
              • 2014-11-30
              • 1970-01-01
              • 1970-01-01
              • 2022-01-05
              • 1970-01-01
              相关资源
              最近更新 更多