rest-man 1.0.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/.github/workflows/multi-matrix-test.yml +35 -0
- data/.github/workflows/single-matrix-test.yml +27 -0
- data/.gitignore +13 -0
- data/.mailmap +10 -0
- data/.rspec +2 -0
- data/.rubocop +2 -0
- data/.rubocop-disables.yml +386 -0
- data/.rubocop.yml +8 -0
- data/AUTHORS +106 -0
- data/CHANGELOG.md +7 -0
- data/Gemfile +11 -0
- data/LICENSE +21 -0
- data/README.md +843 -0
- data/Rakefile +140 -0
- data/exe/restman +92 -0
- data/lib/rest-man.rb +2 -0
- data/lib/rest_man.rb +2 -0
- data/lib/restman/abstract_response.rb +252 -0
- data/lib/restman/exceptions.rb +238 -0
- data/lib/restman/params_array.rb +72 -0
- data/lib/restman/payload.rb +234 -0
- data/lib/restman/platform.rb +49 -0
- data/lib/restman/raw_response.rb +49 -0
- data/lib/restman/request.rb +859 -0
- data/lib/restman/resource.rb +178 -0
- data/lib/restman/response.rb +90 -0
- data/lib/restman/utils.rb +274 -0
- data/lib/restman/version.rb +8 -0
- data/lib/restman/windows/root_certs.rb +105 -0
- data/lib/restman/windows.rb +8 -0
- data/lib/restman.rb +183 -0
- data/matrixeval.yml +73 -0
- data/rest-man.gemspec +41 -0
- data/spec/ISS.jpg +0 -0
- data/spec/cassettes/request_httpbin_with_basic_auth.yml +83 -0
- data/spec/cassettes/request_httpbin_with_cookies.yml +49 -0
- data/spec/cassettes/request_httpbin_with_cookies_2.yml +94 -0
- data/spec/cassettes/request_httpbin_with_cookies_3.yml +49 -0
- data/spec/cassettes/request_httpbin_with_encoding_deflate.yml +45 -0
- data/spec/cassettes/request_httpbin_with_encoding_deflate_and_accept_headers.yml +44 -0
- data/spec/cassettes/request_httpbin_with_encoding_gzip.yml +45 -0
- data/spec/cassettes/request_httpbin_with_encoding_gzip_and_accept_headers.yml +44 -0
- data/spec/cassettes/request_httpbin_with_user_agent.yml +44 -0
- data/spec/cassettes/request_mozilla_org.yml +151 -0
- data/spec/cassettes/request_mozilla_org_callback_returns_true.yml +178 -0
- data/spec/cassettes/request_mozilla_org_with_system_cert.yml +152 -0
- data/spec/cassettes/request_mozilla_org_with_system_cert_and_callback.yml +151 -0
- data/spec/helpers.rb +54 -0
- data/spec/integration/_lib.rb +1 -0
- data/spec/integration/capath_digicert/README +8 -0
- data/spec/integration/capath_digicert/ce5e74ef.0 +1 -0
- data/spec/integration/capath_digicert/digicert.crt +20 -0
- data/spec/integration/capath_digicert/update +1 -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 +20 -0
- data/spec/integration/certs/verisign.crt +14 -0
- data/spec/integration/httpbin_spec.rb +137 -0
- data/spec/integration/integration_spec.rb +118 -0
- data/spec/integration/request_spec.rb +134 -0
- data/spec/spec_helper.rb +40 -0
- data/spec/unit/_lib.rb +1 -0
- data/spec/unit/abstract_response_spec.rb +145 -0
- data/spec/unit/exceptions_spec.rb +108 -0
- data/spec/unit/params_array_spec.rb +36 -0
- data/spec/unit/payload_spec.rb +295 -0
- data/spec/unit/raw_response_spec.rb +22 -0
- data/spec/unit/request2_spec.rb +54 -0
- data/spec/unit/request_spec.rb +1205 -0
- data/spec/unit/resource_spec.rb +134 -0
- data/spec/unit/response_spec.rb +252 -0
- data/spec/unit/restclient_spec.rb +80 -0
- data/spec/unit/utils_spec.rb +147 -0
- data/spec/unit/windows/root_certs_spec.rb +22 -0
- metadata +336 -0
@@ -0,0 +1,108 @@
|
|
1
|
+
require_relative '_lib'
|
2
|
+
|
3
|
+
describe RestMan::Exception do
|
4
|
+
it "returns a 'message' equal to the class name if the message is not set, because 'message' should not be nil" do
|
5
|
+
e = RestMan::Exception.new
|
6
|
+
expect(e.message).to eq "RestMan::Exception"
|
7
|
+
end
|
8
|
+
|
9
|
+
it "returns the 'message' that was set" do
|
10
|
+
e = RestMan::Exception.new
|
11
|
+
message = "An explicitly set message"
|
12
|
+
e.message = message
|
13
|
+
expect(e.message).to eq message
|
14
|
+
end
|
15
|
+
|
16
|
+
it "sets the exception message to ErrorMessage" do
|
17
|
+
expect(RestMan::ResourceNotFound.new.message).to eq 'Not Found'
|
18
|
+
end
|
19
|
+
|
20
|
+
it "contains exceptions in RestMan" do
|
21
|
+
expect(RestMan::Unauthorized.new).to be_a_kind_of(RestMan::Exception)
|
22
|
+
expect(RestMan::ServerBrokeConnection.new).to be_a_kind_of(RestMan::Exception)
|
23
|
+
end
|
24
|
+
end
|
25
|
+
|
26
|
+
describe RestMan::ServerBrokeConnection do
|
27
|
+
it "should have a default message of 'Server broke connection'" do
|
28
|
+
e = RestMan::ServerBrokeConnection.new
|
29
|
+
expect(e.message).to eq 'Server broke connection'
|
30
|
+
end
|
31
|
+
end
|
32
|
+
|
33
|
+
describe RestMan::RequestFailed do
|
34
|
+
before do
|
35
|
+
@response = double('HTTP Response', :code => '502')
|
36
|
+
end
|
37
|
+
|
38
|
+
it "stores the http response on the exception" do
|
39
|
+
response = "response"
|
40
|
+
begin
|
41
|
+
raise RestMan::RequestFailed, response
|
42
|
+
rescue RestMan::RequestFailed => e
|
43
|
+
expect(e.response).to eq response
|
44
|
+
end
|
45
|
+
end
|
46
|
+
|
47
|
+
it "http_code convenience method for fetching the code as an integer" do
|
48
|
+
expect(RestMan::RequestFailed.new(@response).http_code).to eq 502
|
49
|
+
end
|
50
|
+
|
51
|
+
it "http_body convenience method for fetching the body (decoding when necessary)" do
|
52
|
+
expect(RestMan::RequestFailed.new(@response).http_code).to eq 502
|
53
|
+
expect(RestMan::RequestFailed.new(@response).message).to eq 'HTTP status code 502'
|
54
|
+
end
|
55
|
+
|
56
|
+
it "shows the status code in the message" do
|
57
|
+
expect(RestMan::RequestFailed.new(@response).to_s).to match(/502/)
|
58
|
+
end
|
59
|
+
end
|
60
|
+
|
61
|
+
describe RestMan::ResourceNotFound do
|
62
|
+
it "also has the http response attached" do
|
63
|
+
response = "response"
|
64
|
+
begin
|
65
|
+
raise RestMan::ResourceNotFound, response
|
66
|
+
rescue RestMan::ResourceNotFound => e
|
67
|
+
expect(e.response).to eq response
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
it 'stores the body on the response of the exception' do
|
72
|
+
body = "body"
|
73
|
+
stub_request(:get, "www.example.com").to_return(:body => body, :status => 404)
|
74
|
+
begin
|
75
|
+
RestMan.get "www.example.com"
|
76
|
+
raise
|
77
|
+
rescue RestMan::ResourceNotFound => e
|
78
|
+
expect(e.response.body).to eq body
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
83
|
+
describe "backwards compatibility" do
|
84
|
+
it 'aliases RestMan::NotFound as ResourceNotFound' do
|
85
|
+
expect(RestMan::ResourceNotFound).to eq RestMan::NotFound
|
86
|
+
end
|
87
|
+
|
88
|
+
it 'aliases old names for HTTP 413, 414, 416' do
|
89
|
+
expect(RestMan::RequestEntityTooLarge).to eq RestMan::PayloadTooLarge
|
90
|
+
expect(RestMan::RequestURITooLong).to eq RestMan::URITooLong
|
91
|
+
expect(RestMan::RequestedRangeNotSatisfiable).to eq RestMan::RangeNotSatisfiable
|
92
|
+
end
|
93
|
+
|
94
|
+
it 'subclasses NotFound from RequestFailed, ExceptionWithResponse' do
|
95
|
+
expect(RestMan::NotFound).to be < RestMan::RequestFailed
|
96
|
+
expect(RestMan::NotFound).to be < RestMan::ExceptionWithResponse
|
97
|
+
end
|
98
|
+
|
99
|
+
it 'subclasses timeout from RestMan::RequestTimeout, RequestFailed, EWR' do
|
100
|
+
expect(RestMan::Exceptions::OpenTimeout).to be < RestMan::Exceptions::Timeout
|
101
|
+
expect(RestMan::Exceptions::ReadTimeout).to be < RestMan::Exceptions::Timeout
|
102
|
+
|
103
|
+
expect(RestMan::Exceptions::Timeout).to be < RestMan::RequestTimeout
|
104
|
+
expect(RestMan::Exceptions::Timeout).to be < RestMan::RequestFailed
|
105
|
+
expect(RestMan::Exceptions::Timeout).to be < RestMan::ExceptionWithResponse
|
106
|
+
end
|
107
|
+
|
108
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
require_relative '_lib'
|
2
|
+
|
3
|
+
describe RestMan::ParamsArray do
|
4
|
+
|
5
|
+
describe '.new' do
|
6
|
+
it 'accepts various types of containers' do
|
7
|
+
as_array = [[:foo, 123], [:foo, 456], [:bar, 789], [:empty, nil]]
|
8
|
+
[
|
9
|
+
[[:foo, 123], [:foo, 456], [:bar, 789], [:empty, nil]],
|
10
|
+
[{foo: 123}, {foo: 456}, {bar: 789}, {empty: nil}],
|
11
|
+
[{foo: 123}, {foo: 456}, {bar: 789}, {empty: nil}],
|
12
|
+
[{foo: 123}, [:foo, 456], {bar: 789}, {empty: nil}],
|
13
|
+
[{foo: 123}, [:foo, 456], {bar: 789}, [:empty]],
|
14
|
+
].each do |input|
|
15
|
+
expect(RestMan::ParamsArray.new(input).to_a).to eq as_array
|
16
|
+
end
|
17
|
+
|
18
|
+
expect(RestMan::ParamsArray.new([]).to_a).to eq []
|
19
|
+
expect(RestMan::ParamsArray.new([]).empty?).to eq true
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'rejects various invalid input' do
|
23
|
+
expect {
|
24
|
+
RestMan::ParamsArray.new([[]])
|
25
|
+
}.to raise_error(IndexError)
|
26
|
+
|
27
|
+
expect {
|
28
|
+
RestMan::ParamsArray.new([[1,2,3]])
|
29
|
+
}.to raise_error(ArgumentError)
|
30
|
+
|
31
|
+
expect {
|
32
|
+
RestMan::ParamsArray.new([1,2,3])
|
33
|
+
}.to raise_error(NoMethodError)
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
@@ -0,0 +1,295 @@
|
|
1
|
+
# encoding: binary
|
2
|
+
|
3
|
+
require_relative '_lib'
|
4
|
+
|
5
|
+
describe RestMan::Payload, :include_helpers do
|
6
|
+
context "Base Payload" do
|
7
|
+
it "should reset stream after to_s" do
|
8
|
+
payload = RestMan::Payload::Base.new('foobar')
|
9
|
+
expect(payload.to_s).to eq 'foobar'
|
10
|
+
expect(payload.to_s).to eq 'foobar'
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
context "A regular Payload" do
|
15
|
+
it "should use standard enctype as default content-type" do
|
16
|
+
expect(RestMan::Payload::UrlEncoded.new({}).headers['Content-Type']).
|
17
|
+
to eq 'application/x-www-form-urlencoded'
|
18
|
+
end
|
19
|
+
|
20
|
+
it "should form properly encoded params" do
|
21
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => 'bar'}).to_s).
|
22
|
+
to eq "foo=bar"
|
23
|
+
expect(["foo=bar&baz=qux", "baz=qux&foo=bar"]).to include(
|
24
|
+
RestMan::Payload::UrlEncoded.new({:foo => 'bar', :baz => 'qux'}).to_s)
|
25
|
+
end
|
26
|
+
|
27
|
+
it "should escape parameters" do
|
28
|
+
expect(RestMan::Payload::UrlEncoded.new({'foo + bar' => 'baz'}).to_s).
|
29
|
+
to eq "foo+%2B+bar=baz"
|
30
|
+
end
|
31
|
+
|
32
|
+
it "should properly handle hashes as parameter" do
|
33
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => {:bar => 'baz'}}).to_s).
|
34
|
+
to eq "foo[bar]=baz"
|
35
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => {:bar => {:baz => 'qux'}}}).to_s).
|
36
|
+
to eq "foo[bar][baz]=qux"
|
37
|
+
end
|
38
|
+
|
39
|
+
it "should handle many attributes inside a hash" do
|
40
|
+
parameters = RestMan::Payload::UrlEncoded.new({:foo => {:bar => 'baz', :baz => 'qux'}}).to_s
|
41
|
+
expect(parameters).to eq 'foo[bar]=baz&foo[baz]=qux'
|
42
|
+
end
|
43
|
+
|
44
|
+
it "should handle attributes inside an array inside an hash" do
|
45
|
+
parameters = RestMan::Payload::UrlEncoded.new({"foo" => [{"bar" => 'baz'}, {"bar" => 'qux'}]}).to_s
|
46
|
+
expect(parameters).to eq 'foo[][bar]=baz&foo[][bar]=qux'
|
47
|
+
end
|
48
|
+
|
49
|
+
it "should handle arrays inside a hash inside a hash" do
|
50
|
+
parameters = RestMan::Payload::UrlEncoded.new({"foo" => {'even' => [0, 2], 'odd' => [1, 3]}}).to_s
|
51
|
+
expect(parameters).to eq 'foo[even][]=0&foo[even][]=2&foo[odd][]=1&foo[odd][]=3'
|
52
|
+
end
|
53
|
+
|
54
|
+
it "should form properly use symbols as parameters" do
|
55
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => :bar}).to_s).
|
56
|
+
to eq "foo=bar"
|
57
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => {:bar => :baz}}).to_s).
|
58
|
+
to eq "foo[bar]=baz"
|
59
|
+
end
|
60
|
+
|
61
|
+
it "should properly handle arrays as repeated parameters" do
|
62
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => ['bar']}).to_s).
|
63
|
+
to eq "foo[]=bar"
|
64
|
+
expect(RestMan::Payload::UrlEncoded.new({:foo => ['bar', 'baz']}).to_s).
|
65
|
+
to eq "foo[]=bar&foo[]=baz"
|
66
|
+
end
|
67
|
+
|
68
|
+
it 'should not close if stream already closed' do
|
69
|
+
p = RestMan::Payload::UrlEncoded.new({'foo ' => 'bar'})
|
70
|
+
3.times {p.close}
|
71
|
+
end
|
72
|
+
|
73
|
+
end
|
74
|
+
|
75
|
+
context "A multipart Payload" do
|
76
|
+
it "should use standard enctype as default content-type" do
|
77
|
+
m = RestMan::Payload::Multipart.new({})
|
78
|
+
allow(m).to receive(:boundary).and_return(123)
|
79
|
+
expect(m.headers['Content-Type']).to eq 'multipart/form-data; boundary=123'
|
80
|
+
end
|
81
|
+
|
82
|
+
it 'should not error on close if stream already closed' do
|
83
|
+
m = RestMan::Payload::Multipart.new(:file => File.new(test_image_path))
|
84
|
+
3.times {m.close}
|
85
|
+
end
|
86
|
+
|
87
|
+
it "should form properly separated multipart data" do
|
88
|
+
m = RestMan::Payload::Multipart.new([[:bar, "baz"], [:foo, "bar"]])
|
89
|
+
expect(m.to_s).to eq <<-EOS
|
90
|
+
--#{m.boundary}\r
|
91
|
+
Content-Disposition: form-data; name="bar"\r
|
92
|
+
\r
|
93
|
+
baz\r
|
94
|
+
--#{m.boundary}\r
|
95
|
+
Content-Disposition: form-data; name="foo"\r
|
96
|
+
\r
|
97
|
+
bar\r
|
98
|
+
--#{m.boundary}--\r
|
99
|
+
EOS
|
100
|
+
end
|
101
|
+
|
102
|
+
it "should not escape parameters names" do
|
103
|
+
m = RestMan::Payload::Multipart.new([["bar ", "baz"]])
|
104
|
+
expect(m.to_s).to eq <<-EOS
|
105
|
+
--#{m.boundary}\r
|
106
|
+
Content-Disposition: form-data; name="bar "\r
|
107
|
+
\r
|
108
|
+
baz\r
|
109
|
+
--#{m.boundary}--\r
|
110
|
+
EOS
|
111
|
+
end
|
112
|
+
|
113
|
+
it "should form properly separated multipart data" do
|
114
|
+
f = File.new(test_image_path)
|
115
|
+
m = RestMan::Payload::Multipart.new({:foo => f})
|
116
|
+
expect(m.to_s).to eq <<-EOS
|
117
|
+
--#{m.boundary}\r
|
118
|
+
Content-Disposition: form-data; name="foo"; filename="ISS.jpg"\r
|
119
|
+
Content-Type: image/jpeg\r
|
120
|
+
\r
|
121
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
122
|
+
--#{m.boundary}--\r
|
123
|
+
EOS
|
124
|
+
end
|
125
|
+
|
126
|
+
it "should ignore the name attribute when it's not set" do
|
127
|
+
f = File.new(test_image_path)
|
128
|
+
m = RestMan::Payload::Multipart.new({nil => f})
|
129
|
+
expect(m.to_s).to eq <<-EOS
|
130
|
+
--#{m.boundary}\r
|
131
|
+
Content-Disposition: form-data; filename="ISS.jpg"\r
|
132
|
+
Content-Type: image/jpeg\r
|
133
|
+
\r
|
134
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
135
|
+
--#{m.boundary}--\r
|
136
|
+
EOS
|
137
|
+
end
|
138
|
+
|
139
|
+
it "should detect optional (original) content type and filename" do
|
140
|
+
f = File.new(test_image_path)
|
141
|
+
expect(f).to receive(:content_type).and_return('text/plain')
|
142
|
+
expect(f).to receive(:original_filename).and_return('foo.txt')
|
143
|
+
m = RestMan::Payload::Multipart.new({:foo => f})
|
144
|
+
expect(m.to_s).to eq <<-EOS
|
145
|
+
--#{m.boundary}\r
|
146
|
+
Content-Disposition: form-data; name="foo"; filename="foo.txt"\r
|
147
|
+
Content-Type: text/plain\r
|
148
|
+
\r
|
149
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
150
|
+
--#{m.boundary}--\r
|
151
|
+
EOS
|
152
|
+
end
|
153
|
+
|
154
|
+
it "should handle hash in hash parameters" do
|
155
|
+
m = RestMan::Payload::Multipart.new({:bar => {:baz => "foo"}})
|
156
|
+
expect(m.to_s).to eq <<-EOS
|
157
|
+
--#{m.boundary}\r
|
158
|
+
Content-Disposition: form-data; name="bar[baz]"\r
|
159
|
+
\r
|
160
|
+
foo\r
|
161
|
+
--#{m.boundary}--\r
|
162
|
+
EOS
|
163
|
+
|
164
|
+
f = File.new(test_image_path)
|
165
|
+
f.instance_eval "def content_type; 'text/plain'; end"
|
166
|
+
f.instance_eval "def original_filename; 'foo.txt'; end"
|
167
|
+
m = RestMan::Payload::Multipart.new({:foo => {:bar => f}})
|
168
|
+
expect(m.to_s).to eq <<-EOS
|
169
|
+
--#{m.boundary}\r
|
170
|
+
Content-Disposition: form-data; name="foo[bar]"; filename="foo.txt"\r
|
171
|
+
Content-Type: text/plain\r
|
172
|
+
\r
|
173
|
+
#{File.open(f.path, 'rb'){|bin| bin.read}}\r
|
174
|
+
--#{m.boundary}--\r
|
175
|
+
EOS
|
176
|
+
end
|
177
|
+
|
178
|
+
it 'should correctly format hex boundary' do
|
179
|
+
allow(SecureRandom).to receive(:base64).with(12).and_return('TGs89+ttw/xna6TV')
|
180
|
+
f = File.new(test_image_path)
|
181
|
+
m = RestMan::Payload::Multipart.new({:foo => f})
|
182
|
+
expect(m.boundary).to eq('-' * 4 + 'RubyFormBoundary' + 'TGs89AttwBxna6TV')
|
183
|
+
end
|
184
|
+
|
185
|
+
end
|
186
|
+
|
187
|
+
context "streamed payloads" do
|
188
|
+
it "should properly determine the size of file payloads" do
|
189
|
+
f = File.new(test_image_path)
|
190
|
+
payload = RestMan::Payload.generate(f)
|
191
|
+
expect(payload.size).to eq 72_463
|
192
|
+
expect(payload.length).to eq 72_463
|
193
|
+
end
|
194
|
+
|
195
|
+
it "should properly determine the size of other kinds of streaming payloads" do
|
196
|
+
s = StringIO.new 'foo'
|
197
|
+
payload = RestMan::Payload.generate(s)
|
198
|
+
expect(payload.size).to eq 3
|
199
|
+
expect(payload.length).to eq 3
|
200
|
+
|
201
|
+
begin
|
202
|
+
f = Tempfile.new "rest-man"
|
203
|
+
f.write 'foo bar'
|
204
|
+
|
205
|
+
payload = RestMan::Payload.generate(f)
|
206
|
+
expect(payload.size).to eq 7
|
207
|
+
expect(payload.length).to eq 7
|
208
|
+
ensure
|
209
|
+
f.close
|
210
|
+
end
|
211
|
+
end
|
212
|
+
|
213
|
+
it "should have a closed? method" do
|
214
|
+
f = File.new(test_image_path)
|
215
|
+
payload = RestMan::Payload.generate(f)
|
216
|
+
expect(payload.closed?).to be_falsey
|
217
|
+
payload.close
|
218
|
+
expect(payload.closed?).to be_truthy
|
219
|
+
end
|
220
|
+
end
|
221
|
+
|
222
|
+
context "Payload generation" do
|
223
|
+
it "should recognize standard urlencoded params" do
|
224
|
+
expect(RestMan::Payload.generate({"foo" => 'bar'})).to be_kind_of(RestMan::Payload::UrlEncoded)
|
225
|
+
end
|
226
|
+
|
227
|
+
it "should recognize multipart params" do
|
228
|
+
f = File.new(test_image_path)
|
229
|
+
expect(RestMan::Payload.generate({"foo" => f})).to be_kind_of(RestMan::Payload::Multipart)
|
230
|
+
end
|
231
|
+
|
232
|
+
it "should be multipart if forced" do
|
233
|
+
expect(RestMan::Payload.generate({"foo" => "bar", :multipart => true})).to be_kind_of(RestMan::Payload::Multipart)
|
234
|
+
end
|
235
|
+
|
236
|
+
it "should handle deeply nested multipart" do
|
237
|
+
f = File.new(test_image_path)
|
238
|
+
params = {foo: RestMan::ParamsArray.new({nested: f})}
|
239
|
+
expect(RestMan::Payload.generate(params)).to be_kind_of(RestMan::Payload::Multipart)
|
240
|
+
end
|
241
|
+
|
242
|
+
|
243
|
+
it "should return data if no of the above" do
|
244
|
+
expect(RestMan::Payload.generate("data")).to be_kind_of(RestMan::Payload::Base)
|
245
|
+
end
|
246
|
+
|
247
|
+
it "should recognize nested multipart payloads in hashes" do
|
248
|
+
f = File.new(test_image_path)
|
249
|
+
expect(RestMan::Payload.generate({"foo" => {"file" => f}})).to be_kind_of(RestMan::Payload::Multipart)
|
250
|
+
end
|
251
|
+
|
252
|
+
it "should recognize nested multipart payloads in arrays" do
|
253
|
+
f = File.new(test_image_path)
|
254
|
+
expect(RestMan::Payload.generate({"foo" => [f]})).to be_kind_of(RestMan::Payload::Multipart)
|
255
|
+
end
|
256
|
+
|
257
|
+
it "should recognize file payloads that can be streamed" do
|
258
|
+
f = File.new(test_image_path)
|
259
|
+
expect(RestMan::Payload.generate(f)).to be_kind_of(RestMan::Payload::Streamed)
|
260
|
+
end
|
261
|
+
|
262
|
+
it "should recognize other payloads that can be streamed" do
|
263
|
+
expect(RestMan::Payload.generate(StringIO.new('foo'))).to be_kind_of(RestMan::Payload::Streamed)
|
264
|
+
end
|
265
|
+
|
266
|
+
# hashery gem introduces Hash#read convenience method. Existence of #read method used to determine of content is streameable :/
|
267
|
+
it "shouldn't treat hashes as streameable" do
|
268
|
+
expect(RestMan::Payload.generate({"foo" => 'bar'})).to be_kind_of(RestMan::Payload::UrlEncoded)
|
269
|
+
end
|
270
|
+
|
271
|
+
it "should recognize multipart payload wrapped in ParamsArray" do
|
272
|
+
f = File.new(test_image_path)
|
273
|
+
params = RestMan::ParamsArray.new([[:image, f]])
|
274
|
+
expect(RestMan::Payload.generate(params)).to be_kind_of(RestMan::Payload::Multipart)
|
275
|
+
end
|
276
|
+
|
277
|
+
it "should handle non-multipart payload wrapped in ParamsArray" do
|
278
|
+
params = RestMan::ParamsArray.new([[:arg, 'value1'], [:arg, 'value2']])
|
279
|
+
expect(RestMan::Payload.generate(params)).to be_kind_of(RestMan::Payload::UrlEncoded)
|
280
|
+
end
|
281
|
+
|
282
|
+
it "should pass through Payload::Base and subclasses unchanged" do
|
283
|
+
payloads = [
|
284
|
+
RestMan::Payload::Base.new('foobar'),
|
285
|
+
RestMan::Payload::UrlEncoded.new({:foo => 'bar'}),
|
286
|
+
RestMan::Payload::Streamed.new(File.new(test_image_path)),
|
287
|
+
RestMan::Payload::Multipart.new({myfile: File.new(test_image_path)}),
|
288
|
+
]
|
289
|
+
|
290
|
+
payloads.each do |payload|
|
291
|
+
expect(RestMan::Payload.generate(payload)).to equal(payload)
|
292
|
+
end
|
293
|
+
end
|
294
|
+
end
|
295
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
require_relative '_lib'
|
2
|
+
|
3
|
+
describe RestMan::RawResponse do
|
4
|
+
before do
|
5
|
+
@tf = double("Tempfile", :read => "the answer is 42", :open => true, :rewind => true)
|
6
|
+
@net_http_res = double('net http response')
|
7
|
+
@request = double('restman request', :redirection_history => nil)
|
8
|
+
@response = RestMan::RawResponse.new(@tf, @net_http_res, @request)
|
9
|
+
end
|
10
|
+
|
11
|
+
it "behaves like string" do
|
12
|
+
expect(@response.to_s).to eq 'the answer is 42'
|
13
|
+
end
|
14
|
+
|
15
|
+
it "exposes a Tempfile" do
|
16
|
+
expect(@response.file).to eq @tf
|
17
|
+
end
|
18
|
+
|
19
|
+
it "includes AbstractResponse" do
|
20
|
+
expect(RestMan::RawResponse.ancestors).to include(RestMan::AbstractResponse)
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,54 @@
|
|
1
|
+
require_relative '_lib'
|
2
|
+
|
3
|
+
describe RestMan::Request, :include_helpers do
|
4
|
+
|
5
|
+
context 'params for GET requests' do
|
6
|
+
it "manage params for get requests" do
|
7
|
+
stub_request(:get, 'http://some/resource?a=b&c=d').with(:headers => {'Accept'=>'*/*', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
8
|
+
expect(RestMan::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => {:a => :b, 'c' => 'd'}}).body).to eq 'foo'
|
9
|
+
|
10
|
+
stub_request(:get, 'http://some/resource').with(:headers => {'Accept'=>'*/*', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
11
|
+
expect(RestMan::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => :a}).body).to eq 'foo'
|
12
|
+
end
|
13
|
+
|
14
|
+
it 'adds GET params when params are present in URL' do
|
15
|
+
stub_request(:get, 'http://some/resource?a=b&c=d').with(:headers => {'Accept'=>'*/*', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
16
|
+
expect(RestMan::Request.execute(:url => 'http://some/resource?a=b', :method => :get, :headers => {:foo => :bar, :params => {:c => 'd'}}).body).to eq 'foo'
|
17
|
+
end
|
18
|
+
|
19
|
+
it 'encodes nested GET params' do
|
20
|
+
stub_request(:get, 'http://some/resource?a[foo][]=1&a[foo][]=2&a[bar]&b=foo+bar&math=2+%2B+2+%3D%3D+4').with(:headers => {'Accept'=>'*/*',}).to_return(:body => 'foo', :status => 200)
|
21
|
+
expect(RestMan::Request.execute(url: 'http://some/resource', method: :get, headers: {
|
22
|
+
params: {
|
23
|
+
a: {
|
24
|
+
foo: [1,2],
|
25
|
+
bar: nil,
|
26
|
+
},
|
27
|
+
b: 'foo bar',
|
28
|
+
math: '2 + 2 == 4',
|
29
|
+
}
|
30
|
+
}).body).to eq 'foo'
|
31
|
+
end
|
32
|
+
|
33
|
+
end
|
34
|
+
|
35
|
+
it "can use a block to process response" do
|
36
|
+
response_value = nil
|
37
|
+
block = proc do |http_response|
|
38
|
+
response_value = http_response.body
|
39
|
+
end
|
40
|
+
stub_request(:get, 'http://some/resource?a=b&c=d').with(:headers => {'Accept'=>'*/*', 'Foo'=>'bar'}).to_return(:body => 'foo', :status => 200)
|
41
|
+
RestMan::Request.execute(:url => 'http://some/resource', :method => :get, :headers => {:foo => :bar, :params => {:a => :b, 'c' => 'd'}}, :block_response => block)
|
42
|
+
expect(response_value).to eq "foo"
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'closes payload if not nil' do
|
46
|
+
test_file = File.new(test_image_path)
|
47
|
+
|
48
|
+
stub_request(:post, 'http://some/resource').with(:headers => {'Accept'=>'*/*'}).to_return(:body => 'foo', :status => 200)
|
49
|
+
RestMan::Request.execute(:url => 'http://some/resource', :method => :post, :payload => {:file => test_file})
|
50
|
+
|
51
|
+
expect(test_file.closed?).to be true
|
52
|
+
end
|
53
|
+
|
54
|
+
end
|