解析具有花括号的URI,URI :: InvalidURIError:错误的URI(不是URI?)

时间:2012-01-13 03:47:55

标签: ruby parsing uri ruby-1.9.2 curly-braces

使用ruby 1.9.2-p290。我遇到了一个试图解析如下URI的问题:

require 'uri'
my_uri = "http://www.anyserver.com/getdata?anyparameter={330C-B5A2}"
the_uri = URI.parse(my_uri)

发出以下错误:

URI::InvalidURIError: bad URI(is not URI?)

我需要一个不同于每次编码花括号的解决方案:

new_uri = URI.encode("http://www.anyserver.com/getdata?anyparameter={330C-B5A2}")
=> "http://www.anyserver.com/getdata?anyparameter=%7B330C-B5A2%7D"

现在我可以照常解析new_uri,但每次需要时都必须这样做。没有每次都这样做,最简单的方法是什么?

我发布了自己的解决方案,因为我没有看到这个解决方案。


# Accepts URIs when they contain curly braces
# This overrides the DEFAULT_PARSER with the UNRESERVED key, including '{' and '}'
module URI
  def self.parse(uri)
    URI::Parser.new(:UNRESERVED => URI::REGEXP::PATTERN::UNRESERVED + "\{\}").parse(uri)
  end
end

现在我可以使用带有花括号的uri的URI.parse(uri),不会抛出任何错误。

2 个答案:

答案 0 :(得分:5)

# Need to not fail when uri contains curly braces
# This overrides the DEFAULT_PARSER with the UNRESERVED key, including '{' and '}'
# DEFAULT_PARSER is used everywhere, so its better to override it once
module URI
  remove_const :DEFAULT_PARSER
  unreserved = REGEXP::PATTERN::UNRESERVED
  DEFAULT_PARSER = Parser.new(:UNRESERVED => unreserved + "\{\}")
end

跟进同样的问题,因为DEFAULT_PARSER在任何地方都使用,所以最好完全替换它仅仅用于URI #payrse方法。此外,这避免了每次为新Parser对象的实例化分配内存。

答案 1 :(得分:2)

RFC 1738 - http://www.faqs.org/rfcs/rfc1738.html表示您必须对大括号进行编码

Thus, only alphanumerics, the special characters "$-_.+!*'(),", and
reserved characters used for their reserved purposes may be used
unencoded within a URL.