Geral
Quase todos os analisadores HTML conhecidos implementam a API DOM do W3C (parte da API JAXP, API Java para processamento XML) e oferecem um org.w3c.dom.Document
retorno pronto para uso direto pela API JAXP. As principais diferenças costumam ser encontradas nos recursos do analisador em questão. A maioria dos analisadores é, até certo ponto, indulgente e branda com HTML não-formado ("grupo de tags"), como JTidy , NekoHTML , TagSoup e HtmlCleaner . Você geralmente usa esse tipo de analisadores de HTML para "arrumar" a fonte HTML (por exemplo, substituindo o válido <br>
por HTML por um válido em XML <br />
), para que você possa percorrê-lo "da maneira usual" usando a API W3C DOM e JAXP.
Os únicos que saltam são HtmlUnit e Jsoup .
HtmlUnit
O HtmlUnit fornece uma API completamente própria, que oferece a possibilidade de agir como um navegador da Web programaticamente. Ou seja, insira os valores do formulário, clique nos elementos, chame o JavaScript, etc. É muito mais do que apenas um analisador de HTML. É um verdadeiro "navegador da web sem interface gráfica" e uma ferramenta de teste de unidade HTML.
Jsoup
O Jsoup também fornece uma API completamente própria. Ele oferece a possibilidade de selecionar elementos usando seletores CSS semelhantes ao jQuery e fornece uma API inteligente para percorrer a árvore DOM HTML e obter os elementos de interesse.
Particularmente, o deslocamento da árvore HTML DOM é a principal força do Jsoup. Os que já trabalharam org.w3c.dom.Document
sabem como é doloroso atravessar o DOM usando as APIs NodeList
e detalhadas Node
. É verdade que XPath
facilita a vida, mas, ainda assim, é outra curva de aprendizado e pode acabar sendo detalhada.
Aqui está um exemplo que usa um analisador DOM "simples" do W3C, como o JTidy, em combinação com o XPath para extrair o primeiro parágrafo da sua pergunta e os nomes de todos os respondentes (estou usando o XPath, pois sem ele, o código necessário para reunir as informações de interesse caso contrário, cresceria 10 vezes mais, sem escrever métodos utilitários / auxiliares).
String url = "http://stackoverflow.com/questions/3152138";
Document document = new Tidy().parseDOM(new URL(url).openStream(), null);
XPath xpath = XPathFactory.newInstance().newXPath();
Node question = (Node) xpath.compile("//*[@id='question']//*[contains(@class,'post-text')]//p[1]").evaluate(document, XPathConstants.NODE);
System.out.println("Question: " + question.getFirstChild().getNodeValue());
NodeList answerers = (NodeList) xpath.compile("//*[@id='answers']//*[contains(@class,'user-details')]//a[1]").evaluate(document, XPathConstants.NODESET);
for (int i = 0; i < answerers.getLength(); i++) {
System.out.println("Answerer: " + answerers.item(i).getFirstChild().getNodeValue());
}
E aqui está um exemplo de como fazer exatamente o mesmo com o Jsoup:
String url = "http://stackoverflow.com/questions/3152138";
Document document = Jsoup.connect(url).get();
Element question = document.select("#question .post-text p").first();
System.out.println("Question: " + question.text());
Elements answerers = document.select("#answers .user-details a");
for (Element answerer : answerers) {
System.out.println("Answerer: " + answerer.text());
}
Você vê a diferença? Não é apenas menos código, mas o Jsoup também é relativamente fácil de entender se você já tem uma experiência moderada com seletores de CSS (por exemplo, desenvolvendo sites e / ou usando o jQuery).
Resumo
Os prós e contras de cada um devem ser claros o suficiente agora. Se você deseja apenas usar a API JAXP padrão para atravessá-la, vá para o primeiro grupo de analisadores mencionado. Existem muitos deles. Qual escolher depende dos recursos que fornece (como a limpeza de HTML é fácil para você? Existem alguns ouvintes / interceptadores e limpadores específicos de marcas?) E a robustez da biblioteca (com que frequência é atualizada / mantida / corrigida? ) Se você gosta de testar o HTML da unidade, o HtmlUnit é o caminho a seguir. Se você deseja extrair dados específicos do HTML (que muitas vezes é o requisito do mundo real), o Jsoup é o caminho a seguir.
Jsoup
é bom. Eu tentei fazer a interface com outro módulo que funciona comorg.w3c.dom.*
API. Descobriu que Jsoup não obedece oorg.w3c.dom.*
contratoEste artigo compara certos aspectos dos seguintes analisadores:
Não é de forma alguma um resumo completo, e é de 2008. Mas você pode achar útil.
fonte
Adicione o validador.nu HTML Parser , uma implementação do algoritmo de análise HTML5 em Java, à sua lista.
No lado positivo, ele foi projetado especificamente para corresponder ao HTML5 e no coração do validador do HTML5, com grande probabilidade de corresponder ao comportamento de análise de futuros navegadores com um grau muito alto de precisão.
No lado negativo, nenhuma análise herdada dos navegadores funciona exatamente assim e, como o HTML5 ainda está em rascunho, está sujeito a alterações.
Na prática, esses problemas afetam apenas casos de canto obscuros e, para todos os efeitos práticos, são um excelente analisador.
fonte
Eu achei o Jericho HTML Parser muito bem escrito, atualizado (o que muitos dos analisadores não são), sem dependências e fácil de usar.
fonte
Vou acrescentar à resposta do @MJB depois de trabalhar com a maioria das bibliotecas de análise de HTML em Java. Existe um enorme benefício / omissão: analisadores que preservam a formatação e a incorreta do HTML na entrada e na saída.
Essa é a maioria dos analisadores quando você altera o documento, eliminando os espaços em branco, os comentários e as incorretas do DOM, principalmente se eles forem uma biblioteca semelhante a XML.
Jericho é o único analisador que conheço que permite manipular HTML desagradável, preservando a formatação de espaço em branco e a incorreta do HTML (se houver).
fonte
Duas outras opções são HTMLCleaner e HTMLParser .
Eu tentei a maioria dos analisadores aqui para uma estrutura de extração de dados / rastreador que venho desenvolvendo. Eu uso o HTMLCleaner para a maior parte do trabalho de extração de dados. Isso ocorre porque ele suporta um dialeto razoavelmente moderno de HTML, XHTML, HTML 5, com espaços para nome e suporta DOM, portanto, é possível usá-lo com a implementação XPath integrada em Java .
É muito mais fácil fazer isso com o HTMLCleaner do que alguns dos outros analisadores: JSoup, por exemplo, suporta uma interface do tipo DOM, em vez de DOM, portanto, é necessário algum assembly . Jericho tem uma interface de linha SAX, portanto, novamente é necessário algum trabalho, embora Sujit Pal tenha uma boa descrição de como fazer isso mas no final o HTMLCleaner funcionou melhor.
Eu também uso HTMLParser e Jericho para uma tarefa de extração de tabela, que substituiu algum código escrito usando libhtml-tableextract-perl do Perl . Uso HTMLParser para filtrar o HTML da tabela e, em seguida, uso Jericho para analisá-lo. Eu concordo com os comentários de MJB e Adam de que Jericó é bom em alguns casos porque preserva o HTML subjacente. Ele possui um tipo de interface SAX não padrão, portanto, para o processamento XPath, o HTMLCleaner é melhor.
A análise de HTML em Java é um problema surpreendentemente difícil, pois todos os analisadores parecem ter problemas com certos tipos de conteúdo HTML malformado.
fonte