1

MySQL 列 ( product_path) 具有值//*[(@id=\"scroller\")]/li/*/a。将它与 Nokogiri 一起使用会抛出Nokogiri::XML::XPath::SyntaxError: Invalid expression: 什么问题。

require 'mysql2'
require 'active_record'

ActiveRecord::Base.establish_connection( 
  :adapter => "mysql2",
  :host => "localhost",
  ...
)

class MyTable < ActiveRecord::Base
end

@s = MyTable.first

#...Looks like backward slash is escaped automatically by mysql
@s.product_path #=> "//*[(@id=\\\"scroller\\\")]/li/*/a"

p = Nokogiri::HTML(open(@s.url))

#all variations below throw invalid expression error
p.search(@s.product_path).count
p.search("#{@s.product_path").count
p.xpath(@s.product_path).count

#But this works flawlessly.
p.search("//*[(@id=\"scroller\")]/li/*/a").count #=> works fine.

更新

我试过了,它奏效了。

a = '//*[(@id="scroller")]/li/*/a'
p.search(a).count

额外的反斜杠似乎造成了问题。我该如何摆脱它们?

4

2 回答 2

1

您输入的 XPath 表达式为:

//*[(@id=\"scroller\")]/li/*/a

注意转义的双引号。然后你得到这个 Ruby 字符串:

"//*[(@id=\\\"scroller\\\")]/li/*/a"

但这是inspect输出,所以有些东西会被转义。如果你puts是那个字符串,你会得到:

//*[(@id=\"scroller\")]/li/*/a

这正是您输入的字符串。但是,您的 XPath 表达式不应该\"围绕属性值,它应该只有".

因此,您输入了无效的错误 XPath 表达式,将这些表达式从数据库中取回,并想知道为什么它们是错误的。修复你的输入过程,不要过度逃避事情,你应该没问题。

于 2013-08-30T06:50:20.900 回答
0

ActiveRecord::sanitize_sql方法在这里可能有用,但它受到保护,所以在将 xpaths 保存到 db 之前尝试:

ActiveRecord::Base.send :sanitize_sql, your_xpath
于 2013-08-29T21:41:38.517 回答