1. 概述

在将 HTML 转换为纯文本时,如何保留原始的换行格式是一个常见但容易被忽略的问题。本文将聚焦于 使用 Jsoup 解析 HTML 到纯文本时,如何正确保留各类换行 —— 包括文本中的 \n 换行符,以及由 <br><p> 等标签带来的逻辑换行。

如果你直接用 Jsoup 默认方式处理,很可能发现换行全没了,变成一坨挤在一起的文本。✅ 这是踩坑高发区,尤其在处理用户输入富文本后需要转成摘要或预览时。

我们一步步来解决。


2. 保留原始 \n 换行符

Jsoup 默认行为是:把所有 \n 替换成空格。❌ 这显然不是我们想要的。

关键点:关闭 prettyPrint

要保留原始换行,必须关闭 Jsoup 的“美化输出”功能(prettyPrint)。否则,Jsoup 会自动格式化 HTML,把换行、缩进都干掉。

Document.OutputSettings outputSettings = new Document.OutputSettings();
outputSettings.prettyPrint(false); // ✅ 关键:关闭美化

然后使用 Jsoup.clean() 方法配合 Safelist.none()(即允许所有标签但只输出文本)来提取纯文本:

String strHTML = "<html><body>Hello\nworld</body></html>";
String strWithNewLines = Jsoup.clean(strHTML, "", Safelist.none(), outputSettings);

最终结果:

assertEquals("Hello\nworld", strWithNewLines);

✅ 成功保留了原始的 \n 换行!

⚠️ 注意:Safelist.none() 表示不保留任何标签,只提取文本内容。这是生成纯文本的标准做法。


3. 保留 <br><p> 标签对应的换行

更常见的需求是:HTML 中的 <br> 换行和 <p> 段落,应该转换为文本中的 \n

但默认情况下,Jsoup.clean() 会直接把这些标签“吃掉”,不会生成换行。❌

解决方案:先预处理 DOM,再提取文本

思路很简单:

  1. 先用 Jsoup.parse() 解析成 Document 对象
  2. 手动在 <br><p> 前插入 \n
  3. 再转回 HTML 字符串
  4. 最后用 clean() 提取纯文本

代码如下:

String strHTML = "<html><body>Hello<br>World<p>Paragraph</p></body></html>";
Document jsoupDoc = Jsoup.parse(strHTML);

设置输出选项并插入换行:

Document.OutputSettings outputSettings = new Document.OutputSettings();
outputSettings.prettyPrint(false); // ✅ 必须关闭美化
jsoupDoc.outputSettings(outputSettings);

jsoupDoc.select("br").before("\\n"); // 在 <br> 前加 \n
jsoupDoc.select("p").before("\\n");  // 在 <p> 前加 \n

⚠️ 注意:before("\\n") 中是双反斜杠,因为 Java 字符串要转义。

获取处理后的 HTML 字符串,并将 \\n 还原为 \n

String str = jsoupDoc.html().replaceAll("\\\\n", "\n");

最后提取纯文本:

String strWithNewLines = Jsoup.clean(str, "", Safelist.none(), outputSettings);

输出结果:

assertEquals("Hello\nWorld\nParagraph", strWithNewLines);

✅ 完美保留了 <br><p> 对应的换行。


4. 总结

场景 关键操作
保留文本中的 \n 关闭 prettyPrint,直接 clean
保留 <br><p> 换行 parse 成 Document,select().before("\\n"),再 clean

核心要点:

  • ✅ 必须设置 outputSettings.prettyPrint(false)
  • ✅ 使用 Safelist.none() 配合 clean() 提取纯文本
  • ✅ 对 <br><p> 等标签,先在 DOM 层插入 \n 再转换

这些技巧在处理用户生成内容(UGC)、富文本摘要、邮件正文提取等场景非常实用。别再让换行符莫名消失啦!

所有示例代码已托管至 GitHub:https://github.com/baeldung/tutorials/tree/master/jsoup


原始标题:Preserving Line Breaks When Using Jsoup