从string中移除HTML标签

有没有从Javastring中删除HTML的好方法? 一个简单的正则expression式

replaceAll("\\<.*?>","") 

会工作,但是像&amp; 将不会正确转换,两个尖括号之间的非HTML将被删除(即正则expression式中的.*?将消失)。

使用HTMLparsing器,而不是正则expression式。 这对于Jsoup来说简单而言很简单。

 public static String html2text(String html) { return Jsoup.parse(html).text(); } 

Jsoup还支持删除HTML标签对一个可定制的白名单,这是非常有用的,如果你只允许例如<b><i><u>

也可以看看:

  • RegEx匹配除XHTML自包含标签之外的开放标签
  • 领先的Java HTMLparsing器有什么优点和缺点?
  • 我正在寻找一个Java的HTML编码器
  • JSP / Servlet Web应用程序中的XSS预防

如果你正在为Android写作,你可以这样做…

 android.text.Html.fromHtml(instruction).toString() 

如果用户input<b>hey!</b> ,你想要显示<b>hey!</b>或者hey! ? 如果第一个,逃逸less-thans,和html-编码&符号(和可选的引号),你很好。 对代码实施第二种select的修改是:

 replaceAll("\\<[^>]*>","") 

但如果用户input格式不正确的内容,则会遇到问题,如<bhey!</b>

你也可以检查出JTidy ,它将parsing“脏”的htmlinput,并应该给你一个方法来删除标签,保持文本。

试图剥离html的问题是,浏览器有非常宽松的parsing器,比任何你可以find的库更宽松,所以即使你最好去除所有的标签(使用上面的replace方法,一个DOM库,或JTidy) ,您仍然需要确保编码任何剩余的HTML特殊字符以保证您的输出安全。

另一种方法是使用javax.swing.text.html.HTMLEditorKit来提取文本。

 import java.io.*; import javax.swing.text.html.*; import javax.swing.text.html.parser.*; public class Html2Text extends HTMLEditorKit.ParserCallback { StringBuffer s; public Html2Text() { } public void parse(Reader in) throws IOException { s = new StringBuffer(); ParserDelegator delegator = new ParserDelegator(); // the third parameter is TRUE to ignore charset directive delegator.parse(in, this, Boolean.TRUE); } public void handleText(char[] text, int pos) { s.append(text); } public String getText() { return s.toString(); } public static void main(String[] args) { try { // the HTML to convert FileReader in = new FileReader("java-new.html"); Html2Text parser = new Html2Text(); parser.parse(in); in.close(); System.out.println(parser.getText()); } catch (Exception e) { e.printStackTrace(); } } } 

ref: 从文件中删除HTML标签,只提取TEXT

也很简单,使用杰里科 ,你可以保留一些格式(例如换行符和链接)。

  Source htmlSource = new Source(htmlText); Segment htmlSeg = new Segment(htmlSource, 0, htmlSource.length()); Renderer htmlRend = new Renderer(htmlSeg); System.out.println(htmlRend.toString()); 

我认为过滤html标签最简单的方法是:

 private static final Pattern REMOVE_TAGS = Pattern.compile("<.+?>"); public static String removeTags(String string) { if (string == null || string.length() == 0) { return string; } Matcher m = REMOVE_TAGS.matcher(string); return m.replaceAll(""); } 

在Android上,试试这个:

 String result = Html.fromHtml(html).toString(); 

HTML转义真的很难做对 – 我肯定会build议使用库代码来做到这一点,因为它比你想象的要微妙得多。 查看Apache的StringEscapeUtils来获得一个相当好的库来处理Java中的这个问题。

接受的答案只是简单的Jsoup.parse(html).text()有两个潜在的问题(使用JSoup 1.7.3):

  • 它从文本中删除换行符
  • 它将文本&lt;script&gt;<script>

如果你用这个防止XSS,这有点烦人。 这里是我使用JSoup和Apache的StringEscapeUtils改进解决scheme的最佳select:

 // breaks multi-level of escaping, preventing &amp;lt;script&amp;gt; to be rendered as <script> String replace = input.replace("&amp;", ""); // decode any encoded html, preventing &lt;script&gt; to be rendered as <script> String html = StringEscapeUtils.unescapeHtml(replace); // remove all html tags, but maintain line breaks String clean = Jsoup.clean(html, "", Whitelist.none(), new Document.OutputSettings().prettyPrint(false)); // decode html again to convert character entities back into text return StringEscapeUtils.unescapeHtml(clean); 

请注意,最后一步是因为我需要使用纯文本的输出。 如果你只需要HTML输出,那么你应该能够删除它。

这里有一堆testing用例(input到输出):

 {"regular string", "regular string"}, {"<a href=\"link\">A link</a>", "A link"}, {"<script src=\"http://evil.url.com\"/>", ""}, {"&lt;script&gt;", ""}, {"&amp;lt;script&amp;gt;", "lt;scriptgt;"}, // best effort {"\" ' > < \n \\ é å à ü and & preserved", "\" ' > < \n \\ é å à ü and & preserved"} 

如果你find一个更好的方法,请让我知道。

在剥离HTML之前,你可能想用换行符replace<br/> </p></p>标签,以防止它像Tim所暗示的那样变成一个难以辨认的混乱。

我可以考虑删除HTML标签但在尖括号之间留下非HTML的唯一方法是检查HTML标签列表 。 沿着这些线路的东西…

 replaceAll("\\<[\s]*tag[^>]*>","") 

然后HTML解码特殊字符,例如&amp; 。 结果不应该被认为是消毒。

我接受的答案对我来说不适用于我所说的testing用例:“a <b或b> c”的结果是“ab或b> c”。

所以,我用TagSoup代替。 这里有一个适用于我的testing案例(和其他几个)的镜头:

 import java.io.IOException; import java.io.StringReader; import java.util.logging.Logger; import org.ccil.cowan.tagsoup.Parser; import org.xml.sax.Attributes; import org.xml.sax.ContentHandler; import org.xml.sax.InputSource; import org.xml.sax.Locator; import org.xml.sax.SAXException; import org.xml.sax.XMLReader; /** * Take HTML and give back the text part while dropping the HTML tags. * * There is some risk that using TagSoup means we'll permute non-HTML text. * However, it seems to work the best so far in test cases. * * @author dan * @see <a href="http://home.ccil.org/~cowan/XML/tagsoup/">TagSoup</a> */ public class Html2Text2 implements ContentHandler { private StringBuffer sb; public Html2Text2() { } public void parse(String str) throws IOException, SAXException { XMLReader reader = new Parser(); reader.setContentHandler(this); sb = new StringBuffer(); reader.parse(new InputSource(new StringReader(str))); } public String getText() { return sb.toString(); } @Override public void characters(char[] ch, int start, int length) throws SAXException { for (int idx = 0; idx < length; idx++) { sb.append(ch[idx+start]); } } @Override public void ignorableWhitespace(char[] ch, int start, int length) throws SAXException { sb.append(ch); } // The methods below do not contribute to the text @Override public void endDocument() throws SAXException { } @Override public void endElement(String uri, String localName, String qName) throws SAXException { } @Override public void endPrefixMapping(String prefix) throws SAXException { } @Override public void processingInstruction(String target, String data) throws SAXException { } @Override public void setDocumentLocator(Locator locator) { } @Override public void skippedEntity(String name) throws SAXException { } @Override public void startDocument() throws SAXException { } @Override public void startElement(String uri, String localName, String qName, Attributes atts) throws SAXException { } @Override public void startPrefixMapping(String prefix, String uri) throws SAXException { } } 

这里有一个更丰富的更新,试图处理一些格式的rest和列表。 我用Amaya的输出作为指导。

 import java.io.IOException; import java.io.Reader; import java.io.StringReader; import java.util.Stack; import java.util.logging.Logger; import javax.swing.text.MutableAttributeSet; import javax.swing.text.html.HTML; import javax.swing.text.html.HTMLEditorKit; import javax.swing.text.html.parser.ParserDelegator; public class HTML2Text extends HTMLEditorKit.ParserCallback { private static final Logger log = Logger .getLogger(Logger.GLOBAL_LOGGER_NAME); private StringBuffer stringBuffer; private Stack<IndexType> indentStack; public static class IndexType { public String type; public int counter; // used for ordered lists public IndexType(String type) { this.type = type; counter = 0; } } public HTML2Text() { stringBuffer = new StringBuffer(); indentStack = new Stack<IndexType>(); } public static String convert(String html) { HTML2Text parser = new HTML2Text(); Reader in = new StringReader(html); try { // the HTML to convert parser.parse(in); } catch (Exception e) { log.severe(e.getMessage()); } finally { try { in.close(); } catch (IOException ioe) { // this should never happen } } return parser.getText(); } public void parse(Reader in) throws IOException { ParserDelegator delegator = new ParserDelegator(); // the third parameter is TRUE to ignore charset directive delegator.parse(in, this, Boolean.TRUE); } public void handleStartTag(HTML.Tag t, MutableAttributeSet a, int pos) { log.info("StartTag:" + t.toString()); if (t.toString().equals("p")) { if (stringBuffer.length() > 0 && !stringBuffer.substring(stringBuffer.length() - 1) .equals("\n")) { newLine(); } newLine(); } else if (t.toString().equals("ol")) { indentStack.push(new IndexType("ol")); newLine(); } else if (t.toString().equals("ul")) { indentStack.push(new IndexType("ul")); newLine(); } else if (t.toString().equals("li")) { IndexType parent = indentStack.peek(); if (parent.type.equals("ol")) { String numberString = "" + (++parent.counter) + "."; stringBuffer.append(numberString); for (int i = 0; i < (4 - numberString.length()); i++) { stringBuffer.append(" "); } } else { stringBuffer.append("* "); } indentStack.push(new IndexType("li")); } else if (t.toString().equals("dl")) { newLine(); } else if (t.toString().equals("dt")) { newLine(); } else if (t.toString().equals("dd")) { indentStack.push(new IndexType("dd")); newLine(); } } private void newLine() { stringBuffer.append("\n"); for (int i = 0; i < indentStack.size(); i++) { stringBuffer.append(" "); } } public void handleEndTag(HTML.Tag t, int pos) { log.info("EndTag:" + t.toString()); if (t.toString().equals("p")) { newLine(); } else if (t.toString().equals("ol")) { indentStack.pop(); ; newLine(); } else if (t.toString().equals("ul")) { indentStack.pop(); ; newLine(); } else if (t.toString().equals("li")) { indentStack.pop(); ; newLine(); } else if (t.toString().equals("dd")) { indentStack.pop(); ; } } public void handleSimpleTag(HTML.Tag t, MutableAttributeSet a, int pos) { log.info("SimpleTag:" + t.toString()); if (t.toString().equals("br")) { newLine(); } } public void handleText(char[] text, int pos) { log.info("Text:" + new String(text)); stringBuffer.append(text); } public String getText() { return stringBuffer.toString(); } public static void main(String args[]) { String html = "<html><body><p>paragraph at start</p>hello<br />What is happening?<p>this is a<br />mutiline paragraph</p><ol> <li>This</li> <li>is</li> <li>an</li> <li>ordered</li> <li>list <p>with</p> <ul> <li>another</li> <li>list <dl> <dt>This</dt> <dt>is</dt> <dd>sdasd</dd> <dd>sdasda</dd> <dd>asda <p>aasdas</p> </dd> <dd>sdada</dd> <dt>fsdfsdfsd</dt> </dl> <dl> <dt>vbcvcvbcvb</dt> <dt>cvbcvbc</dt> <dd>vbcbcvbcvb</dd> <dt>cvbcv</dt> <dt></dt> </dl> <dl> <dt></dt> </dl></li> <li>cool</li> </ul> <p>stuff</p> </li> <li>cool</li></ol><p></p></body></html>"; System.out.println(convert(html)); } } 

使用Html.fromHtml

HTML标签是

 <a href=”…”> <b>, <big>, <blockquote>, <br>, <cite>, <dfn> <div align=”…”>, <em>, <font size=”…” color=”…” face=”…”> <h1>, <h2>, <h3>, <h4>, <h5>, <h6> <i>, <p>, <small> <strike>, <strong>, <sub>, <sup>, <tt>, <u> 

根据Android的官方文档HTML中的任何标签都会显示为一个通用的replacestring ,然后您的程序可以通过并replace为真正的string

Html.formHtml方法需要一个Html.TagHandler和一个Html.ImageGetter作为参数以及parsing的文本。

 String Str_Html=" <p>This is about me text that the user can put into their profile</p> "; 

然后

 Your_TextView_Obj.setText(Html.fromHtml(Str_Html).toString()); 

产量

这是关于我的文字,用户可以把他们的个人资料

还有一种方法可以使用com.google.gdata.util.common.html.HtmlToText类

 MyWriter.toConsole(HtmlToText.htmlToPlainText(htmlResponse)); 

这不是防弹代码,当我在维基百科条目上运行时,我也获得了样式信息。 不过,我相信对于小型/简单的工作,这将是有效的。

我知道这是旧的,但我只是在一个项目,需要我过滤HTML,这工作得很好:

 noHTMLString.replaceAll("\\&.*?\\;", ""); 

而不是这个:

 html = html.replaceAll("&nbsp;",""); html = html.replaceAll("&amp;".""); 

这听起来像你想从HTML到纯文本。
如果是这样的话,请看www.htmlparser.org。 这里是一个例子,从URL中find的HTML文件中去掉所有的标签。
它使用org.htmlparser.beans.StringBean

 static public String getUrlContentsAsText(String url) { String content = ""; StringBean stringBean = new StringBean(); stringBean.setURL(url); content = stringBean.getStrings(); return content; } 

这是另一种方式来做到这一点:

 public static String removeHTML(String input) { int i = 0; String[] str = input.split(""); String s = ""; boolean inTag = false; for (i = input.indexOf("<"); i < input.indexOf(">"); i++) { inTag = true; } if (!inTag) { for (i = 0; i < str.length; i++) { s = s + str[i]; } } return s; } 

或者,可以使用HtmlCleaner :

 private CharSequence removeHtmlFrom(String html) { return new HtmlCleaner().clean(html).getText(); } 

也可以使用Apache Tika来达到这个目的。 默认情况下,它会保留被剥离的html中的空格,这在某些情况下可能是需要的:

 InputStream htmlInputStream = .. HtmlParser htmlParser = new HtmlParser(); HtmlContentHandler htmlContentHandler = new HtmlContentHandler(); htmlParser.parse(htmlInputStream, htmlContentHandler, new Metadata()) System.out.println(htmlContentHandler.getBodyText().trim()) 

我的5美分:

 String[] temp = yourString.split("&amp;"); String tmp = ""; if (temp.length > 1) { for (int i = 0; i < temp.length; i++) { tmp += temp[i] + "&"; } yourString = tmp.substring(0, tmp.length() - 1); } 

要获得合法的纯HTML文本,你可以这样做:

 String BR_ESCAPED = "&lt;br/&gt;"; Element el=Jsoup.parse(html).select("body"); el.select("br").append(BR_ESCAPED); el.select("p").append(BR_ESCAPED+BR_ESCAPED); el.select("h1").append(BR_ESCAPED+BR_ESCAPED); el.select("h2").append(BR_ESCAPED+BR_ESCAPED); el.select("h3").append(BR_ESCAPED+BR_ESCAPED); el.select("h4").append(BR_ESCAPED+BR_ESCAPED); el.select("h5").append(BR_ESCAPED+BR_ESCAPED); String nodeValue=el.text(); nodeValue=nodeValue.replaceAll(BR_ESCAPED, "<br/>"); nodeValue=nodeValue.replaceAll("(\\s*<br[^>]*>){3,}", "<br/><br/>"); 

合并纯文本更改\ n并更改最后一行:

 nodeValue=nodeValue.replaceAll("(\\s*\n){3,}", "<br/><br/>"); 

从string中删除HTML标签。 某处我们需要parsing一些由服务器响应Httpresponse等响应的string。

所以我们需要parsing它。

这里我将展示如何从string中删除html标签。

  // sample text with tags string str = "<html><head>sdfkashf sdf</head><body>sdfasdf</body></html>"; // regex which match tags System.Text.RegularExpressions.Regex rx = new System.Text.RegularExpressions.Regex("<[^>]*>"); // replace all matches with empty strin str = rx.Replace(str, ""); //now str contains string without html tags 

使用JSoup保留新行信息的一种方法是在所有新的行标记之前添加一些虚拟string,执行JSoup并用“\ n”replace虚拟string。

 String html = "<p>Line one</p><p>Line two</p>Line three<br/>etc."; String NEW_LINE_MARK = "NEWLINESTART1234567890NEWLINEEND"; for (String tag: new String[]{"</p>","<br/>","</h1>","</h2>","</h3>","</h4>","</h5>","</h6>","</li>"}) { html = html.replace(tag, NEW_LINE_MARK+tag); } String text = Jsoup.parse(html).text(); text = text.replace(NEW_LINE_MARK + " ", "\n\n"); text = text.replace(NEW_LINE_MARK, "\n\n"); 

这应该工作 –

用这个

  text.replaceAll('<.*?>' , " ") -> This will replace all the html tags with a space. 

和这个

  text.replaceAll('&.*?;' , "")-> this will replace all the tags which starts with "&" and ends with ";" like &nbsp;, &amp;, &gt; etc. 

你可以简单地使用多个replaceAll()方法

 String RemoveTag(String html){ html = html.replaceAll("\\<.*?>","") html = html.replaceAll("&nbsp;",""); html = html.replaceAll("&amp;".""); ---------- ---------- return html; } 

使用此链接您需要的最常见的replace: http : //tunes.org/wiki/html_20special_20characters_20and_20symbols.html

这是简单而有效的。 我首先使用这种方法删除垃圾,但不是第一行,即replaceAll(“\ <。*?>”,“”),后来我使用特定的关键字search索引,然后使用.substring(开始,结束)方法去掉不必要的东西。 由于这个function更加强大,您可以在整个html页面中精确定位您需要的内容。