waiter_ 0.0.1 → 1.0.2
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 +4 -4
- data/README.md +11 -11
- data/lib/timeout_error.rb +4 -0
- data/lib/version.rb +1 -1
- data/lib/waiter.rb +90 -44
- data/waiter.gemspec +2 -0
- metadata +18 -3
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 6e268b47f92c2f681a1574ce1fe621c31a391fed
|
4
|
+
data.tar.gz: e5361387d097b61bd4a7cb16690c3e56c69579b5
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: a3a8c53b6dc3e0173a4d839eed61ae4ff286c23fe9556a0a5e3737d087fcb14c58dc4c9b9604eff16e5da52159aac0b4147efcbe5bebd53b40a5ce6c021a814f
|
7
|
+
data.tar.gz: 01dde6fe0567b1af0abb61c6caaec4bfac818715ca7ddd69929b22bbb734b98a8c73736c4b333451f2ff259a4ae16b5f02ce6a0296945e28cb04f926f2ea13bd
|
data/README.md
CHANGED
@@ -7,7 +7,7 @@ A simple wait/polling gem.
|
|
7
7
|
Add this line to your application's Gemfile:
|
8
8
|
|
9
9
|
```ruby
|
10
|
-
gem '
|
10
|
+
gem 'waiter_'
|
11
11
|
```
|
12
12
|
|
13
13
|
And then execute:
|
@@ -19,29 +19,30 @@ And then execute:
|
|
19
19
|
Just `include Waiter` and the following APIs will be available.
|
20
20
|
|
21
21
|
```ruby
|
22
|
-
wait('foo').to eq 'foo' # Will pass.
|
23
|
-
wait('foo').to eq 'bar' # Will throw exception.
|
24
|
-
wait('foo').to_not eq 'bar' # Will pass.
|
25
|
-
wait('foo').to_not eq 'foo' # Will fail.
|
22
|
+
wait.for('foo').to eq 'foo' # Will pass.
|
23
|
+
wait.for('foo').to eq 'bar' # Will throw exception.
|
24
|
+
wait.for('foo').to_not eq 'bar' # Will pass.
|
25
|
+
wait.for('foo').to_not eq 'foo' # Will fail.
|
26
26
|
```
|
27
27
|
|
28
28
|
To adjust the timeout/polling, simple chain methods are supported.
|
29
29
|
|
30
|
-
The *
|
30
|
+
The *up_to* method accepts an Integer and adjusts the timeout.
|
31
|
+
Use the *every* method with an Integer to adjust the polling time.
|
31
32
|
|
32
33
|
```ruby
|
33
34
|
# Wait for 30 seconds, polling every 2 second.
|
34
|
-
wait
|
35
|
+
wait.every(2).up_to(30).for('foo').to eq 'foo'
|
35
36
|
```
|
36
37
|
|
37
38
|
You do *not* have to use both methods, you can adjust one or the other. They can also be used in any order.
|
38
39
|
|
39
40
|
```ruby
|
40
41
|
# Wait for 30 seconds, using the default 1 second poll.
|
41
|
-
wait('foo').
|
42
|
+
wait.for('foo').up_to(30).to eq 'foo'
|
42
43
|
|
43
44
|
# Wait for the default 15 seconds, polling every 5 seconds.
|
44
|
-
wait('foo').every(5).to eq 'foo'
|
45
|
+
wait.for('foo').every(5).to eq 'foo'
|
45
46
|
```
|
46
47
|
|
47
48
|
You can also pass a block to be evaluated, using *until*, until it is true.
|
@@ -49,8 +50,7 @@ You can also pass a block to be evaluated, using *until*, until it is true.
|
|
49
50
|
```ruby
|
50
51
|
wait.until { true == true }
|
51
52
|
|
52
|
-
wait.every(5).
|
53
|
+
wait.every(5).up_to(30).until {
|
53
54
|
true == true
|
54
55
|
}
|
55
56
|
```
|
56
|
-
|
data/lib/version.rb
CHANGED
data/lib/waiter.rb
CHANGED
@@ -1,5 +1,7 @@
|
|
1
1
|
require 'rspec/expectations'
|
2
2
|
|
3
|
+
require_relative 'timeout_error'
|
4
|
+
|
3
5
|
module Waiter
|
4
6
|
# Wrapper for RSpec expectations that allows waiting/polling.
|
5
7
|
#
|
@@ -7,20 +9,20 @@ module Waiter
|
|
7
9
|
#
|
8
10
|
# @example
|
9
11
|
#
|
10
|
-
# wait('foo').to eq 'foo' # Will pass.
|
11
|
-
# wait('foo').to eq 'bar' # Will throw exception.
|
12
|
-
# wait('foo').to_not eq 'bar' # Will pass.
|
13
|
-
# wait('foo').to_not eq 'foo' # Will fail.
|
12
|
+
# wait.for('foo').to eq 'foo' # Will pass.
|
13
|
+
# wait.for('foo').to eq 'bar' # Will throw exception.
|
14
|
+
# wait.for('foo').to_not eq 'bar' # Will pass.
|
15
|
+
# wait.for('foo').to_not eq 'foo' # Will fail.
|
14
16
|
#
|
15
17
|
# To adjust the timeout/polling, simple chain methods are supported.
|
16
18
|
#
|
17
|
-
# The *
|
19
|
+
# The *up_to* method accepts an Integer and adjusts the timeout.
|
18
20
|
# Use the *every* method with an Integer to adjust the polling time.
|
19
21
|
#
|
20
22
|
# @example
|
21
23
|
#
|
22
24
|
# # Wait for 30 seconds, polling every 2 second.
|
23
|
-
# wait
|
25
|
+
# wait.every(2).up_to(30).for('foo').to eq 'foo'
|
24
26
|
#
|
25
27
|
# You do *not* have to use both methods, you can adjust one or the other.
|
26
28
|
# They can also be used in any order.
|
@@ -28,10 +30,10 @@ module Waiter
|
|
28
30
|
# @example
|
29
31
|
#
|
30
32
|
# # Wait for 30 seconds, using the default 1 second poll.
|
31
|
-
# wait('foo').
|
33
|
+
# wait.for('foo').up_to(30).to eq 'foo'
|
32
34
|
#
|
33
35
|
# # Wait for the default 15 seconds, polling every 5 seconds.
|
34
|
-
# wait('foo').every(5).to eq 'foo'
|
36
|
+
# wait.for('foo').every(5).to eq 'foo'
|
35
37
|
#
|
36
38
|
# You can also pass a block to be evaluated, using *until*, until it is true.
|
37
39
|
#
|
@@ -39,40 +41,72 @@ module Waiter
|
|
39
41
|
#
|
40
42
|
# wait.until { true == true }
|
41
43
|
#
|
42
|
-
# wait.every(5).
|
44
|
+
# wait.every(5).up_to(30).until {
|
43
45
|
# true == true
|
44
46
|
# }
|
45
47
|
#
|
46
48
|
# @author Derek McNeil <dmcneil@pindrop.com>
|
47
|
-
def wait(
|
48
|
-
|
49
|
+
def wait(opts = {}, &block)
|
50
|
+
ChainableWait.new(opts)
|
49
51
|
end
|
50
52
|
|
51
|
-
|
52
|
-
|
53
|
-
class WaitExpectationTarget < RSpec::Expectations::ExpectationTarget
|
53
|
+
class ChainableWait
|
54
54
|
attr_reader :target
|
55
55
|
attr_accessor :timeout, :polling, :message
|
56
56
|
|
57
57
|
DEFAULT_TIMEOUT = 15
|
58
58
|
DEFAULT_POLLING = 1
|
59
59
|
|
60
|
-
def initialize(
|
61
|
-
@
|
62
|
-
@
|
63
|
-
@
|
60
|
+
def initialize(opts = {})
|
61
|
+
@timeout = opts[:timeout] || DEFAULT_TIMEOUT
|
62
|
+
@polling = opts[:polling] || DEFAULT_POLLING
|
63
|
+
@failure_message = opts[:failure_message] || build_error
|
64
|
+
end
|
65
|
+
|
66
|
+
def for(value = nil, &block)
|
67
|
+
if value
|
68
|
+
@target = value
|
69
|
+
elsif block_given?
|
70
|
+
@target = block
|
71
|
+
end
|
72
|
+
|
73
|
+
self
|
74
|
+
end
|
75
|
+
|
76
|
+
def up_to(seconds)
|
77
|
+
@timeout = seconds
|
78
|
+
self
|
79
|
+
end
|
80
|
+
|
81
|
+
def every(seconds)
|
82
|
+
@polling = seconds
|
83
|
+
self
|
84
|
+
end
|
85
|
+
alias_method :polling_every, :every
|
86
|
+
|
87
|
+
def to(matcher = nil, &block)
|
88
|
+
WaitExpectationTarget.new(@target).to(self, matcher, &block)
|
64
89
|
end
|
65
90
|
|
66
|
-
def
|
91
|
+
def not_to(matcher = nil, &block)
|
92
|
+
WaitExpectationTarget.new(@target).not_to(self, matcher, &block)
|
93
|
+
end
|
94
|
+
alias_method :to_not, :not_to
|
95
|
+
|
96
|
+
def until(&block)
|
67
97
|
unless @timeout > @polling
|
68
98
|
raise ArgumentError, 'Timeout must be a higher value than polling.'
|
69
99
|
end
|
70
100
|
|
71
|
-
|
101
|
+
current_timeout = @timeout
|
102
|
+
|
103
|
+
while current_timeout > 0 && current_timeout > @polling
|
104
|
+
trap('SIGINT') { break }
|
72
105
|
|
73
|
-
while @timeout > 0 && @timeout > @polling
|
74
106
|
@result = begin
|
75
107
|
block.call
|
108
|
+
rescue SystemExit, Interrupt
|
109
|
+
break
|
76
110
|
rescue Exception => error
|
77
111
|
@error = error
|
78
112
|
false
|
@@ -80,52 +114,64 @@ module Waiter
|
|
80
114
|
|
81
115
|
break if @result
|
82
116
|
sleep @polling
|
83
|
-
|
117
|
+
current_timeout = current_timeout - @polling
|
84
118
|
end
|
85
119
|
|
86
120
|
unless @result
|
87
121
|
if @error
|
88
|
-
@error.
|
122
|
+
@error = Waiter::TimeoutError.new(build_error(@error))
|
89
123
|
else
|
90
|
-
@error =
|
124
|
+
@error = Waiter::TimeoutError.new(build_error)
|
91
125
|
end
|
92
126
|
|
93
127
|
raise @error
|
94
128
|
end
|
95
129
|
end
|
96
130
|
|
97
|
-
|
98
|
-
|
99
|
-
def every(seconds)
|
100
|
-
@polling = seconds
|
101
|
-
self
|
102
|
-
end
|
131
|
+
private
|
103
132
|
|
104
|
-
def
|
105
|
-
|
106
|
-
|
133
|
+
def build_error(error = nil)
|
134
|
+
[
|
135
|
+
"Timed out after waiting for #{@timeout}s.",
|
136
|
+
"Polled for #{@polling}s.",
|
137
|
+
error
|
138
|
+
].join("\n")
|
107
139
|
end
|
140
|
+
end
|
108
141
|
|
109
|
-
|
142
|
+
class WaitExpectationTarget < RSpec::Expectations::ExpectationTarget
|
143
|
+
def to(waiter, matcher = nil, &block)
|
110
144
|
prevent_operator_matchers(:to) unless matcher
|
111
|
-
|
112
|
-
|
145
|
+
waiter.until do
|
146
|
+
target = handle_target(waiter.target)
|
147
|
+
RSpec::Expectations::PositiveExpectationHandler.handle_matcher(target,
|
148
|
+
matcher,
|
149
|
+
&block)
|
150
|
+
|
151
|
+
return target
|
113
152
|
end
|
114
|
-
@target
|
115
153
|
end
|
116
154
|
|
117
|
-
def not_to(matcher=
|
155
|
+
def not_to(waiter, matcher = nil, &block)
|
118
156
|
prevent_operator_matchers(:not_to) unless matcher
|
119
|
-
|
120
|
-
|
157
|
+
waiter.until do
|
158
|
+
target = handle_target(waiter.target)
|
159
|
+
RSpec::Expectations::NegativeExpectationHandler.handle_matcher(target,
|
160
|
+
matcher,
|
161
|
+
&block)
|
162
|
+
|
163
|
+
return target
|
121
164
|
end
|
122
|
-
@target
|
123
165
|
end
|
124
166
|
|
125
|
-
|
167
|
+
private
|
126
168
|
|
127
|
-
def
|
128
|
-
|
169
|
+
def handle_target(target)
|
170
|
+
if target.respond_to?(:call)
|
171
|
+
target.call
|
172
|
+
else
|
173
|
+
target
|
174
|
+
end
|
129
175
|
end
|
130
176
|
end
|
131
177
|
end
|
data/waiter.gemspec
CHANGED
@@ -15,6 +15,8 @@ Gem::Specification.new do |spec|
|
|
15
15
|
spec.files = `git ls-files -z`.split("\x0").reject { |f| f.match(%r{^(test|spec|features)/}) }
|
16
16
|
spec.require_paths = ['lib']
|
17
17
|
|
18
|
+
spec.add_dependency 'rspec-expectations', '~> 3.5.0'
|
19
|
+
|
18
20
|
spec.add_development_dependency 'bundler', '~> 1.12'
|
19
21
|
spec.add_development_dependency 'rake', '~> 10.0'
|
20
22
|
spec.add_development_dependency 'rspec', '~> 3.0'
|
metadata
CHANGED
@@ -1,15 +1,29 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: waiter_
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
4
|
+
version: 1.0.2
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Derek McNeil
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date:
|
11
|
+
date: 2017-01-18 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
|
+
- !ruby/object:Gem::Dependency
|
14
|
+
name: rspec-expectations
|
15
|
+
requirement: !ruby/object:Gem::Requirement
|
16
|
+
requirements:
|
17
|
+
- - "~>"
|
18
|
+
- !ruby/object:Gem::Version
|
19
|
+
version: 3.5.0
|
20
|
+
type: :runtime
|
21
|
+
prerelease: false
|
22
|
+
version_requirements: !ruby/object:Gem::Requirement
|
23
|
+
requirements:
|
24
|
+
- - "~>"
|
25
|
+
- !ruby/object:Gem::Version
|
26
|
+
version: 3.5.0
|
13
27
|
- !ruby/object:Gem::Dependency
|
14
28
|
name: bundler
|
15
29
|
requirement: !ruby/object:Gem::Requirement
|
@@ -64,6 +78,7 @@ files:
|
|
64
78
|
- Gemfile
|
65
79
|
- README.md
|
66
80
|
- Rakefile
|
81
|
+
- lib/timeout_error.rb
|
67
82
|
- lib/version.rb
|
68
83
|
- lib/waiter.rb
|
69
84
|
- waiter.gemspec
|
@@ -86,7 +101,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
86
101
|
version: '0'
|
87
102
|
requirements: []
|
88
103
|
rubyforge_project:
|
89
|
-
rubygems_version: 2.
|
104
|
+
rubygems_version: 2.5.1
|
90
105
|
signing_key:
|
91
106
|
specification_version: 4
|
92
107
|
summary: A simple polling gem.
|