18

I am trying to use ruby rest-client to upload a large number of images to a site that I'm writing. My code looks like:

RestClient.post url, :timeout => 90000000, :open_timeout => 90000000, :file_param => file_obj

However, I am getting this error:

RestClient::RequestTimeout: Request Timeout
    from /Library/Ruby/Gems/1.8/gems/rest-client-1.6.1/lib/restclient/request.rb:174:in `transmit'
    from /Library/Ruby/

But when I look at the server log

Completed in 61493ms (View: 2, DB: 1) | 201 Created 

So there doesn't appear to be any reason why this is timing out. Anyone have any idea if there is a timeout param I am not correctly setting?

Thanks

6 Answers 6

22

This syntax sets the timeout as request header (see RestClient.post signature), if you want to use the timeout parameter you must use:

RestClient::Request.execute(:method => :post, :url => @url, :timeout => 90000000)

see: https://github.com/rest-client/rest-client/blob/master/lib/restclient/request.rb#L12

2
  • 2
    RestClient::Request.execute(:method => :post, :url => @url, :timeout => 90000000) Commented Jun 18, 2014 at 19:40
  • 1
    And put any parameters to be sent in the POST body (I think :file_param in the OP) into :payload : Request.execute(:method => :post, :url => @url, :timeout => 90000000, :payload => { :file_param => file_obj }) Commented Sep 29, 2014 at 16:56
14

Looking at the docs, you can pass -1 through RestClient.execute timeout param:

# * :timeout and :open_timeout passing in -1 will disable the timeout by setting the corresponding net timeout values to nil

It can be used as follows:

resource = RestClient::Resource.new(
  "url",
  :timeout => -1,
  :open_timeout => -1
response = resource.get :params => {<params>}
1
  • 6
    This appears to have been updated to nil rather than -1. Using -1 logs a warning (but appears to work). Commented Sep 29, 2014 at 16:58
4

I have used following code and works like a charm as pointed out by Richard

resource = RestClient::Resource.new "url", 
                                    :timeout => $TIMEOUT, 
                                    :open_timeout => $OPEN_TIMEOUT

response = resource.get  :params => { ..... }
4

I already use RestClient.get and RestClient.post extensively, so for me, it was easier to 'Monkey Patch' RestClient. I would recommend using RestClient::Resource.new or RestClient::Request.Execute if possible.

However, since I'm lazy, and don't want to go swap out every occurrence of RestClient.get / RestClient.post in my code, I've decided to take a shortcut.

$timeout = 30
$open_timeout = 30

module RestClient2
  include RestClient

  def self.get(url, headers={}, &block)
    Request.execute(:method => :get, :url => url, :headers => headers, 
     :timeout => $timeout, :open_timeout => $open_timeout, &block)
  end

  def self.post(url, payload, headers={}, &block)
    Request.execute(:method => :post, :url => url, :payload => payload, :headers => headers,
     :timeout => $timeout, :open_timeout => $open_timeout, &block)
  end
end

And than I just just quick replaced RestClient.get/post with RestClient2.get/post.

It would be nice, if RestClient::Request had a default timeout specified, like:

  @timeout = args[:timeout] || 30
  @open_timeout = args[:open_timeout] || 30
0
3

I'm having similar issues. A quick dive into the source reveals this bit of unfriendliness:

def self.post(url, payload, headers={}, &block)
  Request.execute(:method => :post, :url => url, :payload => payload, :headers => headers, &block)
end

Unless I'm missing something, the timeout options aren't passed on to the underlying request. Time for a patch ...

1
  • 5
    A slightly deeper dive shows that while the get, post and related convenience methods indeed do not allow you to pass the :timeout and :open_timout options, they are just thin wrappers for Request.execute, which will accept them. Better to replace calls to the wrappers with calls to execute than to monkey patch, IMHO. Commented Sep 12, 2012 at 19:50
2

The RestClient::Resource.new() allows you to set :timeout and :open_timeout values that will get passed to the Request.execute method, when you use the resource's get, post, put, etc methods

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.