Nokogiri XML Searching



我试着阅读Nokogiri文档等,但我遇到了一个障碍。

我得到一个类似于 的XML输出
<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <ns1:getPoliciesResponse xmlns:ns1="http://policy.api.control.r1soft.com/">
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>bcb68765-a719-4291-912d-2e6af485ea24</diskSafeID>
        <enabled>true</enabled>
        <id>cdb65427-d6f4-4a89-9f77-8763e22dc74b</id>
        <lastReplicationRunTime>2013-06-12T13:29:40.105-05:00</lastReplicationRunTime>
        <name>pstueck-passenger ondemand</name>
        <replicationScheduleFrequencyType>ON_DEMAND</replicationScheduleFrequencyType>
        <state>OK</state>
      </return>
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>e8e13555-f577-40d2-99c8-fa8a019d3b55</diskSafeID>
        <enabled>true</enabled>
        <id>7f55f8d6-92a9-4b14-bff4-631559d92259</id>
        <lastReplicationRunTime>2013-06-16T22:00:04.918-05:00</lastReplicationRunTime>
        <name>pstueck-mysql daily</name>
        <nextReplicationRunTime>2013-06-17T22:00:00-05:00</nextReplicationRunTime>
        <replicationScheduleFrequencyType>DAILY</replicationScheduleFrequencyType>
        <state>ALERT</state>
        <warnings>Policy last completed with alerts</warnings>
      </return>
    </ns1:getPoliciesResponse>
  </soap:Body>
</soap:Envelope>

但是我有一个大#的"返回"部分显示回来。我试图在字符串的末尾使用。search。我只希望它返回整个'返回'部分为给定的'名称'。有人有什么建议吗?

当前代码:

client = Savon::Client.new do
  http.auth.basic "#{opts['api_username']}", "#{opts['api_password']}"
  wsdl.document = "#{opts['api_url']}/Policy?wsdl"
end
getPolicyInformation = client.request :getPolicies
getPolicyInformation = Nokogiri::XML(getPolicyInformation.to_xml)
print getPolicyInformation

如果我搜索指定的<name>,我想返回<return>部分中的所有内容。示例:我只想看到与<name>pstueck-passenger ondemand</name>相关的信息,但是包含<return>的整个部分

您可以使用XPath识别具有特定值的节点,然后通过执行以下操作来指定感兴趣的祖先元素:

require 'nokogiri'
document = <<-XML
<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <ns1:getPoliciesResponse xmlns:ns1="http://policy.api.control.r1soft.com/">
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>bcb68765-a719-4291-912d-2e6af485ea24</diskSafeID>
        <enabled>true</enabled>
        <id>cdb65427-d6f4-4a89-9f77-8763e22dc74b</id>
        <lastReplicationRunTime>2013-06-12T13:29:40.105-05:00</lastReplicationRunTime>
        <name>pstueck-passenger ondemand</name>
        <replicationScheduleFrequencyType>ON_DEMAND</replicationScheduleFrequencyType>
        <state>OK</state>
      </return>
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>e8e13555-f577-40d2-99c8-fa8a019d3b55</diskSafeID>
        <enabled>true</enabled>
        <id>7f55f8d6-92a9-4b14-bff4-631559d92259</id>
        <lastReplicationRunTime>2013-06-16T22:00:04.918-05:00</lastReplicationRunTime>
        <name>pstueck-mysql daily</name>
        <nextReplicationRunTime>2013-06-17T22:00:00-05:00</nextReplicationRunTime>
        <replicationScheduleFrequencyType>DAILY</replicationScheduleFrequencyType>
        <state>ALERT</state>
        <warnings>Policy last completed with alerts</warnings>
      </return>
    </ns1:getPoliciesResponse>
  </soap:Body>
</soap:Envelope>
XML
doc = Nokogiri::XML(document)
ns = { 'soap' => 'http://schemas.xmlsoap.org/soap/envelope/', 'ns1' => "http://policy.api.control.r1soft.com/" }
ret = doc.xpath('/soap:Envelope/soap:Body/ns1:getPoliciesResponse/return/name[text()="pstueck-passenger ondemand"]/ancestor::return', ns)
puts ret.count
puts ret.at('replicationScheduleFrequencyType').text

编辑

已更新以反映所讨论的更新的XML主体。现在处理名称空间

使用CSS查找节点:

require 'nokogiri'
doc = Nokogiri::XML(<<EOT)
<?xml version="1.0"?>
<soap:Envelope xmlns:soap="http://schemas.xmlsoap.org/soap/envelope/">
  <soap:Body>
    <ns1:getPoliciesResponse xmlns:ns1="http://policy.api.control.r1soft.com/">
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>e8e13555-f577-40d2-99c8-fa8a019d3b55</diskSafeID>
        <enabled>true</enabled>
        <id>7f55f8d6-92a9-4b14-bff4-631559d92259</id>
        <lastReplicationRunTime>2013-06-16T22:00:04.918-05:00</lastReplicationRunTime>
        <name>pstueck-mysql daily</name>
        <nextReplicationRunTime>2013-06-17T22:00:00-05:00</nextReplicationRunTime>
        <replicationScheduleFrequencyType>DAILY</replicationScheduleFrequencyType>
        <state>ALERT</state>
        <warnings>Policy last completed with alerts</warnings>
      </return>
      <return>
        <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
        <description/>
        <diskSafeID>bcb68765-a719-4291-912d-2e6af485ea24</diskSafeID>
        <enabled>true</enabled>
        <id>cdb65427-d6f4-4a89-9f77-8763e22dc74b</id>
        <lastReplicationRunTime>2013-06-12T13:29:40.105-05:00</lastReplicationRunTime>
        <name>pstueck-passenger ondemand</name>
        <replicationScheduleFrequencyType>ON_DEMAND</replicationScheduleFrequencyType>
        <state>OK</state>
      </return>
    </ns1:getPoliciesResponse>
  </soap:Body>
</soap:Envelope>
EOT
return_tag = doc.at('return name[text()="pstueck-passenger ondemand"]').parent
puts return_tag.to_xml
输出:

<return>
  <CDPId>XXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXXx</CDPId>
  <description/>
  <diskSafeID>bcb68765-a719-4291-912d-2e6af485ea24</diskSafeID>
  <enabled>true</enabled>
  <id>cdb65427-d6f4-4a89-9f77-8763e22dc74b</id>
  <lastReplicationRunTime>2013-06-12T13:29:40.105-05:00</lastReplicationRunTime>
  <name>pstueck-passenger ondemand</name>
  <replicationScheduleFrequencyType>ON_DEMAND</replicationScheduleFrequencyType>
  <state>OK</state>
</return>

Nokogiri支持XPath和CSS。我发现CSS更容易阅读。

我使用at方法来查找第一个匹配事件,并且为了显示它是第一个匹配,我交换了两个<return>块的顺序。atsearch(...).first是一样的,所以当你在文档中寻找某样东西的第一个实例时,at是最好的选择。

Nokogiri通常足够聪明,知道XPath和CSS选择器之间的区别,因此我们可以使用通用的atsearch。如果因为选择器的性别不特定而需要强制CSS或XPath解析,则可以分别使用特定的cssxpathat_cssat_xpath。它们都记录在Nokogiri::XML::Node文档中。

parent是必需的,因为我们需要所选节点的父节点,即<name>。我只是倒车,倒车了一个街区。这在XPath中更容易实现,我们可以使用..指向父节点。

相关内容

  • 没有找到相关文章

最新更新