【问题标题】:Nokogiri not working for advanced XPath searchNokogiri 不适用于高级 XPath 搜索
【发布时间】:2014-07-23 07:12:30
【问题描述】:

看看这个页面:http://finviz.com/quote.ashx?t=AAPL

XPath

(//*[contains(concat(' ', @class, ' '), ' snapshot-table2 ')]/tbody/tr/td[text() = 'Index']/following::td)[1]/b

应该吐出S&P 500,当我在 JavaScript 控制台中尝试它时,它确实如此。但是,当我尝试将 Nokogiri 与 Ruby 一起使用时,它会返回一个空数组。

这是完整的代码:

url = "http://finviz.com/quote.ashx?t=#{ticker}"
data = Nokogiri::HTML(open(url))
xpath = "(//*[contains(concat(' ', @class, ' '), ' snapshot-table2 ')]/tbody/tr/td[text() = '#{datapoint}']/following::td)[1]/b"
data.xpath(xpath)

data.xpath(xpath) 返回[]

有什么想法吗?

【问题讨论】:

  • 您不能相信浏览器会告诉您节点的正确路径。浏览器试图呈现一些可用的东西,并使用格式错误的 HTML 进行各种修复。那个“固定”的 HTML 就是它将向您展示的内容。相反,请查看当您的open 语句移交 IO 句柄时 Nokogiri 将看到的相同 HTML。使用open(url).read,您将看到服务器发送的原始 HTML,这将使您有更好的机会找到正确的 XPath。

标签: ruby-on-rails ruby xml xpath nokogiri


【解决方案1】:

在该页面的响应中,我没有看到 <tbody> 元素。

您提到您的 XPath 在您的浏览器控制台中工作,这可能是因为浏览器正在注入 tbody 元素以进行渲染,请参阅“Why do browsers insert tbody element into table elements?”了解发生这种情况的详细信息。

在不指定 <tbody> 节点的情况下再次尝试您的 XPath:

data.xpath("(//*[contains(@class, 'snapshot-table2')]/tr/td[text() = 'Index']/following::td)[1]/b")

您也可以使用类似的方法来让相同的 XPath 在浏览器和您的 Ruby 代码中工作:

(//*[contains(@class, 'snapshot-table2')]//tr/td[text() = 'Index']/following::td)[1]/b

【讨论】:

  • 浏览器添加了tbody,因为它试图遵循规范。 HTML 最初是否有<tbody> 对浏览器来说并不重要,但对解析器来说却很重要。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2018-04-03
相关资源
最近更新 更多