Удалить теги HTML из строки - PullRequest
       232

Удалить теги HTML из строки

395 голосов
/ 27 октября 2008

Есть ли хороший способ удалить HTML из строки Java? Простое регулярное выражение типа

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

будет работать, но такие вещи, как &amp;, не будут правильно конвертированы, а не-HTML между двумя угловыми скобками будут удалены (т.е. .*? в регулярном выражении исчезнет)

Ответы [ 28 ]

527 голосов
/ 30 июня 2010

Используйте анализатор HTML вместо регулярных выражений. Это очень просто с Jsoup .

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

Jsoup также поддерживает удаление тегов HTML из настраиваемого белого списка, что очень полезно, если вы хотите разрешить только, например, <b>, <i> и <u>.

Смотри также:

263 голосов
/ 17 июня 2011

Если вы пишете для Android , вы можете сделать это ...

android.text.Html.fromHtml(instruction).toString()
77 голосов
/ 27 октября 2008

Если пользователь вводит <b>hey!</b>, вы хотите отобразить <b>hey!</b> или hey!? Если первое, избегайте меньше чем, и закодируйте амперсанды html (и, возможно, кавычки), и все в порядке. Модификация вашего кода для реализации второго варианта будет:

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

но вы столкнетесь с проблемами, если пользователь введет что-то искаженное, например <bhey!</b>.

Вы также можете проверить JTidy , который проанализирует «грязный» ввод html и даст вам возможность удалить теги, сохраняя текст.

Проблема с попыткой лишить html заключается в том, что браузеры имеют очень мягкие парсеры, более мягкие, чем любая библиотека, которую вы можете найти, поэтому даже если вы приложите все усилия, чтобы удалить все теги (используя метод замены выше, библиотека DOM или JTidy), вам все еще необходимо будет убедиться, что все оставшиеся специальные символы HTML кодированы, чтобы обеспечить безопасность вывода.

28 голосов
/ 18 января 2009

Другой способ - использовать 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 из файла, чтобы извлечь только текст

23 голосов
/ 04 ноября 2010

Я думаю, что самый простой способ фильтрации тегов 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("");
}
18 голосов
/ 06 августа 2011

Также очень просто использовать Иерихон , и вы можете сохранить часть форматирования (разрывы строк и ссылки, например).

    Source htmlSource = new Source(htmlText);
    Segment htmlSeg = new Segment(htmlSource, 0, htmlSource.length());
    Renderer htmlRend = new Renderer(htmlSeg);
    System.out.println(htmlRend.toString());
15 голосов
/ 04 мая 2015

На Android попробуйте это:

String result = Html.fromHtml(html).toString();
12 голосов
/ 27 октября 2008

Экранирование HTML действительно трудно сделать правильно - я бы определенно предложил использовать библиотечный код, чтобы сделать это, так как он намного более тонкий, чем вы думаете. Проверьте Apache StringEscapeUtils для довольно хорошей библиотеки для обработки этого в Java.

12 голосов
/ 13 мая 2014

Принятый ответ на простой Jsoup.parse(html).text() имеет 2 потенциальных проблемы (с JSoup 1.7.3):

  • Удаляет разрывы строк из текста
  • Преобразует текст &lt;script&gt; в <script>

Если вы используете это для защиты от XSS, это немного раздражает. Вот мой лучший пример улучшенного решения с использованием JSoup и Apache StringEscapeUtils:

// 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, вы сможете удалить его.

А вот несколько тестов (входные и выходные данные):

{"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"}

Если вы найдете способ сделать это лучше, пожалуйста, дайте мне знать.

6 голосов
/ 28 октября 2008

Возможно, вы захотите заменить теги <br/> и </p> символами новой строки перед тем, как удалить HTML, чтобы он не стал неразборчивым беспорядком, как предполагает Тим.

Единственный способ, с помощью которого я могу удалить теги HTML, но оставить не-HTML между угловыми скобками, это проверить список тегов HTML . Что-то в этом роде ...

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

Затем HTML-декодировать специальные символы, такие как &amp;. Результат не следует считать санированным.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...