Przeanalizuj kod HTML w systemie Android


83

Próbuję przeanalizować HTML w Androidzie ze strony internetowej, a ponieważ strona internetowa nie jest dobrze sformułowana, otrzymuję SAXException.

Czy istnieje sposób na przeanalizowanie kodu HTML w systemie Android?


Podejrzewam, że zależność Rhino sprawi, że htmlunit będzie piekło przy kompilacji na Androidzie, ale możesz spróbować ... Może również zadziałać inny nie-ścisły parser HTML, taki jak zupa.
Alex

Zastanawiam się, czy można tu użyć webkita.
ziya

Odpowiedzi:


72

Właśnie napotkałem ten problem. Próbowałem kilku rzeczy, ale zdecydowałem się na użycie JSoup . Jar ma około 132k, co jest trochę duże, ale jeśli pobierzesz źródło i usuniesz niektóre z metod, których nie będziesz używać, to nie jest tak duży.
=> Dobrą rzeczą jest to, że będzie obsługiwać źle sformułowany HTML

Oto dobry przykład z ich witryny.

File input = new File("/tmp/input.html");
Document doc = Jsoup.parse(input, "UTF-8", "http://example.com/");

//http://jsoup.org/cookbook/input/load-document-from-url
//Document doc = Jsoup.connect("http://example.com/").get();

Element content = doc.getElementById("content");
Elements links = content.getElementsByTag("a");
for (Element link : links) {
  String linkHref = link.attr("href");
  String linkText = link.text();
}

1
Możesz spróbować dołączyć pełny plik jar i uruchomić ProGuard w swojej aplikacji w wersji produkcyjnej, aby usunąć nieużywany kod.
Andrew Mackenzie

3
OSTRZEŻENIE: JSoup działa bardzo wolno.
kevin

@kevin źródłem tego twierdzenia? Możesz mieć włączone debugowanie.
goetzc

A co z treścią ładowaną dynamicznie za pomocą skryptu java podczas renderowania strony html po stronie klienta? Czy Jsoup pokaże również tę zawartość?
MikeL

56

Czy próbowałeś użyć Html.fromHtml (źródło) ?

Myślę, że ta klasa jest dość liberalna pod względem jakości źródła (używa wewnętrznie TagSoup , który został zaprojektowany z myślą o prawdziwym, złym HTMLu ). Nie obsługuje jednak wszystkich tagów HTML, ale zawiera procedurę obsługi, którą można zaimplementować, aby reagować na tagi, których nie rozumie.


1
To bardzo proste, nie mogę wyszukiwać dokładnych rzeczy (takich jak XPATH)

proszę o uwagę. spowoduje to „zawieszenie wszystkich wątków”. Mam do czynienia z niż gdy otrzymuję json z tekstem w formacie html w nim. nie było problemu z poprawnym wyświetlaniem tekstu html ale po użyciu html.fromhtml () mam z tym problem.
David

23
String tmpHtml = "<html>a whole bunch of html stuff</html>";
String htmlTextStr = Html.fromHtml(tmpHtml).toString();

ładne i proste, bez wtyczek, uwielbiam to! tnxs
RonEskinder

2
Na marginesie: dzwoniąc toString()na Spannedobiekcie wrócił z Html.fromHtml(str)uczyni wiele HTMLznaczników nie działać (włącznie <i> <u> <b>). Więc jeśli ustawiasz widok tekstu, po prostu zrób:myTextView.setText(Html.fromHtml(str))
Sakiboy

@Sakiboy Masz rację. Oprócz tego istnieje wiele innych tagów, które nie działają Html.fromHtml(). Sprawdź to stackoverflow.com/a/3150456/1987045
Rahul Raveendran

super, dokładnie to, czego chciałem, mój programista po stronie serwera wysyłał mi html, teraz mogę łatwo przekonwertować go na surowy ciąg dzięki
Zulqurnain Jutt

3

Wszyscy wiemy, że programowanie ma nieskończone możliwości. Istnieje wiele rozwiązań dostępnych dla jednego problemu, więc myślę, że wszystkie powyższe rozwiązania są idealne i mogą być pomocne dla kogoś, ale dla mnie to oszczędza mój dzień.

Więc Code działa w ten sposób

  private void getWebsite() {
    new Thread(new Runnable() {
      @Override
      public void run() {
        final StringBuilder builder = new StringBuilder();

        try {
          Document doc = Jsoup.connect("http://www.ssaurel.com/blog").get();
          String title = doc.title();
          Elements links = doc.select("a[href]");

          builder.append(title).append("\n");

          for (Element link : links) {
            builder.append("\n").append("Link : ").append(link.attr("href"))
            .append("\n").append("Text : ").append(link.text());
          }
        } catch (IOException e) {
          builder.append("Error : ").append(e.getMessage()).append("\n");
        }

        runOnUiThread(new Runnable() {
          @Override
          public void run() {
            result.setText(builder.toString());
          }
        });
      }
    }).start();
  }

Musisz tylko wywołać powyższą funkcję w onCreate MethodswoimMainActivity

Mam nadzieję, że ten jest również pomocny dla was.

Przeczytaj także oryginalny blog na Medium


Korzystając z naszej strony potwierdzasz, że przeczytałeś(-aś) i rozumiesz nasze zasady używania plików cookie i zasady ochrony prywatności.
Licensed under cc by-sa 3.0 with attribution required.