Nokogiri可以搜索“?xml-stylesheet”标签吗?

我需要解析XML样式表:

  

使用Nokogiri我试过:

 doc.search("?xml-stylesheet").first['href'] 

但我得到错误:

 `on_error': unexpected '?' after '' (Nokogiri::CSS::SyntaxError) 

Nokogiri无法搜索XML处理指令的标签。 您可以像这样访问它们:

 doc.children[0] 

这不是XML元素; 这是一个XML “处理指令” 。 这就是您无法通过查询找到它的原因。 找到你想要的:

 # Find the first xml-stylesheet PI xss = doc.at_xpath('//processing-instruction("xml-stylesheet")') # Find every xml-stylesheet PI xsss = doc.xpath('//processing-instruction("xml-stylesheet")') 

看到行动:

 require 'nokogiri' xml = <  Hi Mom! ENDXML doc = Nokogiri.XML(xml) xss = doc.at_xpath('//processing-instruction("xml-stylesheet")') puts xss.name #=> xml-stylesheet puts xss.content #=> type="text/xsl" href="/templates/disclaimer_en.xsl" 

由于处理指令不是元素,因此它没有属性; 例如,你不能要求xss['type']xss['href'] ; 如果您愿意,您需要将内容解析为元素。 一种方法是:

 class Nokogiri::XML::ProcessingInstruction def to_element document.parse("<#{name} #{content}/>") end end p xss.to_element['href'] #=> "/templates/disclaimer_en.xsl" 

请注意,Nokogiri或libxml2中存在一个错误 ,如果在之前至少有一个字符(可以是空格),则会导致XML声明作为处理指令出现在文档中。 这就是为什么在上面我们专门搜索名为xml-stylesheet处理指令。

编辑 :XPath表达式processing-instruction()[name()="foo"]等同于表达式processing-instruction("foo") 。 如XPath 1.0规范中所述 :

processing-instruction()测试可能有一个Literal参数; 在这种情况下,对于任何名称等于Literal值的处理指令都是如此。

我编辑了上面的答案,使用较短的格式。