2016-11-16 92 views
2

我试图利用引入nokogiri网页获取定义规范链接以获得从HTML头规范链接:如何利用引入nokogiri

<link rel="canonical" href="https://test.com/somepage"> 

这是href我之后。

无论我尝试它似乎不工作。这是我的:

page = Nokogiri::HTML.parse(browser.html) 

canon = page.xpath('//canonical/@href') 
puts canon 

这不会返回任何东西,甚至没有错误。

回答

1

您正试图获得该属性,但不是你怎么做。

您可以使用此:

page.xpath('//link[@rel="canonical"]/@href') 

什么它说的是:给我一个链接元素的任何地方,有一个rel属性,等于"canonical",当你发现节点,让我的href属性的文件。

完整的答案是:

page = Nokogiri::HTML.parse(browser.html) 

canon = page.xpath('//link[@rel="canonical"]/@href') 
puts canon 

你试图做的是得到一个被称为“规范”,而不是属性节点。

+0

'canon'不会是一个字符串,它将是一个Attr对象,它不会像字符串那样操作。当你使用'puts'的时候它会被字符串化,但是如果你试图把它当作任何东西而不是它是什么,它就会遮住真正的对象,这会引起问题。 –

+0

重点是,它会grep什么。 '加农炮'就是为了证明它。 –

1

我使用CSS选择了使用XPath作为他们更可读的粉丝:

require 'nokogiri' 

doc = Nokogiri::HTML('<link rel="canonical" href="https://test.com/somepage">') 
doc.at('link[rel="canonical"]')['href'] # => "https://test.com/somepage" 
什么引入nokogiri和XPath,被访问节点参数时返回

还有的来混淆。试想一下:

require 'nokogiri' 

doc = Nokogiri::HTML('<link rel="canonical" href="https://test.com/somepage">') 

这是我怎么会做它用CSS:

doc.at('link[rel="canonical"]').class # => Nokogiri::XML::Element 
doc.at('link[rel="canonical"]')['href'].class # => String 

doc.at('link[rel="canonical"]')['href'] # => "https://test.com/somepage" 

的XPath,而功能更强大,也能够让你,或者引入nokogiri,Ruby或CPU的,做多工作。

首先,xpathsearch的XPath特定版本,它返回一个NodeSet,而不是节点或元素。一个NodeSet类似于一组节点,如果你不知道你有什么,它会咬你。从NodeSet文档:

NodeSet包含Nokogiri :: XML :: Node对象的列表。通常,一个节点集是回报通过引入nokogiri搜索文档:: XML ::检索#CSS或引入nokogiri :: XML ::检索#XPath的

如果你正在寻找一个特定节点,或仅一个的结果特定类型的节点的单个实例,然后使用at,或者如果您想要挑剔,请使用at_cssat_xpath。 (Nokogiri在使用atsearch时通常会弄清楚你的意思,但有时你必须使用特定的方法让Nokogiri在正确的方向上微调)。在上面的例子中使用at表明它返回节点本身,并且一旦你已经得到了节点,通过把它看作一个散列来获得任何参数的值是微不足道的。

xpathsearchcss都返回节点集,所以,像一个数组,你需要指向实际的元素,那么你想获得的参数:

doc.xpath('//link[@rel="canonical"]/@href').class # => Nokogiri::XML::NodeSet 
doc.xpath('//link[@rel="canonical"]/@href').first.class # => Nokogiri::XML::Attr 

doc.xpath('//link[@rel="canonical"]/@href').text # => "https://test.com/somepage" 

注意'//link[@rel="canonical"]/@href'导致引入nokogiri返回获得Attr对象,而不是文本。您可以打印该对象,并且Ruby将对其进行字符串化,但如果您尝试像对待它一样对待它,它将不会像字符串那样表现出错误,从而导致错误。例如:

doc.xpath('//link[@rel="canonical"]/@href').first.downcase # => NoMethodError: undefined method `downcase' for #<Nokogiri::XML::Attr:0x007faace115d20> 

相反,使用textcontent来获取文本值:

doc.at('//link[@rel="canonical"]/@href').class # => Nokogiri::XML::Attr 

doc.at('//link[@rel="canonical"]/@href').text # => "https://test.com/somepage" 

或获取元素本身,然后访问像你该参数将哈希:

doc.at('//link[@rel="canonical"]').class # => Nokogiri::XML::Element 

doc.at('//link[@rel="canonical"]')['href'] # => "https://test.com/somepage" 

其中之一将返回一个字符串。

另请注意,在此示例中,我没有使用@href返回Attr,我只获取节点本身,然后使用['href']返回参数的文本。这是一个较短的选择器,至少对我来说更有意义,因为Nokogiri不必返回Attr对象,然后您必须使用text进行转换,否则当您不小心将其视为字符串时,可能会遇到问题。

+0

CSS选择器很不错,但速度稍慢,可能难以迁移到其他语言或新开始学习的人。 –

+0

大多数Web开发人员都了解CSS,无论是使用jQuery还是样式表,所以他们很容易以这种方式跳跃。迁移到其他语言并不一定难;我使用了其他可以理解CSS的解析器。 –