concurrent-ruby 0.6.1 → 0.7.0.rc0
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 +1 -1
- data/lib/concurrent.rb +3 -4
- data/lib/concurrent/atomic.rb +46 -0
- data/lib/concurrent/atomic_reference/concurrent_update_error.rb +7 -0
- data/lib/concurrent/atomic_reference/delegated_update.rb +28 -0
- data/lib/concurrent/atomic_reference/direct_update.rb +28 -0
- data/lib/concurrent/atomic_reference/jruby.rb +8 -0
- data/lib/concurrent/atomic_reference/mutex_atomic.rb +47 -0
- data/lib/concurrent/atomic_reference/numeric_cas_wrapper.rb +24 -0
- data/lib/concurrent/atomic_reference/rbx.rb +16 -0
- data/lib/concurrent/atomic_reference/ruby.rb +16 -0
- data/lib/concurrent/atomics.rb +1 -1
- data/lib/concurrent/configuration.rb +1 -1
- data/lib/concurrent/supervisor.rb +1 -1
- data/lib/concurrent/timer_task.rb +0 -36
- data/lib/concurrent/version.rb +1 -1
- data/lib/concurrent_ruby_ext.so +0 -0
- data/lib/extension_helper.rb +9 -0
- metadata +16 -148
- data/lib/concurrent/actor/actor.rb +0 -270
- data/lib/concurrent/actor/postable.rb +0 -102
- data/lib/concurrent/actors.rb +0 -2
- data/lib/concurrent/atomic/atomic.rb +0 -48
- data/lib/concurrent/runnable.rb +0 -90
- data/lib/concurrent/stoppable.rb +0 -20
- data/spec/concurrent/actor/actor_spec.rb +0 -376
- data/spec/concurrent/actor/postable_shared.rb +0 -218
- data/spec/concurrent/actress_spec.rb +0 -211
- data/spec/concurrent/agent_spec.rb +0 -500
- data/spec/concurrent/async_spec.rb +0 -352
- data/spec/concurrent/atomic/atomic_boolean_spec.rb +0 -172
- data/spec/concurrent/atomic/atomic_fixnum_spec.rb +0 -186
- data/spec/concurrent/atomic/atomic_spec.rb +0 -133
- data/spec/concurrent/atomic/condition_spec.rb +0 -171
- data/spec/concurrent/atomic/copy_on_notify_observer_set_spec.rb +0 -10
- data/spec/concurrent/atomic/copy_on_write_observer_set_spec.rb +0 -10
- data/spec/concurrent/atomic/count_down_latch_spec.rb +0 -151
- data/spec/concurrent/atomic/cyclic_barrier_spec.rb +0 -248
- data/spec/concurrent/atomic/event_spec.rb +0 -200
- data/spec/concurrent/atomic/observer_set_shared.rb +0 -242
- data/spec/concurrent/atomic/thread_local_var_spec.rb +0 -113
- data/spec/concurrent/channel/buffered_channel_spec.rb +0 -151
- data/spec/concurrent/channel/channel_spec.rb +0 -39
- data/spec/concurrent/channel/probe_spec.rb +0 -77
- data/spec/concurrent/channel/unbuffered_channel_spec.rb +0 -132
- data/spec/concurrent/collection/blocking_ring_buffer_spec.rb +0 -149
- data/spec/concurrent/collection/priority_queue_spec.rb +0 -317
- data/spec/concurrent/collection/ring_buffer_spec.rb +0 -126
- data/spec/concurrent/configuration_spec.rb +0 -69
- data/spec/concurrent/dataflow_spec.rb +0 -242
- data/spec/concurrent/delay_spec.rb +0 -91
- data/spec/concurrent/dereferenceable_shared.rb +0 -146
- data/spec/concurrent/exchanger_spec.rb +0 -66
- data/spec/concurrent/executor/cached_thread_pool_shared.rb +0 -115
- data/spec/concurrent/executor/fixed_thread_pool_shared.rb +0 -136
- data/spec/concurrent/executor/global_thread_pool_shared.rb +0 -35
- data/spec/concurrent/executor/immediate_executor_spec.rb +0 -12
- data/spec/concurrent/executor/java_cached_thread_pool_spec.rb +0 -44
- data/spec/concurrent/executor/java_fixed_thread_pool_spec.rb +0 -64
- data/spec/concurrent/executor/java_single_thread_executor_spec.rb +0 -21
- data/spec/concurrent/executor/java_thread_pool_executor_spec.rb +0 -71
- data/spec/concurrent/executor/per_thread_executor_spec.rb +0 -57
- data/spec/concurrent/executor/ruby_cached_thread_pool_spec.rb +0 -69
- data/spec/concurrent/executor/ruby_fixed_thread_pool_spec.rb +0 -39
- data/spec/concurrent/executor/ruby_single_thread_executor_spec.rb +0 -18
- data/spec/concurrent/executor/ruby_thread_pool_executor_spec.rb +0 -171
- data/spec/concurrent/executor/safe_task_executor_spec.rb +0 -103
- data/spec/concurrent/executor/thread_pool_class_cast_spec.rb +0 -52
- data/spec/concurrent/executor/thread_pool_executor_shared.rb +0 -155
- data/spec/concurrent/executor/thread_pool_shared.rb +0 -269
- data/spec/concurrent/executor/timer_set_spec.rb +0 -183
- data/spec/concurrent/future_spec.rb +0 -329
- data/spec/concurrent/ivar_spec.rb +0 -215
- data/spec/concurrent/mvar_spec.rb +0 -380
- data/spec/concurrent/obligation_shared.rb +0 -102
- data/spec/concurrent/obligation_spec.rb +0 -282
- data/spec/concurrent/observable_shared.rb +0 -177
- data/spec/concurrent/observable_spec.rb +0 -56
- data/spec/concurrent/options_parser_spec.rb +0 -71
- data/spec/concurrent/promise_spec.rb +0 -367
- data/spec/concurrent/runnable_shared.rb +0 -68
- data/spec/concurrent/runnable_spec.rb +0 -235
- data/spec/concurrent/scheduled_task_spec.rb +0 -340
- data/spec/concurrent/stoppable_shared.rb +0 -37
- data/spec/concurrent/supervisor_spec.rb +0 -1149
- data/spec/concurrent/timer_task_spec.rb +0 -256
- data/spec/concurrent/tvar_spec.rb +0 -137
- data/spec/concurrent/utility/processor_count_spec.rb +0 -20
- data/spec/concurrent/utility/timeout_spec.rb +0 -50
- data/spec/concurrent/utility/timer_spec.rb +0 -52
- data/spec/spec_helper.rb +0 -41
- data/spec/support/example_group_extensions.rb +0 -52
- data/spec/support/less_than_or_equal_to_matcher.rb +0 -5
@@ -1,352 +0,0 @@
|
|
1
|
-
require 'spec_helper'
|
2
|
-
|
3
|
-
module Concurrent
|
4
|
-
|
5
|
-
describe Async do
|
6
|
-
|
7
|
-
let(:executor) { PerThreadExecutor.new }
|
8
|
-
|
9
|
-
let(:async_class) do
|
10
|
-
Class.new do
|
11
|
-
include Concurrent::Async
|
12
|
-
attr_accessor :accessor
|
13
|
-
def initialize
|
14
|
-
init_mutex
|
15
|
-
end
|
16
|
-
def echo(msg)
|
17
|
-
msg
|
18
|
-
end
|
19
|
-
def gather(first, second = nil)
|
20
|
-
return first, second
|
21
|
-
end
|
22
|
-
def boom(ex = StandardError.new)
|
23
|
-
raise ex
|
24
|
-
end
|
25
|
-
def wait(seconds)
|
26
|
-
sleep(seconds)
|
27
|
-
end
|
28
|
-
def with_block
|
29
|
-
yield
|
30
|
-
end
|
31
|
-
end
|
32
|
-
end
|
33
|
-
|
34
|
-
subject do
|
35
|
-
obj = async_class.new
|
36
|
-
obj.executor = executor
|
37
|
-
obj
|
38
|
-
end
|
39
|
-
|
40
|
-
context '#validate_argc' do
|
41
|
-
|
42
|
-
subject do
|
43
|
-
Class.new {
|
44
|
-
def zero() nil; end
|
45
|
-
def three(a, b, c, &block) nil; end
|
46
|
-
def two_plus_two(a, b, c=nil, d=nil, &block) nil; end
|
47
|
-
def many(*args, &block) nil; end
|
48
|
-
}.new
|
49
|
-
end
|
50
|
-
|
51
|
-
it 'raises an exception when the method is not defined' do
|
52
|
-
expect {
|
53
|
-
Async::validate_argc(subject, :bogus)
|
54
|
-
}.to raise_error(StandardError)
|
55
|
-
end
|
56
|
-
|
57
|
-
it 'raises an exception for too many args on a zero arity method' do
|
58
|
-
expect {
|
59
|
-
Async::validate_argc(subject, :zero, 1, 2, 3)
|
60
|
-
}.to raise_error(ArgumentError)
|
61
|
-
end
|
62
|
-
|
63
|
-
it 'does not raise an exception for correct zero arity' do
|
64
|
-
expect {
|
65
|
-
Async::validate_argc(subject, :zero)
|
66
|
-
}.not_to raise_error
|
67
|
-
end
|
68
|
-
|
69
|
-
it 'raises an exception for too many args on a method with positive arity' do
|
70
|
-
expect {
|
71
|
-
Async::validate_argc(subject, :three, 1, 2, 3, 4)
|
72
|
-
}.to raise_error(ArgumentError)
|
73
|
-
end
|
74
|
-
|
75
|
-
it 'raises an exception for too few args on a method with positive arity' do
|
76
|
-
expect {
|
77
|
-
Async::validate_argc(subject, :three, 1, 2)
|
78
|
-
}.to raise_error(ArgumentError)
|
79
|
-
end
|
80
|
-
|
81
|
-
it 'does not raise an exception for correct positive arity' do
|
82
|
-
expect {
|
83
|
-
Async::validate_argc(subject, :three, 1, 2, 3)
|
84
|
-
}.not_to raise_error
|
85
|
-
end
|
86
|
-
|
87
|
-
it 'raises an exception for too few args on a method with negative arity' do
|
88
|
-
expect {
|
89
|
-
Async::validate_argc(subject, :two_plus_two, 1)
|
90
|
-
}.to raise_error(ArgumentError)
|
91
|
-
end
|
92
|
-
|
93
|
-
it 'does not raise an exception for correct negative arity' do
|
94
|
-
expect {
|
95
|
-
Async::validate_argc(subject, :two_plus_two, 1, 2)
|
96
|
-
Async::validate_argc(subject, :two_plus_two, 1, 2, 3, 4)
|
97
|
-
Async::validate_argc(subject, :two_plus_two, 1, 2, 3, 4, 5, 6)
|
98
|
-
|
99
|
-
Async::validate_argc(subject, :many)
|
100
|
-
Async::validate_argc(subject, :many, 1, 2)
|
101
|
-
Async::validate_argc(subject, :many, 1, 2, 3, 4)
|
102
|
-
}.not_to raise_error
|
103
|
-
end
|
104
|
-
end
|
105
|
-
|
106
|
-
context 'executor' do
|
107
|
-
|
108
|
-
it 'returns the default executor when #executor= has never been called' do
|
109
|
-
Concurrent.configuration.should_receive(:global_operation_pool).
|
110
|
-
and_return(ImmediateExecutor.new)
|
111
|
-
subject = async_class.new
|
112
|
-
subject.async.echo(:foo)
|
113
|
-
end
|
114
|
-
|
115
|
-
it 'returns the memo after #executor= has been called' do
|
116
|
-
executor = ImmediateExecutor.new
|
117
|
-
executor.should_receive(:post)
|
118
|
-
subject = async_class.new
|
119
|
-
subject.executor = executor
|
120
|
-
subject.async.echo(:foo)
|
121
|
-
end
|
122
|
-
|
123
|
-
it 'raises an exception if #executor= is called after initialization complete' do
|
124
|
-
executor = ImmediateExecutor.new
|
125
|
-
subject = async_class.new
|
126
|
-
subject.async.echo(:foo)
|
127
|
-
expect {
|
128
|
-
subject.executor = executor
|
129
|
-
}.to raise_error(ArgumentError)
|
130
|
-
end
|
131
|
-
end
|
132
|
-
|
133
|
-
context '#async' do
|
134
|
-
|
135
|
-
it 'raises an error when calling a method that does not exist' do
|
136
|
-
expect {
|
137
|
-
subject.async.bogus
|
138
|
-
}.to raise_error(StandardError)
|
139
|
-
end
|
140
|
-
|
141
|
-
it 'raises an error when passing too few arguments' do
|
142
|
-
expect {
|
143
|
-
subject.async.gather
|
144
|
-
}.to raise_error(ArgumentError)
|
145
|
-
end
|
146
|
-
|
147
|
-
it 'raises an error when pasing too many arguments (arity >= 0)' do
|
148
|
-
expect {
|
149
|
-
subject.async.echo(1, 2, 3, 4, 5)
|
150
|
-
}.to raise_error(StandardError)
|
151
|
-
end
|
152
|
-
|
153
|
-
it 'returns a :pending Future' do
|
154
|
-
val = subject.async.wait(5)
|
155
|
-
val.should be_a Concurrent::Future
|
156
|
-
val.should be_pending
|
157
|
-
end
|
158
|
-
|
159
|
-
it 'runs the Future on the memoized executor' do
|
160
|
-
executor = ImmediateExecutor.new
|
161
|
-
executor.should_receive(:post).with(any_args)
|
162
|
-
subject = async_class.new
|
163
|
-
subject.executor = executor
|
164
|
-
subject.async.echo(:foo)
|
165
|
-
end
|
166
|
-
|
167
|
-
it 'sets the value on success' do
|
168
|
-
val = subject.async.echo(:foo)
|
169
|
-
val.value.should eq :foo
|
170
|
-
val.should be_fulfilled
|
171
|
-
end
|
172
|
-
|
173
|
-
it 'sets the reason on failure' do
|
174
|
-
ex = ArgumentError.new
|
175
|
-
val = subject.async.boom(ex)
|
176
|
-
sleep(0.1)
|
177
|
-
val.reason.should eq ex
|
178
|
-
val.should be_rejected
|
179
|
-
end
|
180
|
-
|
181
|
-
it 'sets the reason when giving too many optional arguments' do
|
182
|
-
val = subject.async.gather(1, 2, 3, 4, 5)
|
183
|
-
sleep(0.1)
|
184
|
-
val.reason.should be_a StandardError
|
185
|
-
val.should be_rejected
|
186
|
-
end
|
187
|
-
|
188
|
-
it 'supports attribute accessors' do
|
189
|
-
subject.async.accessor = :foo
|
190
|
-
sleep(0.1)
|
191
|
-
val = subject.async.accessor
|
192
|
-
sleep(0.1)
|
193
|
-
val.value.should eq :foo
|
194
|
-
subject.accessor.should eq :foo
|
195
|
-
end
|
196
|
-
|
197
|
-
it 'supports methods with blocks' do
|
198
|
-
val = subject.async.with_block{ :foo }
|
199
|
-
sleep(0.1)
|
200
|
-
val.value.should eq :foo
|
201
|
-
end
|
202
|
-
|
203
|
-
it 'is aliased as #future' do
|
204
|
-
val = subject.future.wait(5)
|
205
|
-
val.should be_a Concurrent::Future
|
206
|
-
end
|
207
|
-
|
208
|
-
context '#method_missing' do
|
209
|
-
|
210
|
-
it 'defines the method after the first call' do
|
211
|
-
expect { subject.async.method(:echo) }.to raise_error(NameError)
|
212
|
-
subject.async.echo(:foo)
|
213
|
-
sleep(0.1)
|
214
|
-
expect { subject.async.method(:echo) }.not_to raise_error
|
215
|
-
end
|
216
|
-
|
217
|
-
it 'does not define the method on name/arity exception' do
|
218
|
-
expect { subject.async.method(:bogus) }.to raise_error(NameError)
|
219
|
-
expect { subject.async.bogus }.to raise_error(NameError)
|
220
|
-
expect { subject.async.method(:bogus) }.to raise_error(NameError)
|
221
|
-
end
|
222
|
-
end
|
223
|
-
end
|
224
|
-
|
225
|
-
context '#await' do
|
226
|
-
|
227
|
-
it 'raises an error when calling a method that does not exist' do
|
228
|
-
expect {
|
229
|
-
subject.await.bogus
|
230
|
-
}.to raise_error(StandardError)
|
231
|
-
end
|
232
|
-
|
233
|
-
it 'raises an error when passing too few arguments' do
|
234
|
-
expect {
|
235
|
-
subject.await.gather
|
236
|
-
}.to raise_error(ArgumentError)
|
237
|
-
end
|
238
|
-
|
239
|
-
it 'raises an error when pasing too many arguments (arity >= 0)' do
|
240
|
-
expect {
|
241
|
-
subject.await.echo(1, 2, 3, 4, 5)
|
242
|
-
}.to raise_error(StandardError)
|
243
|
-
end
|
244
|
-
|
245
|
-
it 'returns a :fulfilled IVar' do
|
246
|
-
val = subject.await.echo(5)
|
247
|
-
val.should be_a Concurrent::IVar
|
248
|
-
val.should be_fulfilled
|
249
|
-
end
|
250
|
-
|
251
|
-
it 'sets the value on success' do
|
252
|
-
val = subject.await.echo(:foo)
|
253
|
-
val.value.should eq :foo
|
254
|
-
val.should be_fulfilled
|
255
|
-
end
|
256
|
-
|
257
|
-
it 'sets the reason on failure' do
|
258
|
-
ex = ArgumentError.new
|
259
|
-
val = subject.await.boom(ex)
|
260
|
-
val.reason.should eq ex
|
261
|
-
val.should be_rejected
|
262
|
-
end
|
263
|
-
|
264
|
-
it 'sets the reason when giving too many optional arguments' do
|
265
|
-
val = subject.await.gather(1, 2, 3, 4, 5)
|
266
|
-
val.reason.should be_a StandardError
|
267
|
-
val.should be_rejected
|
268
|
-
end
|
269
|
-
|
270
|
-
it 'supports attribute accessors' do
|
271
|
-
subject.await.accessor = :foo
|
272
|
-
val = subject.await.accessor
|
273
|
-
val.value.should eq :foo
|
274
|
-
subject.accessor.should eq :foo
|
275
|
-
end
|
276
|
-
|
277
|
-
it 'supports methods with blocks' do
|
278
|
-
val = subject.await.with_block{ :foo }
|
279
|
-
val.value.should eq :foo
|
280
|
-
end
|
281
|
-
|
282
|
-
it 'is aliased as #delay' do
|
283
|
-
val = subject.delay.echo(5)
|
284
|
-
val.should be_a Concurrent::IVar
|
285
|
-
end
|
286
|
-
|
287
|
-
context '#method_missing' do
|
288
|
-
|
289
|
-
it 'defines the method after the first call' do
|
290
|
-
expect { subject.await.method(:echo) }.to raise_error(NameError)
|
291
|
-
subject.await.echo(:foo)
|
292
|
-
expect { subject.await.method(:echo) }.not_to raise_error
|
293
|
-
end
|
294
|
-
|
295
|
-
it 'does not define the method on name/arity exception' do
|
296
|
-
expect { subject.await.method(:bogus) }.to raise_error(NameError)
|
297
|
-
expect { subject.await.bogus }.to raise_error(NameError)
|
298
|
-
expect { subject.await.method(:bogus) }.to raise_error(NameError)
|
299
|
-
end
|
300
|
-
end
|
301
|
-
end
|
302
|
-
|
303
|
-
context 'locking' do
|
304
|
-
|
305
|
-
it 'uses the same mutex for both #async and #await' do
|
306
|
-
object = Class.new {
|
307
|
-
include Concurrent::Async
|
308
|
-
attr_reader :bucket
|
309
|
-
def initialize() init_mutex; end
|
310
|
-
def gather(seconds, first, *rest)
|
311
|
-
sleep(seconds)
|
312
|
-
(@bucket ||= []).concat([first])
|
313
|
-
@bucket.concat(rest)
|
314
|
-
end
|
315
|
-
}.new
|
316
|
-
|
317
|
-
object.async.gather(0.5, :a, :b)
|
318
|
-
sleep(0.1)
|
319
|
-
object.await.gather(0, :c, :d)
|
320
|
-
object.bucket.should eq [:a, :b, :c, :d]
|
321
|
-
end
|
322
|
-
|
323
|
-
context 'raises an InitializationError' do
|
324
|
-
|
325
|
-
let(:async_class) do
|
326
|
-
Class.new do
|
327
|
-
include Concurrent::Async
|
328
|
-
def echo(msg) msg; end
|
329
|
-
end
|
330
|
-
end
|
331
|
-
|
332
|
-
it 'when #async is called before #init_mutex' do
|
333
|
-
expect {
|
334
|
-
async_class.new.async.echo(:foo)
|
335
|
-
}.to raise_error(Concurrent::InitializationError)
|
336
|
-
end
|
337
|
-
|
338
|
-
it 'when #await is called before #init_mutex' do
|
339
|
-
expect {
|
340
|
-
async_class.new.async.echo(:foo)
|
341
|
-
}.to raise_error(Concurrent::InitializationError)
|
342
|
-
end
|
343
|
-
|
344
|
-
it 'when #executor= is called before #init_mutex' do
|
345
|
-
expect {
|
346
|
-
async_class.new.executor = Concurrent::ImmediateExecutor.new
|
347
|
-
}.to raise_error(Concurrent::InitializationError)
|
348
|
-
end
|
349
|
-
end
|
350
|
-
end
|
351
|
-
end
|
352
|
-
end
|
@@ -1,172 +0,0 @@
|
|
1
|
-
require 'spec_helper'
|
2
|
-
|
3
|
-
share_examples_for :atomic_boolean do
|
4
|
-
|
5
|
-
describe 'construction' do
|
6
|
-
|
7
|
-
it 'sets the initial value' do
|
8
|
-
described_class.new(true).value.should be_true
|
9
|
-
end
|
10
|
-
|
11
|
-
it 'defaults the initial value to false' do
|
12
|
-
described_class.new.value.should be_false
|
13
|
-
end
|
14
|
-
|
15
|
-
it 'evaluates the truthiness of a true value' do
|
16
|
-
described_class.new(10).value.should be_true
|
17
|
-
end
|
18
|
-
|
19
|
-
it 'evaluates the truthiness of a false value' do
|
20
|
-
described_class.new(nil).value.should be_false
|
21
|
-
end
|
22
|
-
end
|
23
|
-
|
24
|
-
describe '#value' do
|
25
|
-
|
26
|
-
it 'returns the current value' do
|
27
|
-
counter = described_class.new(true)
|
28
|
-
counter.value.should be_true
|
29
|
-
counter.make_false
|
30
|
-
counter.value.should be_false
|
31
|
-
counter.make_true
|
32
|
-
counter.value.should be_true
|
33
|
-
end
|
34
|
-
end
|
35
|
-
|
36
|
-
describe '#value=' do
|
37
|
-
|
38
|
-
it 'sets the #value to the given `Boolean`' do
|
39
|
-
atomic = described_class.new(true)
|
40
|
-
atomic.value = false
|
41
|
-
atomic.value.should be_false
|
42
|
-
end
|
43
|
-
|
44
|
-
it 'returns the new value' do
|
45
|
-
atomic = described_class.new(false)
|
46
|
-
(atomic.value = true).should be_true
|
47
|
-
end
|
48
|
-
|
49
|
-
it 'evaluates the truthiness of a true value' do
|
50
|
-
atomic = described_class.new(false)
|
51
|
-
atomic.value = 10
|
52
|
-
atomic.value.should be_true
|
53
|
-
end
|
54
|
-
|
55
|
-
it 'evaluates the truthiness of a false value' do
|
56
|
-
atomic = described_class.new(true)
|
57
|
-
atomic.value = nil
|
58
|
-
atomic.value.should be_false
|
59
|
-
end
|
60
|
-
end
|
61
|
-
|
62
|
-
describe '#true?' do
|
63
|
-
|
64
|
-
specify { described_class.new(true).true?.should be_true }
|
65
|
-
|
66
|
-
specify { described_class.new(false).true?.should be_false }
|
67
|
-
end
|
68
|
-
|
69
|
-
describe '#false?' do
|
70
|
-
|
71
|
-
specify { described_class.new(true).false?.should be_false }
|
72
|
-
|
73
|
-
specify { described_class.new(false).false?.should be_true }
|
74
|
-
end
|
75
|
-
|
76
|
-
describe '#make_true' do
|
77
|
-
|
78
|
-
it 'makes a false value true and returns true' do
|
79
|
-
subject = described_class.new(false)
|
80
|
-
subject.make_true.should be_true
|
81
|
-
subject.value.should be_true
|
82
|
-
end
|
83
|
-
|
84
|
-
it 'keeps a true value true and returns false' do
|
85
|
-
subject = described_class.new(true)
|
86
|
-
subject.make_true.should be_false
|
87
|
-
subject.value.should be_true
|
88
|
-
end
|
89
|
-
end
|
90
|
-
|
91
|
-
describe '#make_false' do
|
92
|
-
|
93
|
-
it 'makes a true value false and returns true' do
|
94
|
-
subject = described_class.new(true)
|
95
|
-
subject.make_false.should be_true
|
96
|
-
subject.value.should be_false
|
97
|
-
end
|
98
|
-
|
99
|
-
it 'keeps a false value false and returns false' do
|
100
|
-
subject = described_class.new(false)
|
101
|
-
subject.make_false.should be_false
|
102
|
-
subject.value.should be_false
|
103
|
-
end
|
104
|
-
end
|
105
|
-
end
|
106
|
-
|
107
|
-
module Concurrent
|
108
|
-
|
109
|
-
describe MutexAtomicBoolean do
|
110
|
-
|
111
|
-
it_should_behave_like :atomic_boolean
|
112
|
-
|
113
|
-
specify 'construction is synchronized' do
|
114
|
-
mutex = double('mutex')
|
115
|
-
Mutex.should_receive(:new).once.with(no_args).and_return(mutex)
|
116
|
-
described_class.new
|
117
|
-
end
|
118
|
-
|
119
|
-
context 'instance methods' do
|
120
|
-
|
121
|
-
before(:each) do
|
122
|
-
mutex = double('mutex')
|
123
|
-
Mutex.stub(:new).with(no_args).and_return(mutex)
|
124
|
-
mutex.should_receive(:lock)
|
125
|
-
mutex.should_receive(:unlock)
|
126
|
-
end
|
127
|
-
|
128
|
-
specify 'value is synchronized' do
|
129
|
-
described_class.new.value
|
130
|
-
end
|
131
|
-
|
132
|
-
specify 'value= is synchronized' do
|
133
|
-
described_class.new.value = 10
|
134
|
-
end
|
135
|
-
|
136
|
-
specify 'true? is synchronized' do
|
137
|
-
described_class.new.true?
|
138
|
-
end
|
139
|
-
|
140
|
-
specify 'false? is synchronized' do
|
141
|
-
described_class.new.false?
|
142
|
-
end
|
143
|
-
|
144
|
-
specify 'make_true is synchronized' do
|
145
|
-
described_class.new.make_true
|
146
|
-
end
|
147
|
-
|
148
|
-
specify 'make_false is synchronized' do
|
149
|
-
described_class.new.make_false
|
150
|
-
end
|
151
|
-
end
|
152
|
-
end
|
153
|
-
|
154
|
-
if TestHelpers.jruby?
|
155
|
-
|
156
|
-
describe JavaAtomicBoolean do
|
157
|
-
it_should_behave_like :atomic_boolean
|
158
|
-
end
|
159
|
-
end
|
160
|
-
|
161
|
-
describe AtomicBoolean do
|
162
|
-
if jruby?
|
163
|
-
it 'inherits from JavaAtomicBoolean' do
|
164
|
-
AtomicBoolean.ancestors.should include(JavaAtomicBoolean)
|
165
|
-
end
|
166
|
-
else
|
167
|
-
it 'inherits from MutexAtomicBoolean' do
|
168
|
-
AtomicBoolean.ancestors.should include(MutexAtomicBoolean)
|
169
|
-
end
|
170
|
-
end
|
171
|
-
end
|
172
|
-
end
|