rest-core 3.2.0 → 3.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.
Files changed (54) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGES.md +23 -0
  3. data/Gemfile +1 -1
  4. data/README.md +11 -10
  5. data/Rakefile +2 -1
  6. data/lib/rest-core.rb +0 -1
  7. data/lib/rest-core/builder.rb +59 -12
  8. data/lib/rest-core/client/universal.rb +11 -10
  9. data/lib/rest-core/middleware.rb +20 -0
  10. data/lib/rest-core/middleware/cache.rb +12 -10
  11. data/lib/rest-core/middleware/default_headers.rb +2 -2
  12. data/lib/rest-core/middleware/default_payload.rb +2 -26
  13. data/lib/rest-core/middleware/default_query.rb +2 -10
  14. data/lib/rest-core/middleware/json_request.rb +2 -1
  15. data/lib/rest-core/middleware/json_response.rb +5 -2
  16. data/lib/rest-core/test.rb +3 -12
  17. data/lib/rest-core/version.rb +1 -1
  18. data/rest-core.gemspec +11 -12
  19. data/task/gemgem.rb +1 -5
  20. data/test/test_auth_basic.rb +4 -4
  21. data/test/test_builder.rb +20 -4
  22. data/test/test_cache.rb +19 -20
  23. data/test/test_clash.rb +1 -1
  24. data/test/test_clash_response.rb +11 -11
  25. data/test/test_client.rb +10 -10
  26. data/test/test_client_oauth1.rb +3 -3
  27. data/test/test_config.rb +1 -1
  28. data/test/test_default_headers.rb +13 -0
  29. data/test/test_default_payload.rb +11 -3
  30. data/test/test_default_query.rb +12 -4
  31. data/test/test_error_detector.rb +1 -1
  32. data/test/test_error_detector_http.rb +1 -1
  33. data/test/test_error_handler.rb +5 -5
  34. data/test/test_event_source.rb +16 -16
  35. data/test/test_follow_redirect.rb +6 -6
  36. data/test/test_future.rb +2 -2
  37. data/test/test_json_request.rb +9 -4
  38. data/test/test_json_response.rb +9 -9
  39. data/test/test_oauth1_header.rb +9 -9
  40. data/test/test_oauth2_header.rb +3 -3
  41. data/test/test_parse_link.rb +4 -4
  42. data/test/test_payload.rb +21 -21
  43. data/test/test_promise.rb +7 -7
  44. data/test/test_query_response.rb +5 -5
  45. data/test/test_rest-client.rb +7 -6
  46. data/test/test_simple.rb +5 -5
  47. data/test/test_smash.rb +1 -1
  48. data/test/test_smash_response.rb +11 -11
  49. data/test/test_thread_pool.rb +1 -1
  50. data/test/test_timeout.rb +3 -3
  51. data/test/test_universal.rb +12 -2
  52. metadata +9 -10
  53. data/lib/rest-core/wrapper.rb +0 -72
  54. data/test/test_wrapper.rb +0 -36
data/test/test_payload.rb CHANGED
@@ -3,31 +3,31 @@ require 'rest-core/test'
3
3
 
4
4
  describe RC::Payload do
5
5
  describe 'A regular Payload' do
6
- should 'use standard enctype as default content-type' do
6
+ would 'use standard enctype as default content-type' do
7
7
  RC::Payload::UrlEncoded.new({}).headers['Content-Type'].
8
8
  should.eq 'application/x-www-form-urlencoded'
9
9
  end
10
10
 
11
- should 'form properly encoded params' do
11
+ would 'form properly encoded params' do
12
12
  RC::Payload::UrlEncoded.new(:foo => 'bar').read.
13
13
  should.eq 'foo=bar'
14
14
  RC::Payload::UrlEncoded.new(:foo => 'bar', :baz => 'qux').read.
15
15
  should.eq 'baz=qux&foo=bar'
16
16
  end
17
17
 
18
- should 'escape parameters' do
18
+ would 'escape parameters' do
19
19
  RC::Payload::UrlEncoded.new('foo ' => 'bar').read.
20
20
  should.eq 'foo%20=bar'
21
21
  end
22
22
 
23
- should 'properly handle arrays as repeated parameters' do
23
+ would 'properly handle arrays as repeated parameters' do
24
24
  RC::Payload::UrlEncoded.new(:foo => ['bar']).read.
25
25
  should.eq 'foo=bar'
26
26
  RC::Payload::UrlEncoded.new(:foo => ['bar', 'baz']).read.
27
27
  should.eq 'foo=bar&foo=baz'
28
28
  end
29
29
 
30
- should 'not close if stream already closed' do
30
+ would 'not close if stream already closed' do
31
31
  p = RC::Payload::UrlEncoded.new('foo ' => 'bar')
32
32
  p.close
33
33
  2.times{ p.close.should.eq nil }
@@ -35,19 +35,19 @@ describe RC::Payload do
35
35
  end
36
36
 
37
37
  describe 'A multipart Payload' do
38
- should 'use standard enctype as default content-type' do
38
+ would 'use standard enctype as default content-type' do
39
39
  p = RC::Payload::Multipart.new({})
40
40
  stub(p).boundary{123}
41
41
  p.headers['Content-Type'].should.eq 'multipart/form-data; boundary=123'
42
42
  end
43
43
 
44
- should 'not error on close if stream already closed' do
44
+ would 'not error on close if stream already closed' do
45
45
  p = RC::Payload::Multipart.new(:file => File.open(__FILE__))
46
46
  p.close
47
47
  2.times{ p.close.should.eq nil }
48
48
  end
49
49
 
50
- should 'form properly separated multipart data' do
50
+ would 'form properly separated multipart data' do
51
51
  p = RC::Payload::Multipart.new(:bar => 'baz', :foo => 'bar')
52
52
  p.read.should.eq <<-EOS
53
53
  --#{p.boundary}\r
@@ -62,7 +62,7 @@ bar\r
62
62
  EOS
63
63
  end
64
64
 
65
- should 'form multiple files with the same name' do
65
+ would 'form multiple files with the same name' do
66
66
  with_img do |f, n|
67
67
  with_img do |ff, nn|
68
68
  p = RC::Payload::Multipart.new(:foo => [f, ff])
@@ -83,7 +83,7 @@ Content-Type: image/jpeg\r
83
83
  end
84
84
  end
85
85
 
86
- should 'not escape parameters names' do
86
+ would 'not escape parameters names' do
87
87
  p = RC::Payload::Multipart.new('bar ' => 'baz')
88
88
  p.read.should.eq <<-EOS
89
89
  --#{p.boundary}\r
@@ -94,7 +94,7 @@ baz\r
94
94
  EOS
95
95
  end
96
96
 
97
- should 'form properly separated multipart data' do
97
+ would 'form properly separated multipart data' do
98
98
  with_img do |f, n|
99
99
  p = RC::Payload::Multipart.new(:foo => f)
100
100
  p.read.should.eq <<-EOS
@@ -108,7 +108,7 @@ Content-Type: image/jpeg\r
108
108
  end
109
109
  end
110
110
 
111
- should "ignore the name attribute when it's not set" do
111
+ would "ignore the name attribute when it's not set" do
112
112
  with_img do |f, n|
113
113
  p = RC::Payload::Multipart.new(nil => f)
114
114
  p.read.should.eq <<-EOS
@@ -122,7 +122,7 @@ Content-Type: image/jpeg\r
122
122
  end
123
123
  end
124
124
 
125
- should 'detect optional (original) content type and filename' do
125
+ would 'detect optional (original) content type and filename' do
126
126
  File.open(__FILE__) do |f|
127
127
  def f.content_type ; 'image/jpeg'; end
128
128
  def f.original_filename; 'foo.txt' ; end
@@ -140,14 +140,14 @@ Content-Type: image/jpeg\r
140
140
  end
141
141
 
142
142
  describe 'streamed payloads' do
143
- should 'properly determine the size of file payloads' do
143
+ would 'properly determine the size of file payloads' do
144
144
  File.open(__FILE__) do |f|
145
145
  p = RC::Payload.generate(f)
146
146
  p.size.should.eq f.stat.size
147
147
  end
148
148
  end
149
149
 
150
- should 'properly determine the size of other kinds of payloads' do
150
+ would 'properly determine the size of other kinds of payloads' do
151
151
  s = StringIO.new('foo')
152
152
  p = RC::Payload.generate(s)
153
153
  p.size.should.eq 3
@@ -166,37 +166,37 @@ Content-Type: image/jpeg\r
166
166
  end
167
167
 
168
168
  describe 'Payload generation' do
169
- should 'recognize standard urlencoded params' do
169
+ would 'recognize standard urlencoded params' do
170
170
  RC::Payload.generate('foo' => 'bar').should.
171
171
  kind_of?(RC::Payload::UrlEncoded)
172
172
  end
173
173
 
174
- should 'recognize multipart params' do
174
+ would 'recognize multipart params' do
175
175
  File.open(__FILE__) do |f|
176
176
  RC::Payload.generate('foo' => f).should.
177
177
  kind_of?(RC::Payload::Multipart)
178
178
  end
179
179
  end
180
180
 
181
- should 'return data if none of the above' do
181
+ would 'return data if none of the above' do
182
182
  RC::Payload.generate('data').should.
183
183
  kind_of?(RC::Payload::StreamedString)
184
184
  end
185
185
 
186
- should 'recognize nested multipart payloads in arrays' do
186
+ would 'recognize nested multipart payloads in arrays' do
187
187
  File.open(__FILE__) do |f|
188
188
  RC::Payload.generate('foo' => [f]).should.
189
189
  kind_of?(RC::Payload::Multipart)
190
190
  end
191
191
  end
192
192
 
193
- should 'recognize file payloads that can be streamed' do
193
+ would 'recognize file payloads that can be streamed' do
194
194
  File.open(__FILE__) do |f|
195
195
  RC::Payload.generate(f).should.kind_of?(RC::Payload::Streamed)
196
196
  end
197
197
  end
198
198
 
199
- should 'recognize other payloads that can be streamed' do
199
+ would 'recognize other payloads that can be streamed' do
200
200
  RC::Payload.generate(StringIO.new('foo')).should.
201
201
  kind_of?(RC::Payload::Streamed)
202
202
  end
data/test/test_promise.rb CHANGED
@@ -17,7 +17,7 @@ describe RC::Promise do
17
17
  Muack.verify
18
18
  end
19
19
 
20
- should 'work, reject, yield' do
20
+ would 'work, reject, yield' do
21
21
  @client.pool_size = 1
22
22
  flag = 0
23
23
  @promise.defer do
@@ -27,10 +27,10 @@ describe RC::Promise do
27
27
  end
28
28
  @promise.yield
29
29
  flag.should.eq 1
30
- @promise.send(:error).should.kind_of RC::Error
30
+ @promise.send(:error).should.kind_of? RC::Error
31
31
  end
32
32
 
33
- should 'work, fulfill, yield' do
33
+ would 'work, fulfill, yield' do
34
34
  @client.pool_size = 2
35
35
  flag = 0
36
36
  @promise.defer do
@@ -45,7 +45,7 @@ describe RC::Promise do
45
45
  @promise.send(:headers).should.eq('K' => 'V')
46
46
  end
47
47
 
48
- should 'then then then' do
48
+ would 'then then then' do
49
49
  plusone = lambda do |r|
50
50
  r.merge(RC::RESPONSE_BODY => r[RC::RESPONSE_BODY] + 1)
51
51
  end
@@ -54,7 +54,7 @@ describe RC::Promise do
54
54
  @promise.future_body.should.eq 6
55
55
  end
56
56
 
57
- should 'call inline if pool_size < 0' do
57
+ would 'call inline if pool_size < 0' do
58
58
  @client.pool_size = -1
59
59
  current_thread = Thread.current
60
60
  @promise.defer do
@@ -62,7 +62,7 @@ describe RC::Promise do
62
62
  end
63
63
  end
64
64
 
65
- should 'call in a new thread if pool_size == 0' do
65
+ would 'call in a new thread if pool_size == 0' do
66
66
  @client.pool_size = 0
67
67
  thread = nil
68
68
  mock(Thread).new.with_any_args.peek_return do |t|
@@ -75,7 +75,7 @@ describe RC::Promise do
75
75
  @promise.yield
76
76
  end
77
77
 
78
- should 'call in thread pool if pool_size > 0' do
78
+ would 'call in thread pool if pool_size > 0' do
79
79
  @client.pool_size = 1
80
80
  flag = 0
81
81
  rd, wr = IO.pipe
@@ -8,15 +8,15 @@ describe RC::QueryResponse do
8
8
  RC::REQUEST_HEADERS =>
9
9
  {'Accept' => 'application/x-www-form-urlencoded'}}
10
10
 
11
- should 'give {} for nil' do
11
+ would 'give {} for nil' do
12
12
  app.call({}){ |response| response.should.eq(expected) }
13
13
  end
14
14
 
15
- should 'give {} for ""' do
15
+ would 'give {} for ""' do
16
16
  app.call(RC::RESPONSE_BODY => ''){ |r| r.should.eq(expected) }
17
17
  end
18
18
 
19
- should 'give {"a" => "b"} for "a=b"' do
19
+ would 'give {"a" => "b"} for "a=b"' do
20
20
  e = expected.merge(RC::RESPONSE_BODY => {'a' => 'b'})
21
21
  app.call(RC::RESPONSE_BODY => 'a=b'){ |r| r.should.eq(e) }
22
22
  end
@@ -32,14 +32,14 @@ describe RC::QueryResponse do
32
32
  }
33
33
  end
34
34
 
35
- should 'do nothing' do
35
+ would 'do nothing' do
36
36
  expected = 'a=b&c=d'
37
37
  client.new(:query_response => false).get(''){ |response|
38
38
  response.should.eq(expected)
39
39
  }.get('').should.eq(expected)
40
40
  end
41
41
 
42
- should 'parse' do
42
+ would 'parse' do
43
43
  expected = {'a' => 'b', 'c' => 'd'}
44
44
  client.new.get(''){ |response|
45
45
  response.should.eq(expected)
@@ -14,15 +14,16 @@ describe RC::RestClient do
14
14
  c = client.new
15
15
 
16
16
  post = lambda do |payload, body|
17
- stub_request(:post, path).with(:body => body).to_return(:body => ok)
17
+ WebMock::API.stub_request(:post, path).
18
+ with(:body => body).to_return(:body => ok)
18
19
  c.post(path, payload).should.eq ok
19
20
  end
20
21
 
21
- should 'post with string' do
22
+ would 'post with string' do
22
23
  post['string', 'string']
23
24
  end
24
25
 
25
- should 'post with file' do
26
+ would 'post with file' do
26
27
  File.open(__FILE__) do |f|
27
28
  b = f.read
28
29
  f.rewind
@@ -30,20 +31,20 @@ describe RC::RestClient do
30
31
  end
31
32
  end
32
33
 
33
- should 'post with socket' do
34
+ would 'post with socket' do
34
35
  rd, wr = IO.pipe
35
36
  wr.write('socket')
36
37
  wr.close
37
38
  post[rd, 'socket']
38
39
  end
39
40
 
40
- should 'not kill the thread if error was coming from the task' do
41
+ would 'not kill the thread if error was coming from the task' do
41
42
  mock(RestClient::Request).execute{ raise 'boom' }.with_any_args
42
43
  c.request(RC::RESPONSE_KEY => RC::FAIL).first.message.should.eq 'boom'
43
44
  Muack.verify
44
45
  end
45
46
 
46
- should 'cancel the task if timing out' do
47
+ would 'cancel the task if timing out' do
47
48
  timer = Object.new.instance_eval do
48
49
  def on_timeout; yield ; end
49
50
  def error ; 'boom'; end
data/test/test_simple.rb CHANGED
@@ -8,28 +8,28 @@ describe RC::Simple do
8
8
  WebMock.reset!
9
9
  end
10
10
 
11
- should 'give RESPONSE_BODY' do
11
+ would 'give RESPONSE_BODY' do
12
12
  stub_request(:get, path).to_return(:body => 'OK')
13
13
  RC::Simple.new.get(path).should.eq 'OK'
14
14
  end
15
15
 
16
- should 'give RESPONSE_HEADERS' do
16
+ would 'give RESPONSE_HEADERS' do
17
17
  stub_request(:head, path).to_return(:headers => {'A' => 'B'})
18
18
  RC::Simple.new.head(path).should.eq 'A' => 'B'
19
19
  end
20
20
 
21
- should 'give RESPONSE_HEADERS' do
21
+ would 'give RESPONSE_HEADERS' do
22
22
  stub_request(:get, path).to_return(:status => 199)
23
23
  RC::Simple.new.get(path, {},
24
24
  RC::RESPONSE_KEY => RC::RESPONSE_STATUS).should.eq 199
25
25
  end
26
26
 
27
- should 'give RESPONSE_SOCKET' do
27
+ would 'give RESPONSE_SOCKET' do
28
28
  stub_request(:get, path).to_return(:body => 'OK')
29
29
  RC::Simple.new.get(path, {}, RC::HIJACK => true).read.should.eq 'OK'
30
30
  end
31
31
 
32
- should 'give REQUEST_URI' do
32
+ would 'give REQUEST_URI' do
33
33
  stub_request(:get, "#{path}?a=b").to_return(:body => 'OK')
34
34
  RC::Simple.new.get(path, {:a => 'b'},
35
35
  RC::RESPONSE_KEY => RC::REQUEST_URI).should.eq "#{path}?a=b"
data/test/test_smash.rb CHANGED
@@ -2,7 +2,7 @@
2
2
  require 'rest-core/test'
3
3
 
4
4
  describe RC::Smash do
5
- should 'deep access' do
5
+ would 'deep access' do
6
6
  h = {0 => 1, 2 => {3 => 4, 5 => [6, {7 => 8}]}, 9 => false, 10 => nil}
7
7
  c = RC::Smash.new(h)
8
8
  c[0] .should.eq(1)
@@ -5,19 +5,19 @@ describe RC::SmashResponse do
5
5
  describe 'app' do
6
6
  app = RC::SmashResponse.new(RC::Dry.new, true)
7
7
 
8
- should 'do nothing' do
8
+ would 'do nothing' do
9
9
  env = {RC::RESPONSE_BODY => []}
10
10
  app.call(env) do |res|
11
11
  res.should.eq(env)
12
- res[RC::RESPONSE_BODY].should.kind_of(Array)
12
+ res[RC::RESPONSE_BODY].should.kind_of?(Array)
13
13
  end
14
14
  end
15
15
 
16
- should 'smash' do
16
+ would 'smash' do
17
17
  app.call(RC::RESPONSE_BODY => {}) do |res|
18
18
  body = res[RC::RESPONSE_BODY]
19
- body.should.kind_of(RC::Smash)
20
- body.should.empty
19
+ body.should.kind_of?(RC::Smash)
20
+ body.should.empty?
21
21
  body[0].should.eq(nil)
22
22
  body[0, 0].should.eq(nil)
23
23
  end
@@ -34,22 +34,22 @@ describe RC::SmashResponse do
34
34
  }
35
35
  end
36
36
 
37
- should 'do nothing' do
37
+ would 'do nothing' do
38
38
  b = client.new(:smash_response => false).get(''){ |res|
39
39
  res.should.eq(body)
40
- res.should.kind_of(Hash)
40
+ res.should.kind_of?(Hash)
41
41
  }.get('')
42
42
  b.should.eq(body)
43
- b.should.kind_of(Hash)
43
+ b.should.kind_of?(Hash)
44
44
  end
45
45
 
46
- should 'clash' do
46
+ would 'clash' do
47
47
  b = client.new.get(''){ |res|
48
48
  res.should.eq(body)
49
- res.should.kind_of(RC::Smash)
49
+ res.should.kind_of?(RC::Smash)
50
50
  }.get('')
51
51
  b.should.eq(body)
52
- b.should.kind_of(RC::Smash)
52
+ b.should.kind_of?(RC::Smash)
53
53
  end
54
54
  end
55
55
  end
@@ -2,7 +2,7 @@
2
2
  require 'rest-core/test'
3
3
 
4
4
  describe RC::ThreadPool do
5
- should 'have the same pool for the same client' do
5
+ would 'have the same pool for the same client' do
6
6
  client = RC::Builder.client
7
7
  pool = RC::ThreadPool[client]
8
8
  RC::ThreadPool[client].object_id.should.eq pool.object_id
data/test/test_timeout.rb CHANGED
@@ -9,18 +9,18 @@ describe RC::Timeout do
9
9
  Muack.verify
10
10
  end
11
11
 
12
- should 'bypass timeout if timeout is 0' do
12
+ would 'bypass timeout if timeout is 0' do
13
13
  mock(app).monitor.times(0)
14
14
  app.call({}){ |e| e.should.eq({}) }
15
15
  end
16
16
 
17
- should 'run the monitor to setup timeout' do
17
+ would 'run the monitor to setup timeout' do
18
18
  env = {'timeout' => 2}
19
19
  mock(app).monitor(env)
20
20
  app.call(env){|e| e[RC::TIMER].should.kind_of?(RC::Timer)}
21
21
  end
22
22
 
23
- should "not raise timeout error if there's already an error" do
23
+ would "not raise timeout error if there's already an error" do
24
24
  env = {'timeout' => 0.01}
25
25
  mock(app.app).call(hash_including(env)){ raise "error" }
26
26
  lambda{ app.call(env){} }.should .raise(RuntimeError)
@@ -2,7 +2,7 @@
2
2
  require 'rest-core/test'
3
3
 
4
4
  describe RC::Universal do
5
- should 'send Authorization header' do
5
+ would 'send Authorization header' do
6
6
  u = RC::Universal.new(:log_method => false)
7
7
  u.username = 'Aladdin'
8
8
  u.password = 'open sesame'
@@ -17,7 +17,7 @@ describe RC::Universal do
17
17
  {'Authorization' => 'Basic QWxhZGRpbjpvcGVuIHNlc2FtZQ=='}.merge(acc))
18
18
  end
19
19
 
20
- should 'clash' do
20
+ would 'clash' do
21
21
  url = 'http://localhost/'
22
22
  stub_request(:get, url).to_return(:body => '{"a":{"b":"c"}}')
23
23
  res = RC::Universal.new(:json_response => true,
@@ -25,4 +25,14 @@ describe RC::Universal do
25
25
  :log_method => false).get(url)
26
26
  res['a']['d'].should.eq({})
27
27
  end
28
+
29
+ would 'follow redirect regardless response body' do
30
+ url = 'http://localhost/'
31
+ stub_request(:get, url).to_return(:body => 'bad json!',
32
+ :status => 302, :headers => {'Location' => "#{url}a"})
33
+ stub_request(:get, "#{url}a").to_return(:body => '{"good":"json!"}')
34
+ RC::Universal.new(:json_response => true,
35
+ :log_method => false).
36
+ get(url).should.eq 'good' => 'json!'
37
+ end
28
38
  end