-1

https://api.twitter.com/1/statuses/user_timeline.json?include_entities=true&include_rts=true&screen_name=# {user}&count=#{number} (URI::InvalidURIError)

我从命令行解析的参数是

name = ARGV[1]
number = ARGV[2]

将不胜感激一些帮助...

4

1 回答 1

0

与其尝试将值插入 URL,不如做正确的事,让 Ruby 处理可能的特殊字符编码:

require 'uri'

name = 'foo'
number = 1

uri = URI('https://api.twitter.com/1/statuses/user_timeline.json?include_entities=true&include_rts=true')
uri.query = URI.encode_www_form(
  Hash[
    URI.decode_www_form(uri.query)
  ].merge('name' => name, 'count' => number)
)

puts uri

运行后,输出如下:

https://api.twitter.com/1/statuses/user_timeline.json?include_entities=true&include_rts=true&name=foo&count=1

虽然 90% 的情况下您可以使用插值将值放入 URL,但有时您需要包含需要编码的字符,并且当您尝试使用时,您的 URL 会生成错误它。

URI类遵循查询应如何编码的规范,因此您不会遇到这些问题。

分解它,你可以看到会发生什么:

uri.query
# => "include_entities=true&include_rts=true"
URI.decode_www_form(uri.query)
# => [["include_entities", "true"], ["include_rts", "true"]]
Hash[URI.decode_www_form(uri.query)]
# => {"include_entities"=>"true", "include_rts"=>"true"}
Hash[URI.decode_www_form(uri.query)].merge('name' => name, 'count' => number)
# => {"include_entities"=>"true", "include_rts"=>"true", "name"=>"foo", "count"=>1}
URI.encode_www_form(Hash[URI.decode_www_form(uri.query)].merge('name' => name, 'count' => number))
# => "include_entities=true&include_rts=true&name=foo&count=1"

编辑:

URI:Module (NoMethodError) 的未定义方法“decode_www_form”

我正在使用红宝石 1.9

查看可寻址宝石。它做得非常好,并且比内置的 URI 类具有更多功能:

require 'addressable/uri'

name = 'foo'
number = 1

uri = Addressable::URI.parse('https://api.twitter.com/1/statuses/user_timeline.json?include_entities=true&include_rts=true')
uri.query_values = uri.query_values.merge('name' => name, 'count' => number)

puts uri

看起来像:

https://api.twitter.com/1/statuses/user_timeline.json?count=1&include_entities=true&include_rts=true&name=foo
于 2013-06-09T06:15:08.817 回答