rest-client 1.6.7 → 1.8.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.
- checksums.yaml +7 -0
- data/.gitignore +7 -0
- data/.rspec +1 -0
- data/.travis.yml +14 -0
- data/AUTHORS +81 -0
- data/Gemfile +11 -0
- data/LICENSE +21 -0
- data/README.rdoc +63 -24
- data/Rakefile +85 -35
- data/bin/restclient +9 -8
- data/history.md +63 -1
- data/lib/restclient/abstract_response.rb +44 -15
- data/lib/restclient/exceptions.rb +20 -10
- data/lib/restclient/payload.rb +21 -18
- data/lib/restclient/platform.rb +30 -0
- data/lib/restclient/raw_response.rb +3 -2
- data/lib/restclient/request.rb +368 -63
- data/lib/restclient/resource.rb +3 -4
- data/lib/restclient/response.rb +2 -5
- data/lib/restclient/version.rb +7 -0
- data/lib/restclient/windows/root_certs.rb +105 -0
- data/lib/restclient/windows.rb +8 -0
- data/lib/restclient.rb +6 -15
- data/rest-client.gemspec +30 -0
- data/rest-client.windows.gemspec +19 -0
- data/spec/integration/capath_digicert/244b5494.0 +19 -0
- data/spec/integration/capath_digicert/81b9768f.0 +19 -0
- data/spec/integration/capath_digicert/README +8 -0
- data/spec/integration/capath_digicert/digicert.crt +19 -0
- data/spec/integration/capath_verisign/415660c1.0 +14 -0
- data/spec/integration/capath_verisign/7651b327.0 +14 -0
- data/spec/integration/capath_verisign/README +8 -0
- data/spec/integration/capath_verisign/verisign.crt +14 -0
- data/spec/integration/certs/digicert.crt +19 -0
- data/spec/{integration_spec.rb → integration/integration_spec.rb} +10 -13
- data/spec/integration/request_spec.rb +86 -7
- data/spec/spec_helper.rb +2 -0
- data/spec/{abstract_response_spec.rb → unit/abstract_response_spec.rb} +18 -15
- data/spec/{exceptions_spec.rb → unit/exceptions_spec.rb} +17 -20
- data/spec/unit/master_shake.jpg +0 -0
- data/spec/{payload_spec.rb → unit/payload_spec.rb} +42 -31
- data/spec/unit/raw_response_spec.rb +18 -0
- data/spec/{request2_spec.rb → unit/request2_spec.rb} +6 -14
- data/spec/unit/request_spec.rb +917 -0
- data/spec/{resource_spec.rb → unit/resource_spec.rb} +27 -31
- data/spec/{response_spec.rb → unit/response_spec.rb} +63 -57
- data/spec/{restclient_spec.rb → unit/restclient_spec.rb} +8 -2
- data/spec/unit/windows/root_certs_spec.rb +22 -0
- metadata +210 -112
- data/VERSION +0 -1
- data/lib/restclient/net_http_ext.rb +0 -55
- data/spec/base.rb +0 -16
- data/spec/integration/certs/equifax.crt +0 -19
- data/spec/master_shake.jpg +0 -0
- data/spec/raw_response_spec.rb +0 -17
- data/spec/request_spec.rb +0 -529
@@ -1,23 +1,20 @@
|
|
1
|
-
require
|
2
|
-
|
3
|
-
require 'webmock/rspec'
|
4
|
-
include WebMock
|
1
|
+
require 'spec_helper'
|
5
2
|
|
6
3
|
describe RestClient::Exception do
|
7
4
|
it "returns a 'message' equal to the class name if the message is not set, because 'message' should not be nil" do
|
8
5
|
e = RestClient::Exception.new
|
9
|
-
e.message.should
|
6
|
+
e.message.should eq "RestClient::Exception"
|
10
7
|
end
|
11
|
-
|
8
|
+
|
12
9
|
it "returns the 'message' that was set" do
|
13
10
|
e = RestClient::Exception.new
|
14
11
|
message = "An explicitly set message"
|
15
12
|
e.message = message
|
16
|
-
e.message.should
|
13
|
+
e.message.should eq message
|
17
14
|
end
|
18
|
-
|
15
|
+
|
19
16
|
it "sets the exception message to ErrorMessage" do
|
20
|
-
RestClient::ResourceNotFound.new.message.should
|
17
|
+
RestClient::ResourceNotFound.new.message.should eq 'Resource Not Found'
|
21
18
|
end
|
22
19
|
|
23
20
|
it "contains exceptions in RestClient" do
|
@@ -29,13 +26,13 @@ end
|
|
29
26
|
describe RestClient::ServerBrokeConnection do
|
30
27
|
it "should have a default message of 'Server broke connection'" do
|
31
28
|
e = RestClient::ServerBrokeConnection.new
|
32
|
-
e.message.should
|
29
|
+
e.message.should eq 'Server broke connection'
|
33
30
|
end
|
34
31
|
end
|
35
32
|
|
36
33
|
describe RestClient::RequestFailed do
|
37
34
|
before do
|
38
|
-
@response =
|
35
|
+
@response = double('HTTP Response', :code => '502')
|
39
36
|
end
|
40
37
|
|
41
38
|
it "stores the http response on the exception" do
|
@@ -43,17 +40,17 @@ describe RestClient::RequestFailed do
|
|
43
40
|
begin
|
44
41
|
raise RestClient::RequestFailed, response
|
45
42
|
rescue RestClient::RequestFailed => e
|
46
|
-
e.response.should
|
43
|
+
e.response.should eq response
|
47
44
|
end
|
48
45
|
end
|
49
46
|
|
50
47
|
it "http_code convenience method for fetching the code as an integer" do
|
51
|
-
RestClient::RequestFailed.new(@response).http_code.should
|
48
|
+
RestClient::RequestFailed.new(@response).http_code.should eq 502
|
52
49
|
end
|
53
50
|
|
54
51
|
it "http_body convenience method for fetching the body (decoding when necessary)" do
|
55
|
-
RestClient::RequestFailed.new(@response).http_code.should
|
56
|
-
RestClient::RequestFailed.new(@response).message.should
|
52
|
+
RestClient::RequestFailed.new(@response).http_code.should eq 502
|
53
|
+
RestClient::RequestFailed.new(@response).message.should eq 'HTTP status code 502'
|
57
54
|
end
|
58
55
|
|
59
56
|
it "shows the status code in the message" do
|
@@ -67,22 +64,22 @@ describe RestClient::ResourceNotFound do
|
|
67
64
|
begin
|
68
65
|
raise RestClient::ResourceNotFound, response
|
69
66
|
rescue RestClient::ResourceNotFound => e
|
70
|
-
e.response.should
|
67
|
+
e.response.should eq response
|
71
68
|
end
|
72
69
|
end
|
73
70
|
end
|
74
71
|
|
75
72
|
describe "backwards compatibility" do
|
76
73
|
it "alias RestClient::Request::Redirect to RestClient::Redirect" do
|
77
|
-
RestClient::Request::Redirect.should
|
74
|
+
RestClient::Request::Redirect.should eq RestClient::Redirect
|
78
75
|
end
|
79
76
|
|
80
77
|
it "alias RestClient::Request::Unauthorized to RestClient::Unauthorized" do
|
81
|
-
RestClient::Request::Unauthorized.should
|
78
|
+
RestClient::Request::Unauthorized.should eq RestClient::Unauthorized
|
82
79
|
end
|
83
80
|
|
84
81
|
it "alias RestClient::Request::RequestFailed to RestClient::RequestFailed" do
|
85
|
-
RestClient::Request::RequestFailed.should
|
82
|
+
RestClient::Request::RequestFailed.should eq RestClient::RequestFailed
|
86
83
|
end
|
87
84
|
|
88
85
|
it "make the exception's response act like an Net::HTTPResponse" do
|
@@ -92,7 +89,7 @@ describe "backwards compatibility" do
|
|
92
89
|
RestClient.get "www.example.com"
|
93
90
|
raise
|
94
91
|
rescue RestClient::ResourceNotFound => e
|
95
|
-
e.response.body.should
|
92
|
+
e.response.body.should eq body
|
96
93
|
end
|
97
94
|
end
|
98
95
|
end
|
Binary file
|
@@ -1,29 +1,31 @@
|
|
1
|
-
|
1
|
+
# encoding: binary
|
2
|
+
|
3
|
+
require 'spec_helper'
|
2
4
|
|
3
5
|
describe RestClient::Payload do
|
4
6
|
context "A regular Payload" do
|
5
7
|
it "should use standard enctype as default content-type" do
|
6
8
|
RestClient::Payload::UrlEncoded.new({}).headers['Content-Type'].
|
7
|
-
should
|
9
|
+
should eq 'application/x-www-form-urlencoded'
|
8
10
|
end
|
9
11
|
|
10
12
|
it "should form properly encoded params" do
|
11
13
|
RestClient::Payload::UrlEncoded.new({:foo => 'bar'}).to_s.
|
12
|
-
should
|
14
|
+
should eq "foo=bar"
|
13
15
|
["foo=bar&baz=qux", "baz=qux&foo=bar"].should include(
|
14
16
|
RestClient::Payload::UrlEncoded.new({:foo => 'bar', :baz => 'qux'}).to_s)
|
15
17
|
end
|
16
18
|
|
17
19
|
it "should escape parameters" do
|
18
20
|
RestClient::Payload::UrlEncoded.new({'foo ' => 'bar'}).to_s.
|
19
|
-
should
|
21
|
+
should eq "foo%20=bar"
|
20
22
|
end
|
21
23
|
|
22
24
|
it "should properly handle hashes as parameter" do
|
23
25
|
RestClient::Payload::UrlEncoded.new({:foo => {:bar => 'baz'}}).to_s.
|
24
|
-
should
|
26
|
+
should eq "foo[bar]=baz"
|
25
27
|
RestClient::Payload::UrlEncoded.new({:foo => {:bar => {:baz => 'qux'}}}).to_s.
|
26
|
-
should
|
28
|
+
should eq "foo[bar][baz]=qux"
|
27
29
|
end
|
28
30
|
|
29
31
|
it "should handle many attributes inside a hash" do
|
@@ -43,18 +45,18 @@ describe RestClient::Payload do
|
|
43
45
|
|
44
46
|
it "should form properly use symbols as parameters" do
|
45
47
|
RestClient::Payload::UrlEncoded.new({:foo => :bar}).to_s.
|
46
|
-
should
|
48
|
+
should eq "foo=bar"
|
47
49
|
RestClient::Payload::UrlEncoded.new({:foo => {:bar => :baz}}).to_s.
|
48
|
-
should
|
50
|
+
should eq "foo[bar]=baz"
|
49
51
|
end
|
50
52
|
|
51
53
|
it "should properly handle arrays as repeated parameters" do
|
52
54
|
RestClient::Payload::UrlEncoded.new({:foo => ['bar']}).to_s.
|
53
|
-
should
|
55
|
+
should eq "foo[]=bar"
|
54
56
|
RestClient::Payload::UrlEncoded.new({:foo => ['bar', 'baz']}).to_s.
|
55
|
-
should
|
57
|
+
should eq "foo[]=bar&foo[]=baz"
|
56
58
|
end
|
57
|
-
|
59
|
+
|
58
60
|
it 'should not close if stream already closed' do
|
59
61
|
p = RestClient::Payload::UrlEncoded.new({'foo ' => 'bar'})
|
60
62
|
3.times {p.close}
|
@@ -65,10 +67,10 @@ describe RestClient::Payload do
|
|
65
67
|
context "A multipart Payload" do
|
66
68
|
it "should use standard enctype as default content-type" do
|
67
69
|
m = RestClient::Payload::Multipart.new({})
|
68
|
-
m.stub
|
69
|
-
m.headers['Content-Type'].should
|
70
|
+
m.stub(:boundary).and_return(123)
|
71
|
+
m.headers['Content-Type'].should eq 'multipart/form-data; boundary=123'
|
70
72
|
end
|
71
|
-
|
73
|
+
|
72
74
|
it 'should not error on close if stream already closed' do
|
73
75
|
m = RestClient::Payload::Multipart.new(:file => File.new(File.join(File.dirname(File.expand_path(__FILE__)), 'master_shake.jpg')))
|
74
76
|
3.times {m.close}
|
@@ -76,7 +78,7 @@ describe RestClient::Payload do
|
|
76
78
|
|
77
79
|
it "should form properly separated multipart data" do
|
78
80
|
m = RestClient::Payload::Multipart.new([[:bar, "baz"], [:foo, "bar"]])
|
79
|
-
m.to_s.should
|
81
|
+
m.to_s.should eq <<-EOS
|
80
82
|
--#{m.boundary}\r
|
81
83
|
Content-Disposition: form-data; name="bar"\r
|
82
84
|
\r
|
@@ -91,7 +93,7 @@ bar\r
|
|
91
93
|
|
92
94
|
it "should not escape parameters names" do
|
93
95
|
m = RestClient::Payload::Multipart.new([["bar ", "baz"]])
|
94
|
-
m.to_s.should
|
96
|
+
m.to_s.should eq <<-EOS
|
95
97
|
--#{m.boundary}\r
|
96
98
|
Content-Disposition: form-data; name="bar "\r
|
97
99
|
\r
|
@@ -103,12 +105,12 @@ baz\r
|
|
103
105
|
it "should form properly separated multipart data" do
|
104
106
|
f = File.new(File.dirname(__FILE__) + "/master_shake.jpg")
|
105
107
|
m = RestClient::Payload::Multipart.new({:foo => f})
|
106
|
-
m.to_s.should
|
108
|
+
m.to_s.should eq <<-EOS
|
107
109
|
--#{m.boundary}\r
|
108
110
|
Content-Disposition: form-data; name="foo"; filename="master_shake.jpg"\r
|
109
111
|
Content-Type: image/jpeg\r
|
110
112
|
\r
|
111
|
-
#{
|
113
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
112
114
|
--#{m.boundary}--\r
|
113
115
|
EOS
|
114
116
|
end
|
@@ -116,12 +118,12 @@ Content-Type: image/jpeg\r
|
|
116
118
|
it "should ignore the name attribute when it's not set" do
|
117
119
|
f = File.new(File.dirname(__FILE__) + "/master_shake.jpg")
|
118
120
|
m = RestClient::Payload::Multipart.new({nil => f})
|
119
|
-
m.to_s.should
|
121
|
+
m.to_s.should eq <<-EOS
|
120
122
|
--#{m.boundary}\r
|
121
123
|
Content-Disposition: form-data; filename="master_shake.jpg"\r
|
122
124
|
Content-Type: image/jpeg\r
|
123
125
|
\r
|
124
|
-
#{
|
126
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
125
127
|
--#{m.boundary}--\r
|
126
128
|
EOS
|
127
129
|
end
|
@@ -131,19 +133,19 @@ Content-Type: image/jpeg\r
|
|
131
133
|
f.instance_eval "def content_type; 'text/plain'; end"
|
132
134
|
f.instance_eval "def original_filename; 'foo.txt'; end"
|
133
135
|
m = RestClient::Payload::Multipart.new({:foo => f})
|
134
|
-
m.to_s.should
|
136
|
+
m.to_s.should eq <<-EOS
|
135
137
|
--#{m.boundary}\r
|
136
138
|
Content-Disposition: form-data; name="foo"; filename="foo.txt"\r
|
137
139
|
Content-Type: text/plain\r
|
138
140
|
\r
|
139
|
-
#{
|
141
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
140
142
|
--#{m.boundary}--\r
|
141
143
|
EOS
|
142
144
|
end
|
143
145
|
|
144
146
|
it "should handle hash in hash parameters" do
|
145
147
|
m = RestClient::Payload::Multipart.new({:bar => {:baz => "foo"}})
|
146
|
-
m.to_s.should
|
148
|
+
m.to_s.should eq <<-EOS
|
147
149
|
--#{m.boundary}\r
|
148
150
|
Content-Disposition: form-data; name="bar[baz]"\r
|
149
151
|
\r
|
@@ -155,12 +157,12 @@ foo\r
|
|
155
157
|
f.instance_eval "def content_type; 'text/plain'; end"
|
156
158
|
f.instance_eval "def original_filename; 'foo.txt'; end"
|
157
159
|
m = RestClient::Payload::Multipart.new({:foo => {:bar => f}})
|
158
|
-
m.to_s.should
|
160
|
+
m.to_s.should eq <<-EOS
|
159
161
|
--#{m.boundary}\r
|
160
162
|
Content-Disposition: form-data; name="foo[bar]"; filename="foo.txt"\r
|
161
163
|
Content-Type: text/plain\r
|
162
164
|
\r
|
163
|
-
#{
|
165
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
164
166
|
--#{m.boundary}--\r
|
165
167
|
EOS
|
166
168
|
end
|
@@ -171,23 +173,23 @@ Content-Type: text/plain\r
|
|
171
173
|
it "should properly determine the size of file payloads" do
|
172
174
|
f = File.new(File.dirname(__FILE__) + "/master_shake.jpg")
|
173
175
|
payload = RestClient::Payload.generate(f)
|
174
|
-
payload.size.should
|
175
|
-
payload.length.should
|
176
|
+
payload.size.should eq 76_988
|
177
|
+
payload.length.should eq 76_988
|
176
178
|
end
|
177
179
|
|
178
180
|
it "should properly determine the size of other kinds of streaming payloads" do
|
179
181
|
s = StringIO.new 'foo'
|
180
182
|
payload = RestClient::Payload.generate(s)
|
181
|
-
payload.size.should
|
182
|
-
payload.length.should
|
183
|
+
payload.size.should eq 3
|
184
|
+
payload.length.should eq 3
|
183
185
|
|
184
186
|
begin
|
185
187
|
f = Tempfile.new "rest-client"
|
186
188
|
f.write 'foo bar'
|
187
189
|
|
188
190
|
payload = RestClient::Payload.generate(f)
|
189
|
-
payload.size.should
|
190
|
-
payload.length.should
|
191
|
+
payload.size.should eq 7
|
192
|
+
payload.length.should eq 7
|
191
193
|
ensure
|
192
194
|
f.close
|
193
195
|
end
|
@@ -230,5 +232,14 @@ Content-Type: text/plain\r
|
|
230
232
|
it "should recognize other payloads that can be streamed" do
|
231
233
|
RestClient::Payload.generate(StringIO.new('foo')).should be_kind_of(RestClient::Payload::Streamed)
|
232
234
|
end
|
235
|
+
|
236
|
+
# hashery gem introduces Hash#read convenience method. Existence of #read method used to determine of content is streameable :/
|
237
|
+
it "shouldn't treat hashes as streameable" do
|
238
|
+
RestClient::Payload.generate({"foo" => 'bar'}).should be_kind_of(RestClient::Payload::UrlEncoded)
|
239
|
+
end
|
240
|
+
end
|
241
|
+
|
242
|
+
class HashMapForTesting < Hash
|
243
|
+
alias :read :[]
|
233
244
|
end
|
234
245
|
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
describe RestClient::RawResponse do
|
4
|
+
before do
|
5
|
+
@tf = double("Tempfile", :read => "the answer is 42", :open => true)
|
6
|
+
@net_http_res = double('net http response')
|
7
|
+
@request = double('http request')
|
8
|
+
@response = RestClient::RawResponse.new(@tf, @net_http_res, {}, @request)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "behaves like string" do
|
12
|
+
@response.to_s.should eq 'the answer is 42'
|
13
|
+
end
|
14
|
+
|
15
|
+
it "exposes a Tempfile" do
|
16
|
+
@response.file.should eq @tf
|
17
|
+
end
|
18
|
+
end
|
@@ -1,40 +1,32 @@
|
|
1
|
-
require
|
2
|
-
|
3
|
-
require 'webmock/rspec'
|
4
|
-
include WebMock
|
1
|
+
require 'spec_helper'
|
5
2
|
|
6
3
|
describe RestClient::Request do
|
7
4
|
|
8
5
|
it "manage params for get requests" do
|
9
6
|
stub_request(:get, 'http://some/resource?a=b&c=d').with(:headers => {'Accept'=>'*/*; q=0.5, application/xml', 'Accept-Encoding'=>'gzip, deflate', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
10
|
-
RestClient::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => {:a => :b, 'c' => 'd'}}).body.should
|
7
|
+
RestClient::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => {:a => :b, 'c' => 'd'}}).body.should eq 'foo'
|
11
8
|
|
12
9
|
stub_request(:get, 'http://some/resource').with(:headers => {'Accept'=>'*/*; q=0.5, application/xml', 'Accept-Encoding'=>'gzip, deflate', 'Foo'=>'bar', 'params' => 'a'}).to_return(:body => 'foo', :status => 200)
|
13
|
-
RestClient::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => :a}).body.should
|
10
|
+
RestClient::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => :a}).body.should eq 'foo'
|
14
11
|
end
|
15
12
|
|
16
13
|
it "can use a block to process response" do
|
17
14
|
response_value = nil
|
18
|
-
block =
|
15
|
+
block = proc do |http_response|
|
19
16
|
response_value = http_response.body
|
20
17
|
end
|
21
18
|
stub_request(:get, 'http://some/resource?a=b&c=d').with(:headers => {'Accept'=>'*/*; q=0.5, application/xml', 'Accept-Encoding'=>'gzip, deflate', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
22
19
|
RestClient::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => {:a => :b, 'c' => 'd'}}, :block_response => block)
|
23
|
-
response_value.should
|
20
|
+
response_value.should eq "foo"
|
24
21
|
end
|
25
22
|
|
26
23
|
it 'closes payload if not nil' do
|
27
24
|
test_file = File.new(File.join( File.dirname(File.expand_path(__FILE__)), 'master_shake.jpg'))
|
28
|
-
initial_count = tmp_count
|
29
25
|
|
30
26
|
stub_request(:post, 'http://some/resource').with(:headers => {'Accept'=>'*/*; q=0.5, application/xml', 'Accept-Encoding'=>'gzip, deflate'}).to_return(:body => 'foo', :status => 200)
|
31
27
|
RestClient::Request.execute(:url => 'http://some/resource', :method => :post, :payload => {:file => test_file})
|
32
28
|
|
33
|
-
|
29
|
+
test_file.closed?.should be_true
|
34
30
|
end
|
35
31
|
|
36
32
|
end
|
37
|
-
|
38
|
-
def tmp_count
|
39
|
-
Dir.glob(Dir::tmpdir + "/*").size
|
40
|
-
end
|