Dado que los archivos HTML son generalmente problemáticos, primero tendrá que limpiarlos con un analizador/analizador. He usado JTidy pero nunca felizmente. NekoHTML funciona bien, pero cualquiera de estas herramientas siempre hace una buena estimación de lo que se pretende. De hecho, está pidiendo que un programa altere el marcado de un documento hasta que se ajuste a un esquema. Es probable que cause una pérdida estructural (marcado), de estilo o de contenido. Es inevitable, y no sabrá realmente lo que falta a menos que escanee manualmente a través de un navegador (y luego también debe confiar en el navegador).
Realmente depende de su propósito — si tiene miles de documentos feos con toneladas de marcas externas (no HTML), entonces un proceso manual es probablemente irrazonable. Si su objetivo es la precisión en algunos documentos importantes, entonces arreglarlos manualmente es una propuesta razonable.
Un enfoque es el proceso manual de paso repetido de la fuente a través de un analizador bien formado y de validación, en un ciclo de edición que utiliza los mensajes de error para finalmente reparar el marcado roto. Esto requiere cierta comprensión de XML, pero no es una mala educación.
Con Java 5, las características XML necesarias — llamadas JAXP API — ahora están integradas en Java; no necesita ninguna biblioteca externa.
Primero obtiene una instancia de un DocumentBuilderFactory, establece sus características, crea un DocumentBuilder (analizador), luego llama a su método parse() con un InputSource. InputSource tiene una serie de posibles constructores, con un StringReader utilizado en el ejemplo siguiente:
import javax.xml.parsers.*;
// ...
DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();
dbf.setValidating(false);
dbf.setNamespaceAware(true);
dbf.setIgnoringComments(false);
dbf.setIgnoringElementContentWhitespace(false);
dbf.setExpandEntityReferences(false);
DocumentBuilder db = dbf.newDocumentBuilder();
return db.parse(new InputSource(new StringReader(source)));
Esto devuelve un documento de DOM. Si no te importa utilizar bibliotecas externas, también están las API JDOM y XOM, y si bien estas tienen algunas ventajas sobre las API SAX y DOM en JAXP, sí requieren que se agreguen bibliotecas que no sean de Java. El DOM puede ser algo engorroso, pero después de tantos años de usarlo ya no me importa.
Neko + Xerces hacen el trabajo bastante bien. Gracias a todos los que respondieron –
Cuidado con JTidy. Tiene un error de fuga de memoria.Si lo ejecuta en un sistema de producción, eventualmente explotará: StackOverflowError y eventualmente OutOfMemoryError. Dicho esto, es maravillosamente bueno arreglar html rotos para que puedas alimentarlo en un analizador dom. – Joel
¿Existe alguna forma clara de usar JTidy como interfaz para JDOM o XOM de forma continua? Es decir, ¿sin leer primero todo el documento en la memoria? (¿Y sin usar PipedInput/OutputStream y múltiples hilos?) ¿O estaría mejor solo usando Neko en ese caso? –