ruby on rails - ¿Cómo elimino HTML entre dos comentarios HTML usando Nokogiri?
ruby-on-rails web-scraping (1)
Extraer contenido entre dos nodos no es algo normal que haríamos; Normalmente querríamos contenido dentro de un nodo particular. Los comentarios son nodos, solo son tipos especiales de nodos.
require ''nokogiri''
doc = Nokogiri::HTML(<<EOT)
<body>
<!-- begin content -->
<div>some text</div>
<div><p>Some more elements</p></div>
<!-- end content -->
</body>
EOT
Al buscar un comentario que contenga el texto especificado, es posible encontrar un nodo inicial:
start_comment = doc.at("//comment()[contains(.,''begin content'')]") # => #<Nokogiri::XML::Comment:0x3fe94994268c " begin content ">
Una vez que se encuentra, se necesita un bucle que almacena el nodo actual, luego busca el siguiente hermano hasta que encuentra otro comentario:
content = Nokogiri::XML::NodeSet.new(doc)
contained_node = start_comment.next_sibling
loop do
break if contained_node.comment?
content << contained_node
contained_node = contained_node.next_sibling
end
content.to_html # => "/n <div>some text</div>/n <div><p>Some more elements</p></div>/n"
Tengo algunas páginas HTML donde los contenidos que se extraerán están marcados con comentarios HTML como a continuación.
<html>
.....
<!-- begin content -->
<div>some text</div>
<div><p>Some more elements</p></div>
<!-- end content -->
...
</html>
Estoy usando Nokogiri e intento extraer el HTML entre los contenidos <!-- begin content -->
y <!-- end content -->
.
Quiero extraer los elementos completos entre estos dos comentarios HTML:
<div>some text</div>
<div><p>Some more elements</p></div>
Puedo obtener la versión de solo texto usando la devolución de llamada de estos personajes:
class TextExtractor < Nokogiri::XML::SAX::Document
def initialize
@interesting = false
@text = ""
@html = ""
end
def comment(string)
case string.strip # strip leading and trailing whitespaces
when /^begin content/ # match starting comment
@interesting = true
when /^end content/
@interesting = false # match closing comment
end
def characters(string)
@text << string if @interesting
end
end
Obtengo la versión de solo texto con @text
pero necesito el HTML completo almacenado en @html
.