itrigga-net_helper 0.2.0 → 0.3.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- data/Gemfile +6 -2
- data/README.rdoc +36 -1
- data/Rakefile +18 -13
- data/VERSION +1 -1
- data/lib/itrigga/net_helper.rb +52 -145
- data/lib/itrigga/net_helper/rest_client.rb +19 -0
- data/lib/itrigga/net_helper/typhoeus.rb +35 -0
- data/spec/net_helper/rest_client_spec.rb +32 -0
- data/spec/net_helper/typhoeus_spec.rb +90 -0
- data/spec/net_helper_spec.rb +167 -236
- data/spec/spec.opts +5 -0
- data/spec/spec_helper.rb +54 -16
- metadata +95 -31
- data/Gemfile.lock +0 -36
data/Gemfile
CHANGED
@@ -5,13 +5,17 @@ source "http://rubygems.org"
|
|
5
5
|
|
6
6
|
# Add dependencies to develop your gem here.
|
7
7
|
# Include everything needed to run rake, tests, features, etc.
|
8
|
+
gem "rest-client"
|
9
|
+
gem "hpricot"
|
10
|
+
gem 'itrigga-core_ext', :require=>'core_ext'
|
11
|
+
|
8
12
|
group :development do
|
9
13
|
gem "hpricot"
|
10
14
|
gem "bundler", "~> 1.0.0"
|
11
15
|
gem "jeweler", "~> 1.6.4"
|
16
|
+
gem "rspec", "1.3.0"
|
17
|
+
gem "rspec-rails", "1.3.2"
|
12
18
|
gem "rcov", ">= 0"
|
13
|
-
gem 'rspec'
|
14
19
|
gem 'json_pure'
|
15
|
-
gem 'itrigga-core_ext', ">= 0"
|
16
20
|
gem "fastercsv", ">= 1.5.4"
|
17
21
|
end
|
data/README.rdoc
CHANGED
@@ -1,6 +1,41 @@
|
|
1
1
|
= net_helper
|
2
2
|
|
3
|
-
|
3
|
+
Provides a wrapper around HTTP GET requests. Uses Net::HTTP (under RestClient) by default, but will use Typhoeus if available
|
4
|
+
Will return the raw body (unparsed) for each request.
|
5
|
+
|
6
|
+
== Usage
|
7
|
+
Rails2
|
8
|
+
gem.config 'itrigga-net_helper', :lib => 'net_helper'
|
9
|
+
|
10
|
+
Rails3 (bundler)
|
11
|
+
gem 'itrigga-net_helper', :require => 'net_helper'
|
12
|
+
|
13
|
+
=== Basic example
|
14
|
+
Itrigga::NetHelper.get :url => "http://www.google.com"
|
15
|
+
|
16
|
+
=== Adding params
|
17
|
+
Itrigga::NetHelper.get :url => "http://www.google.com", :params => {:p1 => "123"}
|
18
|
+
Gives url http://www.google.com?p1=123
|
19
|
+
|
20
|
+
=== Variables
|
21
|
+
|
22
|
+
timeout - in seconds (default 5)
|
23
|
+
retries_on_timeout - how many times to try again (default 5)
|
24
|
+
max_redirects - number of redirects to follow (default 3)
|
25
|
+
|
26
|
+
The SystemTimer gem will be used for timeout is available.
|
27
|
+
|
28
|
+
Itrigga::NetHelper.get :url => "http://www.google.com", :timeout => 300, :max_redirects => 1
|
29
|
+
|
30
|
+
== Using Typhoeus
|
31
|
+
The Typhoeus gem needs to be installed (see https://github.com/dbalatero/typhoeus)
|
32
|
+
Rails2 - gem.config 'typhoeus'
|
33
|
+
Rails3 - gem 'typhoeus'
|
34
|
+
|
35
|
+
To enable for all requests set the constant ITNH_HTTP_ENGINE = "Typhoeus"
|
36
|
+
To use on a per request basis
|
37
|
+
|
38
|
+
Itrigga::NetHelper.get :url => "http://www.google.com", :http_engine => "Typhoeus"
|
4
39
|
|
5
40
|
== Contributing to net_helper
|
6
41
|
|
data/Rakefile
CHANGED
@@ -26,22 +26,27 @@ Jeweler::Tasks.new do |gem|
|
|
26
26
|
end
|
27
27
|
Jeweler::RubygemsDotOrgTasks.new
|
28
28
|
|
29
|
-
require '
|
30
|
-
|
31
|
-
|
32
|
-
test.pattern = 'test/**/test_*.rb'
|
33
|
-
test.verbose = true
|
34
|
-
end
|
29
|
+
require 'spec/version'
|
30
|
+
require 'spec/rake/spectask'
|
31
|
+
require 'spec/ruby'
|
35
32
|
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
test.verbose = true
|
41
|
-
test.rcov_opts << '--exclude "gems/*"'
|
33
|
+
Spec::Rake::SpecTask.new(:spec) do |spec|
|
34
|
+
RAILS_ENV = "test"
|
35
|
+
spec.spec_files = FileList['spec/**/*_spec.rb']
|
36
|
+
spec.spec_opts = ['--options', 'spec/spec.opts']
|
42
37
|
end
|
43
38
|
|
44
|
-
task :default => :
|
39
|
+
task :default => :spec
|
40
|
+
|
41
|
+
desc "Run all specs with rcov"
|
42
|
+
Spec::Rake::SpecTask.new(:rcov) do |t|
|
43
|
+
t.spec_files = FileList['spec/**/*_spec.rb']
|
44
|
+
t.spec_opts = ['--options', 'spec/spec.opts']
|
45
|
+
t.rcov = true
|
46
|
+
t.rcov_dir = 'coverage'
|
47
|
+
t.rcov_opts = ['--exclude', "features,kernel,load-diff-lcs\.rb,instance_exec\.rb,lib/spec.rb,lib/spec/runner.rb,^spec/*,bin/spec,examples,/gems,/Library/Ruby,\.autotest,#{ENV['GEM_HOME']}"]
|
48
|
+
t.rcov_opts << '--sort coverage --text-summary --aggregate coverage.data'
|
49
|
+
end
|
45
50
|
|
46
51
|
require 'rake/rdoctask'
|
47
52
|
Rake::RDocTask.new do |rdoc|
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.3.0
|
data/lib/itrigga/net_helper.rb
CHANGED
@@ -1,3 +1,7 @@
|
|
1
|
+
require 'rest-client'
|
2
|
+
require 'itrigga/core_ext'
|
3
|
+
Dir[File.join(File.expand_path(File.dirname(__FILE__)),"net_helper","*.rb")].each{|f| require f}
|
4
|
+
|
1
5
|
require 'uri'
|
2
6
|
require 'hpricot'
|
3
7
|
require 'json'
|
@@ -10,171 +14,74 @@ module Itrigga
|
|
10
14
|
|
11
15
|
module_function
|
12
16
|
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
else
|
17
|
-
false
|
18
|
-
end
|
17
|
+
# gets a list of engines available (each is a different class in this module that implements 'get' method)
|
18
|
+
def available_http_engines
|
19
|
+
Itrigga::NetHelper.constants
|
19
20
|
end
|
20
|
-
|
21
|
-
def do_get(url, time_out=5, retries_on_timeout=5, max_redirects = 3)
|
22
|
-
retrycount = 0
|
23
|
-
resp = nil
|
24
|
-
begin
|
25
|
-
resp = get_with_timeout( url, time_out )
|
26
|
-
|
27
|
-
handle_response( url, resp, retries_on_timeout, max_redirects )
|
28
|
-
|
29
|
-
rescue Timeout::Error
|
30
|
-
if(retrycount.to_i < retries_on_timeout.to_i)
|
31
|
-
retrycount+=1
|
32
|
-
retry
|
33
|
-
else
|
34
|
-
raise IOError.new( "HTTP request timed out #{retrycount} times" )
|
35
|
-
end
|
36
|
-
end
|
37
21
|
|
22
|
+
def default_http_engine
|
23
|
+
"RestClient"
|
38
24
|
end
|
39
25
|
|
40
|
-
def typhoeus_request( opts={} )
|
41
|
-
opts[:timeout] ||= 30
|
42
|
-
opts[:timeout] *= 1000 # Typhoeus does its timeouts in ms
|
43
|
-
opts[:follow_location] ||= true
|
44
|
-
opts[:disable_ssl_peer_verification] = true if opts[:disable_ssl_peer_verification].nil?
|
45
|
-
|
46
|
-
request = Typhoeus::Request.new(opts[:url], opts)
|
47
|
-
|
48
|
-
request.on_complete do |response|
|
49
|
-
if response.success?
|
50
|
-
return response.body
|
51
|
-
elsif response.timed_out?
|
52
|
-
# aw hell no
|
53
|
-
raise IOError.new("Timed out request to #{opts[:url]} after #{opts[:timeout]}ms")
|
54
|
-
elsif response.code == 0
|
55
|
-
# Could not get an http response, something's wrong.
|
56
|
-
raise IOError.new(response.curl_error_message)
|
57
|
-
else
|
58
|
-
# Received a non-successful http response.
|
59
|
-
raise IOError.new("HTTP request failed: " + response.code.to_s)
|
60
|
-
end
|
61
|
-
end
|
62
|
-
|
63
|
-
hydra = Typhoeus::Hydra.new
|
64
|
-
hydra.queue(request)
|
65
|
-
hydra.run
|
66
|
-
end
|
67
26
|
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
else
|
72
|
-
Net::HTTP.get_response(URI.parse(url))
|
73
|
-
end
|
74
|
-
end
|
75
|
-
|
76
|
-
def get_with_timeout( url, time_out)
|
77
|
-
resp = nil
|
78
|
-
if defined?(SystemTimer)
|
79
|
-
resp = SystemTimer.timeout_after(time_out) do
|
80
|
-
get_response(url, time_out)
|
81
|
-
end
|
82
|
-
else
|
83
|
-
resp = timeout(time_out) do
|
84
|
-
get_response(url, time_out)
|
85
|
-
end
|
86
|
-
end
|
87
|
-
resp
|
27
|
+
# wrapper method for backwards compat.
|
28
|
+
def do_get(url, timeout=5, retries_on_timeout=5, max_redirects = 3)
|
29
|
+
get :url => url, :timeout => timeout, :retries_on_timeout => retries_on_timeout, :max_redirects => max_redirects
|
88
30
|
end
|
31
|
+
|
32
|
+
|
33
|
+
def get(options = {})
|
34
|
+
opts = { :timeout => 5, :retries_on_timeout => 5, :max_redirects => 3, :headers => {} }.merge(options)
|
35
|
+
raise ArgumentError.new(":url is required" ) unless opts[:url]
|
89
36
|
|
90
|
-
|
91
|
-
|
92
|
-
def handle_response( url, resp, retries_on_timeout=5, max_redirects = 3 )
|
93
|
-
if resp.is_a? Net::HTTPSuccess then resp.body
|
94
|
-
elsif resp.is_a? String then resp
|
95
|
-
elsif resp.is_a? Net::HTTPRedirection
|
96
|
-
if max_redirects > 0
|
97
|
-
do_get( URI.parse(url).merge(resp['location']).to_s, retries_on_timeout, max_redirects - 1 )
|
98
|
-
else
|
99
|
-
raise IOError.new("too many redirects!")
|
100
|
-
end
|
101
|
-
else
|
102
|
-
resp.error!
|
103
|
-
end
|
37
|
+
engine_klass = get_engine opts
|
38
|
+
with_timeout(opts) { engine_klass.get(opts) }
|
104
39
|
end
|
105
|
-
|
106
|
-
|
107
|
-
def get( options = {} )
|
108
|
-
opts = {:timeout=>5, :retries_on_timeout=>5, :max_redirects => 3, :headers=>{} }.merge(options)
|
109
|
-
raise ArgumentError.new(":url is required" ) unless opts[:url]
|
110
40
|
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
raw_get(opts)
|
120
|
-
end
|
121
|
-
else
|
122
|
-
timeout( opts[:timeout] ) do
|
123
|
-
raw_get(opts)
|
124
|
-
end
|
41
|
+
|
42
|
+
|
43
|
+
def with_timeout(opts, &block)
|
44
|
+
retrycount = 0
|
45
|
+
resp = begin
|
46
|
+
if defined?(SystemTimer)
|
47
|
+
SystemTimer.timeout_after(opts[:timeout]) do
|
48
|
+
yield
|
125
49
|
end
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
retry
|
130
|
-
else
|
131
|
-
raise IOError.new( "HTTP request timed out #{retrycount} times" )
|
50
|
+
else
|
51
|
+
timeout( opts[:timeout] ) do
|
52
|
+
yield
|
132
53
|
end
|
133
54
|
end
|
134
|
-
|
55
|
+
rescue ::TimeoutError, ::RestClient::RequestTimeout
|
56
|
+
if(retrycount < opts[:retries_on_timeout])
|
57
|
+
retrycount+=1
|
58
|
+
retry
|
59
|
+
else
|
60
|
+
raise IOError.new( "HTTP request timed out #{retrycount} times" )
|
61
|
+
end
|
135
62
|
end
|
63
|
+
resp
|
136
64
|
end
|
137
|
-
|
138
|
-
|
65
|
+
|
66
|
+
|
67
|
+
|
68
|
+
def get_engine(opts = {})
|
69
|
+
# default to rest_client if not given an engine
|
70
|
+
opts[:http_engine] ||= ( defined?(ITNH_HTTP_ENGINE) ? ITNH_HTTP_ENGINE : default_http_engine )
|
139
71
|
|
140
|
-
if
|
141
|
-
|
142
|
-
end
|
72
|
+
# only use typhoeus if it is actually been required
|
73
|
+
opts[:http_engine] = default_http_engine if opts[:http_engine] == "Typhoeus" && defined?(::Typhoeus) == nil
|
143
74
|
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
if opts[:username]
|
148
|
-
resp = get_with_auth(opts)
|
149
|
-
retries = 0
|
150
|
-
while resp.is_a? Net::HTTPRedirection do
|
151
|
-
retries += 1
|
152
|
-
raise IOError.new( "HTTP request timed out #{retries} times" ) if retries > (opts[:max_redirects] || 3)
|
153
|
-
|
154
|
-
resp = get_with_auth(opts.merge(:parsed_url=>URI.parse(resp['location'])))
|
155
|
-
end
|
156
|
-
|
157
|
-
resp.body
|
158
|
-
|
75
|
+
if available_http_engines.include?(opts[:http_engine])
|
76
|
+
Itrigga::NetHelper.const_get opts[:http_engine]
|
159
77
|
else
|
160
|
-
|
161
|
-
|
78
|
+
puts "[NetHelper] Could not find http_engine '#{opts[:http_engine]}'. Available engines are: #{available_http_engines.join(',')}. Defaulting to Net::HTTP"
|
79
|
+
Itrigga::NetHelper.const_get default_http_engine
|
162
80
|
end
|
81
|
+
|
163
82
|
end
|
164
|
-
|
165
|
-
def get_with_auth( opts )
|
166
|
-
establish_session_if_needed(opts)
|
167
83
|
|
168
|
-
|
169
|
-
req.basic_auth( opts[:username], opts[:password] ) if opts[:username]
|
170
|
-
resp = opts[:http_session].request(req, opts[:headers])
|
171
|
-
end
|
172
|
-
|
173
|
-
def establish_session_if_needed(opts)
|
174
|
-
opts[:parsed_url] ||= URI.parse(opts[:url])
|
175
|
-
opts[:http_session] ||= Net::HTTP.new(opts[:parsed_url].host, opts[:parsed_url].port)
|
176
|
-
opts[:http_session].use_ssl = true if opts[:parsed_url].scheme == 'https'
|
177
|
-
end
|
84
|
+
|
178
85
|
|
179
86
|
def query_string( h, opts={:encode_values=>false, :skip_empty=>false} )
|
180
87
|
params = []
|
@@ -0,0 +1,19 @@
|
|
1
|
+
module Itrigga
|
2
|
+
module NetHelper
|
3
|
+
class RestClient
|
4
|
+
|
5
|
+
def self.get( opts={} )
|
6
|
+
raise ArgumentError.new(":url is required") unless opts[:url]
|
7
|
+
|
8
|
+
# rest_client expects :user and not :username
|
9
|
+
opts[:user] ||= opts.delete(:username) if opts[:username]
|
10
|
+
|
11
|
+
opts[:headers] = {:params => opts.delete(:params)} if opts[:params]
|
12
|
+
|
13
|
+
response = ::RestClient::Request.new(opts.merge(:method => :get)).execute
|
14
|
+
response.to_str
|
15
|
+
end
|
16
|
+
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
module Itrigga
|
2
|
+
module NetHelper
|
3
|
+
class Typhoeus
|
4
|
+
|
5
|
+
def self.get( opts={} )
|
6
|
+
opts[:timeout] ||= 30
|
7
|
+
opts[:timeout] *= 1000 # Typhoeus does its timeouts in ms
|
8
|
+
opts[:follow_location] ||= true
|
9
|
+
opts[:disable_ssl_peer_verification] = true if opts[:disable_ssl_peer_verification].nil?
|
10
|
+
|
11
|
+
request = ::Typhoeus::Request.new(opts[:url], opts)
|
12
|
+
|
13
|
+
request.on_complete do |response|
|
14
|
+
if response.success?
|
15
|
+
return response.body
|
16
|
+
elsif response.timed_out?
|
17
|
+
# aw hell no
|
18
|
+
raise ::TimeoutError.new("Timed out request to #{opts[:url]} after #{opts[:timeout]}ms")
|
19
|
+
elsif response.code == 0
|
20
|
+
# Could not get an http response, something's wrong.
|
21
|
+
raise IOError.new(response.curl_error_message)
|
22
|
+
else
|
23
|
+
# Received a non-successful http response.
|
24
|
+
raise IOError.new("HTTP request failed: " + response.code.to_s)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
hydra = ::Typhoeus::Hydra.new
|
29
|
+
hydra.queue(request)
|
30
|
+
hydra.run
|
31
|
+
end
|
32
|
+
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,32 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), '..', 'spec_helper' )
|
2
|
+
|
3
|
+
describe "Itrigga::NetHelper::RestClient" do
|
4
|
+
before do
|
5
|
+
@mock_response = mock("Response", :to_str => "stuff")
|
6
|
+
@client = mock("RestClient::Request")
|
7
|
+
@client.stub!(:execute).and_return(@mock_response)
|
8
|
+
RestClient::Request.stub!(:new).and_return(@client)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should raise error if no url" do
|
12
|
+
lambda { Itrigga::NetHelper::RestClient.get }.should raise_error(ArgumentError,":url is required")
|
13
|
+
end
|
14
|
+
|
15
|
+
it "should call execute on new Request" do
|
16
|
+
RestClient::Request.should_receive(:new).with(hash_including(:method => :get, :url => "abc", :param1 => "blart")).and_return(@client)
|
17
|
+
Itrigga::NetHelper::RestClient.get :url => "abc", :param1 => "blart"
|
18
|
+
end
|
19
|
+
|
20
|
+
it "should return the correct value" do
|
21
|
+
@mock_response.should_receive(:to_str).and_return("stuff")
|
22
|
+
Itrigga::NetHelper::RestClient.get(:url => "abc").should == "stuff"
|
23
|
+
end
|
24
|
+
|
25
|
+
context "when given a :username" do
|
26
|
+
it "should convert it to :user" do
|
27
|
+
RestClient::Request.should_receive(:new).with(hash_including(:method => :get, :url => "abc", :user => "blart")).and_return(@client)
|
28
|
+
Itrigga::NetHelper::RestClient.get :url => "abc", :username => "blart"
|
29
|
+
end
|
30
|
+
end
|
31
|
+
|
32
|
+
end
|
@@ -0,0 +1,90 @@
|
|
1
|
+
require File.join(File.dirname(__FILE__), '..', 'spec_helper' )
|
2
|
+
|
3
|
+
|
4
|
+
|
5
|
+
describe "Itrigga::NetHelper::Typhoeus" do
|
6
|
+
before do
|
7
|
+
# define Typhoeus stubs as not installed as gem dependancy
|
8
|
+
Object.class_eval %{
|
9
|
+
module Typhoeus
|
10
|
+
class Request
|
11
|
+
attr_accessor :on_complete
|
12
|
+
def initialize(url,opts = {}); end
|
13
|
+
def on_complete(&block); @on_complete = block; end
|
14
|
+
end
|
15
|
+
|
16
|
+
class Hydra
|
17
|
+
attr_accessor :request
|
18
|
+
def queue(request); end
|
19
|
+
def run; end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
}
|
23
|
+
|
24
|
+
@opts = {:url => "blart"}
|
25
|
+
@response = mock("Response", :success? => true, :body => "stuff")
|
26
|
+
@request = Typhoeus::Request.new("blart", @opts)
|
27
|
+
# @request.stub!(:on_complete).and_yield(@response)
|
28
|
+
Typhoeus::Request.stub!(:new).and_return(@request)
|
29
|
+
@hydra = Typhoeus::Hydra.new
|
30
|
+
Typhoeus::Hydra.stub!(:new).and_return(@hydra)
|
31
|
+
end
|
32
|
+
|
33
|
+
after do
|
34
|
+
Object.send(:remove_const, :Typhoeus)
|
35
|
+
end
|
36
|
+
|
37
|
+
it "should create a Request object" do
|
38
|
+
Typhoeus::Request.should_receive(:new).with("blart",@opts).and_return(@request)
|
39
|
+
Itrigga::NetHelper::Typhoeus.get @opts
|
40
|
+
end
|
41
|
+
|
42
|
+
it "should call queue on hydra" do
|
43
|
+
@hydra.should_receive(:queue).with(@request)
|
44
|
+
Itrigga::NetHelper::Typhoeus.get(@opts)
|
45
|
+
end
|
46
|
+
|
47
|
+
it "should call run on hydra" do
|
48
|
+
@hydra.should_receive(:run)
|
49
|
+
Itrigga::NetHelper::Typhoeus.get(@opts)
|
50
|
+
end
|
51
|
+
|
52
|
+
it "should return the response body" do
|
53
|
+
@request.stub!(:on_complete).and_yield(@response)
|
54
|
+
Itrigga::NetHelper::Typhoeus.get(@opts).should == "stuff"
|
55
|
+
end
|
56
|
+
|
57
|
+
context "a timeout" do
|
58
|
+
before do
|
59
|
+
@response = mock("Response", :success? => false, :timed_out? => true, :body => "stuff")
|
60
|
+
@request.stub!(:on_complete).and_yield(@response)
|
61
|
+
end
|
62
|
+
|
63
|
+
it "should raise a TimeoutError" do
|
64
|
+
lambda { Itrigga::NetHelper::Typhoeus.get(@opts) }.should raise_error(TimeoutError)
|
65
|
+
end
|
66
|
+
end
|
67
|
+
|
68
|
+
context "response code == 0" do
|
69
|
+
before do
|
70
|
+
@response = mock("Response", :success? => false, :timed_out? => false, :code => 0, :body => "stuff", :curl_error_message => "blart")
|
71
|
+
@request.stub!(:on_complete).and_yield(@response)
|
72
|
+
end
|
73
|
+
|
74
|
+
it "should raise a TimeoutError" do
|
75
|
+
lambda { Itrigga::NetHelper::Typhoeus.get(@opts) }.should raise_error(IOError)
|
76
|
+
end
|
77
|
+
end
|
78
|
+
|
79
|
+
context "any other http status code" do
|
80
|
+
before do
|
81
|
+
@response = mock("Response", :success? => false, :timed_out? => false, :code => 500, :body => "stuff")
|
82
|
+
@request.stub!(:on_complete).and_yield(@response)
|
83
|
+
end
|
84
|
+
|
85
|
+
it "should raise a TimeoutError" do
|
86
|
+
lambda { Itrigga::NetHelper::Typhoeus.get(@opts) }.should raise_error(IOError)
|
87
|
+
end
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|