如何使用Ruby on Rails发出HTTP请求?


235

我想从另一个网站获取信息。因此,(也许)我应该向该网站发出请求(在我的情况下为HTTP GET请求)并接收响应。

如何在Ruby on Rails中做到这一点?

如果可能,是否可以在我的控制器中使用正确的方法?

Answers:


329

您可以使用Ruby的Net::HTTP类:

require 'net/http'

url = URI.parse('http://www.example.com/index.html')
req = Net::HTTP::Get.new(url.to_s)
res = Net::HTTP.start(url.host, url.port) {|http|
  http.request(req)
}
puts res.body

1
“ req”在这里是什么意思?
sixty4bit 2014年

18
这意味着要求
ArthurCollé2014年

1
看起来这可能是一个阻止请求,不是吗?
Scott Eisenberg 2015年

在哪里放置api密钥?
user1735921

1
只需添加www。应该没有必要,通常没有必要。
JackHasaKeyboard '16

111

Net :: HTTP是内置在Ruby中的,但让我们面对现实吧,通常使用繁琐的1980年代样式并尝试更高级别的替代方法通常会更容易:


4
还是Rails附带的ActiveResource!
Marnen Laibow-Koser 2011年

8
我想提醒您不要这样做,因为您将向Rails应用程序添加更多依赖项。更多的依赖关系意味着更多的内存消耗以及潜在的更大的攻击面。使用起来Net::HTTP很麻烦,但是这样做并不值得。
詹森·杨

3
这应该是公认的答案。当您可以安装大量宝石时为什么要编程?
忽略

5
@JasonYeo完全不同意。引入依赖项意味着您不必重新发明轮子,而您会从别人已经完成的辛勤工作中受益。如果有一颗让您的生活更轻松的宝石,通常没有充分的理由不使用它。
Marnen Laibow-Koser '18

1
@JasonYeo发生左垫事件的原因仅在于NPM对存储库的运行不佳,并允许作者删除其所有软件包。妥善管理的软件包存储库不能做到这一点(无论如何,它是OSS,因此您可以根据需要轻松进行镜像)。就是说,leftpad传奇并不是反对普遍引入依赖关系的争论,而是反对糟糕地管理回购协议。我确实同意您的另一点,那就是,一个依赖程度远远超出您需要的大依赖可能会过分夸大其提供的价值。
Marnen Laibow-Koser


82
require 'net/http'
result = Net::HTTP.get(URI.parse('http://www.example.com/about.html'))
# or
result = Net::HTTP.get(URI.parse('http://www.example.com'), '/about.html')

13

我更喜欢httpclient而不是Net :: HTTP。

client = HTTPClient.new
puts client.get_content('http://www.example.com/index.html')

如果您要创建作为服务客户端的类,那么HTTParty是一个不错的选择。这是一个方便的mixin,可为您提供90%的需求。在示例中查看Google和Twitter客户端有多短。

并回答您的第二个问题:不,我不会将此功能放在控制器中-如果可能的话,我会使用模型来封装细节(也许使用HTTParty),然后从控制器中调用它。


以及如何安全地在URL中传递参数?例如:http://www.example.com/index.html?param1 = test1&param2 = test2。然后,我需要从其他网站参数中读取并准备响应。但是如何读取参数?
user502052 2011年

您是什么意思,您需要阅读其他网站的参数吗?那怎么可能呢?您想达到什么目的?
Marnen Laibow-Koser 2011年

8

我最喜欢的两种获取URL内容的方法是OpenURITyphoeus

OpenURI是因为它无处不在,而Typhoeus是因为它非常灵活和强大。


8

如果要在代理后面进行REST api调用,则以下代码可以工作:

require "uri"
require 'net/http'

proxy_host = '<proxy addr>'
proxy_port = '<proxy_port>'
proxy_user = '<username>'
proxy_pass = '<password>'

uri = URI.parse("https://saucelabs.com:80/rest/v1/users/<username>")
proxy = Net::HTTP::Proxy(proxy_host, proxy_port, proxy_user, proxy_pass)

req = Net::HTTP::Get.new(uri.path)
req.basic_auth(<sauce_username>,<sauce_password>)

result = proxy.start(uri.host,uri.port) do |http|
http.request(req)
end

puts result.body
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.