简体   繁体   中英

Nokogiri: How to get xml class by one of its subtag's content

For example, I've got this XML object:

<PARENT>
  <ROW>
    <ID>1</ID>
    <INFO>1234</INFO>
  </ROW>
  <ROW>
    <ID>2</ID>
    <INFO>4321</INFO>
  </ROW>
  <ROW>
    <ID>3</ID>
    <INFO>4444</INFO>
  </ROW>
</PARENT>

in a variable called rows .

xml = Nokogiri::XML(rows)

What I need is to retrieve whole ROW subtag searching by ID inside of the ID tag.

XPath allows you to do this:

xml.xpath '//PARENT/ROW/ID[text="3"]/..'
s = <<-EOS
<PARENT>
  <ROW>
    <ID>1</ID>
    <INFO>1234</INFO>
  </ROW>
  <ROW>
    <ID>2</ID>
    <INFO>4321</INFO>
  </ROW>
  <ROW>
    <ID>3</ID>
    <INFO>4444</INFO>
  </ROW>
</PARENT>
EOS

doc = Nokogiri::XML(s)
element = doc.xpath("//ROW[ID='2']")
p element.to_s
# => "<ROW>\n    <ID>2</ID>\n    <INFO>4321</INFO>\n  </ROW>"

And if you want to refine the result to one specific node, add it to the end.

s = <<-EOS
<PARENT>
  <ROW>
    <ID>1</ID>
    <INFO>1234</INFO>
  </ROW>
  <ROW>
    <ID>2</ID>
    <INFO>4321</INFO>
  </ROW>
  <ROW>
    <ID>3</ID>
    <INFO>4444</INFO>
  </ROW>
</PARENT>
EOS

doc = Nokogiri::XML(s)
element = doc.xpath("//ROW[ID='2']/INFO")
p element.to_s
# => "<INFO>4321</INFO>"

You can get the whole row like this:

>> xml.xpath("//ROW[ID=3]").each { |el| p el } #=> 0
#<Nokogiri::XML::Element:0x809ba610 name="ROW" children=[#<Nokogiri::XML::Text:0x809ba318 "\n    ">, #<Nokogiri::XML::Element:0x809ba2c8 name="ID" children=[#<Nokogiri::XML::Text:0x809b9fd0 "3">]>, #<Nokogiri::XML::Text:0x809b9e54 "\n    ">, #<Nokogiri::XML::Element:0x809b9e04 name="INFO" children=[#<Nokogiri::XML::Text:0x809b9ad0 "4444">]>, #<Nokogiri::XML::Text:0x809b9968 "\n  ">]>

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM