empathy 0.0.1.RC0
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +17 -0
- data/Gemfile +4 -0
- data/LICENSE.txt +22 -0
- data/README.rdoc +135 -0
- data/Rakefile +33 -0
- data/TESTING.rdoc +11 -0
- data/empathy.gemspec +23 -0
- data/empathy.mspec +34 -0
- data/lib/empathy.rb +162 -0
- data/lib/empathy/em/condition_variable.rb +57 -0
- data/lib/empathy/em/mutex.rb +70 -0
- data/lib/empathy/em/queue.rb +84 -0
- data/lib/empathy/em/thread.rb +363 -0
- data/lib/empathy/object.rb +19 -0
- data/lib/empathy/thread.rb +8 -0
- data/lib/empathy/version.rb +3 -0
- data/mspec/lib/mspec/empathy.rb +19 -0
- data/mspec/lib/mspec/guards/empathy.rb +10 -0
- data/rubyspec/core/kernel/fixtures/__method__.rb +25 -0
- data/rubyspec/core/kernel/fixtures/autoload_b.rb +5 -0
- data/rubyspec/core/kernel/fixtures/autoload_c.rb +5 -0
- data/rubyspec/core/kernel/fixtures/autoload_d.rb +5 -0
- data/rubyspec/core/kernel/fixtures/caller_fixture1.rb +42 -0
- data/rubyspec/core/kernel/fixtures/caller_fixture2.rb +26 -0
- data/rubyspec/core/kernel/fixtures/chomp.rb +4 -0
- data/rubyspec/core/kernel/fixtures/chomp_f.rb +4 -0
- data/rubyspec/core/kernel/fixtures/chop.rb +4 -0
- data/rubyspec/core/kernel/fixtures/chop_f.rb +4 -0
- data/rubyspec/core/kernel/fixtures/classes.rb +410 -0
- data/rubyspec/core/kernel/fixtures/eval_locals.rb +6 -0
- data/rubyspec/core/kernel/fixtures/eval_return_with_lambda.rb +12 -0
- data/rubyspec/core/kernel/fixtures/eval_return_without_lambda.rb +14 -0
- data/rubyspec/core/kernel/fixtures/test.rb +362 -0
- data/rubyspec/core/kernel/sleep_spec.rb +43 -0
- data/rubyspec/core/mutex/lock_spec.rb +8 -0
- data/rubyspec/core/mutex/locked_spec.rb +8 -0
- data/rubyspec/core/mutex/sleep_spec.rb +56 -0
- data/rubyspec/core/mutex/synchronize_spec.rb +8 -0
- data/rubyspec/core/mutex/try_lock_spec.rb +8 -0
- data/rubyspec/core/mutex/unlock_spec.rb +8 -0
- data/rubyspec/core/thread/abort_on_exception_spec.rb +126 -0
- data/rubyspec/core/thread/add_trace_func_spec.rb +7 -0
- data/rubyspec/core/thread/alive_spec.rb +60 -0
- data/rubyspec/core/thread/allocate_spec.rb +9 -0
- data/rubyspec/core/thread/backtrace_spec.rb +7 -0
- data/rubyspec/core/thread/critical_spec.rb +96 -0
- data/rubyspec/core/thread/current_spec.rb +15 -0
- data/rubyspec/core/thread/element_reference_spec.rb +53 -0
- data/rubyspec/core/thread/element_set_spec.rb +46 -0
- data/rubyspec/core/thread/exclusive_spec.rb +20 -0
- data/rubyspec/core/thread/exit_spec.rb +21 -0
- data/rubyspec/core/thread/fixtures/classes.rb +291 -0
- data/rubyspec/core/thread/fork_spec.rb +9 -0
- data/rubyspec/core/thread/group_spec.rb +5 -0
- data/rubyspec/core/thread/initialize_spec.rb +26 -0
- data/rubyspec/core/thread/inspect_spec.rb +48 -0
- data/rubyspec/core/thread/join_spec.rb +63 -0
- data/rubyspec/core/thread/key_spec.rb +64 -0
- data/rubyspec/core/thread/keys_spec.rb +47 -0
- data/rubyspec/core/thread/kill_spec.rb +21 -0
- data/rubyspec/core/thread/list_spec.rb +38 -0
- data/rubyspec/core/thread/main_spec.rb +10 -0
- data/rubyspec/core/thread/new_spec.rb +56 -0
- data/rubyspec/core/thread/pass_spec.rb +8 -0
- data/rubyspec/core/thread/priority_spec.rb +9 -0
- data/rubyspec/core/thread/raise_spec.rb +225 -0
- data/rubyspec/core/thread/run_spec.rb +9 -0
- data/rubyspec/core/thread/safe_level_spec.rb +6 -0
- data/rubyspec/core/thread/set_trace_func_spec.rb +7 -0
- data/rubyspec/core/thread/shared/exit.rb +173 -0
- data/rubyspec/core/thread/shared/start.rb +51 -0
- data/rubyspec/core/thread/shared/wakeup.rb +59 -0
- data/rubyspec/core/thread/start_spec.rb +9 -0
- data/rubyspec/core/thread/status_spec.rb +48 -0
- data/rubyspec/core/thread/stop_spec.rb +66 -0
- data/rubyspec/core/thread/terminate_spec.rb +11 -0
- data/rubyspec/core/thread/value_spec.rb +36 -0
- data/rubyspec/core/thread/wakeup_spec.rb +7 -0
- data/rubyspec/empathy_spec.rb +26 -0
- data/rubyspec/library/conditionvariable/broadcast_spec.rb +62 -0
- data/rubyspec/library/conditionvariable/signal_spec.rb +64 -0
- data/rubyspec/library/conditionvariable/wait_spec.rb +21 -0
- data/rubyspec/library/mutex/lock_spec.rb +10 -0
- data/rubyspec/library/mutex/locked_spec.rb +10 -0
- data/rubyspec/library/mutex/synchronize_spec.rb +10 -0
- data/rubyspec/library/mutex/try_lock_spec.rb +10 -0
- data/rubyspec/library/mutex/unlock_spec.rb +10 -0
- data/rubyspec/library/queue/append_spec.rb +7 -0
- data/rubyspec/library/queue/clear_spec.rb +15 -0
- data/rubyspec/library/queue/deq_spec.rb +7 -0
- data/rubyspec/library/queue/empty_spec.rb +15 -0
- data/rubyspec/library/queue/enq_spec.rb +7 -0
- data/rubyspec/library/queue/length_spec.rb +7 -0
- data/rubyspec/library/queue/num_waiting_spec.rb +19 -0
- data/rubyspec/library/queue/pop_spec.rb +7 -0
- data/rubyspec/library/queue/push_spec.rb +7 -0
- data/rubyspec/library/queue/shared/deque.rb +37 -0
- data/rubyspec/library/queue/shared/enque.rb +10 -0
- data/rubyspec/library/queue/shared/length.rb +9 -0
- data/rubyspec/library/queue/shift_spec.rb +7 -0
- data/rubyspec/library/queue/size_spec.rb +7 -0
- data/rubyspec/shared/kernel/raise.rb +68 -0
- data/rubyspec/shared/mutex/lock.rb +52 -0
- data/rubyspec/shared/mutex/locked.rb +31 -0
- data/rubyspec/shared/mutex/synchronize.rb +23 -0
- data/rubyspec/shared/mutex/try_lock.rb +30 -0
- data/rubyspec/shared/mutex/unlock.rb +35 -0
- data/rubyspec/spec_helper.rb +48 -0
- data/spec/empathy_spec.rb +129 -0
- data/spec/library_spec.rb +79 -0
- data/spec/spec_helper.rb +6 -0
- metadata +222 -0
@@ -0,0 +1,68 @@
|
|
1
|
+
describe :kernel_raise, :shared => true do
|
2
|
+
before :each do
|
3
|
+
ScratchPad.clear
|
4
|
+
end
|
5
|
+
|
6
|
+
it "aborts execution" do
|
7
|
+
lambda do
|
8
|
+
@object.raise Exception, "abort"
|
9
|
+
ScratchPad.record :no_abort
|
10
|
+
end.should raise_error(Exception, "abort")
|
11
|
+
|
12
|
+
ScratchPad.recorded.should be_nil
|
13
|
+
end
|
14
|
+
|
15
|
+
it "raises RuntimeError if no exception class is given" do
|
16
|
+
lambda { @object.raise }.should raise_error(RuntimeError)
|
17
|
+
end
|
18
|
+
|
19
|
+
it "raises a given Exception instance" do
|
20
|
+
error = RuntimeError.new
|
21
|
+
lambda { @object.raise(error) }.should raise_error(error)
|
22
|
+
end
|
23
|
+
|
24
|
+
it "raises a RuntimeError if string given" do
|
25
|
+
lambda { @object.raise("a bad thing") }.should raise_error(RuntimeError)
|
26
|
+
end
|
27
|
+
|
28
|
+
it "raises a TypeError when passed a non-Exception object" do
|
29
|
+
lambda { @object.raise(Object.new) }.should raise_error(TypeError)
|
30
|
+
end
|
31
|
+
|
32
|
+
it "raises a TypeError when passed true" do
|
33
|
+
lambda { @object.raise(true) }.should raise_error(TypeError)
|
34
|
+
end
|
35
|
+
|
36
|
+
it "raises a TypeError when passed false" do
|
37
|
+
lambda { @object.raise(false) }.should raise_error(TypeError)
|
38
|
+
end
|
39
|
+
|
40
|
+
it "raises a TypeError when passed nil" do
|
41
|
+
lambda { @object.raise(nil) }.should raise_error(TypeError)
|
42
|
+
end
|
43
|
+
|
44
|
+
it "re-raises the rescued exception" do
|
45
|
+
lambda do
|
46
|
+
begin
|
47
|
+
raise Exception, "outer"
|
48
|
+
ScratchPad.record :no_abort
|
49
|
+
rescue
|
50
|
+
begin
|
51
|
+
raise StandardError, "inner"
|
52
|
+
rescue
|
53
|
+
end
|
54
|
+
|
55
|
+
@object.raise
|
56
|
+
ScratchPad.record :no_reraise
|
57
|
+
end
|
58
|
+
end.should raise_error(Exception, "outer")
|
59
|
+
|
60
|
+
ScratchPad.recorded.should be_nil
|
61
|
+
end
|
62
|
+
|
63
|
+
it "allows Exception, message, and backtrace parameters" do
|
64
|
+
lambda do
|
65
|
+
@object.raise(ArgumentError, "message", caller)
|
66
|
+
end.should raise_error(ArgumentError, "message")
|
67
|
+
end
|
68
|
+
end
|
@@ -0,0 +1,52 @@
|
|
1
|
+
describe :mutex_lock, :shared => true do
|
2
|
+
before :each do
|
3
|
+
ScratchPad.clear
|
4
|
+
end
|
5
|
+
|
6
|
+
it "returns self" do
|
7
|
+
m = Mutex.new
|
8
|
+
m.lock.should == m
|
9
|
+
m.unlock
|
10
|
+
end
|
11
|
+
|
12
|
+
it "waits if the lock is not available" do
|
13
|
+
m = Mutex.new
|
14
|
+
|
15
|
+
m.lock
|
16
|
+
|
17
|
+
th = Thread.new do
|
18
|
+
m.lock
|
19
|
+
ScratchPad.record :after_lock
|
20
|
+
end
|
21
|
+
|
22
|
+
Thread.pass while th.status and th.status != "sleep"
|
23
|
+
|
24
|
+
ScratchPad.recorded.should be_nil
|
25
|
+
m.unlock
|
26
|
+
th.join
|
27
|
+
ScratchPad.recorded.should == :after_lock
|
28
|
+
end
|
29
|
+
|
30
|
+
# Unable to find a specific ticket but behavior change may be
|
31
|
+
# related to this ML thread.
|
32
|
+
ruby_bug "[ruby-core:23457]", "1.8.7.174" do
|
33
|
+
it "raises a ThreadError when used recursively" do
|
34
|
+
m = Mutex.new
|
35
|
+
|
36
|
+
th = Thread.new do
|
37
|
+
m.lock
|
38
|
+
m.lock
|
39
|
+
v = 1
|
40
|
+
end
|
41
|
+
|
42
|
+
Thread.pass while th.status and th.status != "sleep"
|
43
|
+
|
44
|
+
ScratchPad.recorded.should be_nil
|
45
|
+
|
46
|
+
lambda do
|
47
|
+
th.kill
|
48
|
+
th.join
|
49
|
+
end.should raise_error(ThreadError)
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
describe :mutex_locked, :shared => true do
|
2
|
+
it "returns true if locked" do
|
3
|
+
m = Mutex.new
|
4
|
+
m.lock
|
5
|
+
m.locked?.should be_true
|
6
|
+
end
|
7
|
+
|
8
|
+
it "returns false if unlocked" do
|
9
|
+
m = Mutex.new
|
10
|
+
m.locked?.should be_false
|
11
|
+
end
|
12
|
+
|
13
|
+
it "returns the status of the lock" do
|
14
|
+
m1 = Mutex.new
|
15
|
+
m2 = Mutex.new
|
16
|
+
|
17
|
+
m2.lock # hold th with only m1 locked
|
18
|
+
|
19
|
+
th = Thread.new do
|
20
|
+
m1.lock
|
21
|
+
m2.lock
|
22
|
+
end
|
23
|
+
|
24
|
+
Thread.pass while th.status and th.status != "sleep"
|
25
|
+
|
26
|
+
m1.locked?.should be_true
|
27
|
+
m2.unlock # release th
|
28
|
+
th.join
|
29
|
+
m1.locked?.should be_false
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
describe :mutex_synchronize, :shared => true do
|
2
|
+
it "wraps the lock/unlock pair in an ensure" do
|
3
|
+
m1 = Mutex.new
|
4
|
+
m2 = Mutex.new
|
5
|
+
m2.lock
|
6
|
+
|
7
|
+
th = Thread.new do
|
8
|
+
lambda do
|
9
|
+
m1.synchronize do
|
10
|
+
m2.lock
|
11
|
+
raise Exception
|
12
|
+
end
|
13
|
+
end.should raise_error(Exception)
|
14
|
+
end
|
15
|
+
|
16
|
+
Thread.pass while th.status and th.status != "sleep"
|
17
|
+
|
18
|
+
m1.locked?.should be_true
|
19
|
+
m2.unlock
|
20
|
+
th.join
|
21
|
+
m1.locked?.should be_false
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,30 @@
|
|
1
|
+
describe :mutex_try_lock, :shared => true do
|
2
|
+
describe "when unlocked" do
|
3
|
+
it "returns true" do
|
4
|
+
m = Mutex.new
|
5
|
+
m.try_lock.should be_true
|
6
|
+
end
|
7
|
+
|
8
|
+
it "locks the mutex" do
|
9
|
+
m = Mutex.new
|
10
|
+
m.try_lock
|
11
|
+
m.locked?.should be_true
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
describe "when locked by the current thread" do
|
16
|
+
it "returns false" do
|
17
|
+
m = Mutex.new
|
18
|
+
m.lock
|
19
|
+
m.try_lock.should be_false
|
20
|
+
end
|
21
|
+
end
|
22
|
+
|
23
|
+
describe "when locked by another thread" do
|
24
|
+
it "returns false" do
|
25
|
+
m = Mutex.new
|
26
|
+
m.lock
|
27
|
+
Thread.new { m.try_lock }.value.should be_false
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
@@ -0,0 +1,35 @@
|
|
1
|
+
describe :mutex_unlock, :shared => true do
|
2
|
+
it "raises ThreadError unless Mutex is locked" do
|
3
|
+
mutex = Mutex.new
|
4
|
+
lambda { mutex.unlock }.should raise_error(ThreadError)
|
5
|
+
end
|
6
|
+
|
7
|
+
it "raises ThreadError unless thread owns Mutex" do
|
8
|
+
mutex = Mutex.new
|
9
|
+
wait = Mutex.new
|
10
|
+
wait.lock
|
11
|
+
th = Thread.new do
|
12
|
+
mutex.lock
|
13
|
+
wait.lock
|
14
|
+
end
|
15
|
+
|
16
|
+
# avoid race on mutex.lock
|
17
|
+
Thread.pass while th.status and th.status != "sleep"
|
18
|
+
|
19
|
+
lambda { mutex.unlock }.should raise_error(ThreadError)
|
20
|
+
|
21
|
+
wait.unlock
|
22
|
+
th.join
|
23
|
+
end
|
24
|
+
|
25
|
+
it "raises ThreadError if previously locking thread is gone" do
|
26
|
+
mutex = Mutex.new
|
27
|
+
th = Thread.new do
|
28
|
+
mutex.lock
|
29
|
+
end
|
30
|
+
|
31
|
+
th.join
|
32
|
+
|
33
|
+
lambda { mutex.unlock }.should raise_error(ThreadError)
|
34
|
+
end
|
35
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
# encoding: UTF-8
|
2
|
+
unless ENV['MSPEC_RUNNER']
|
3
|
+
begin
|
4
|
+
require "pp"
|
5
|
+
require 'mspec/version'
|
6
|
+
require 'mspec/helpers'
|
7
|
+
require 'mspec/guards'
|
8
|
+
require 'mspec/runner/shared'
|
9
|
+
require 'mspec/matchers/be_ancestor_of'
|
10
|
+
require 'mspec/matchers/output'
|
11
|
+
require 'mspec/matchers/output_to_fd'
|
12
|
+
require 'mspec/matchers/complain'
|
13
|
+
require 'mspec/matchers/equal_element'
|
14
|
+
require 'mspec/matchers/equal_utf16'
|
15
|
+
require 'mspec/matchers/match_yaml'
|
16
|
+
|
17
|
+
# Code to setup HOME directory correctly on Windows
|
18
|
+
# This duplicates Ruby 1.9 semantics for defining HOME
|
19
|
+
platform_is :windows do
|
20
|
+
if ENV['HOME']
|
21
|
+
ENV['HOME'] = ENV['HOME'].tr '\\', '/'
|
22
|
+
elsif ENV['HOMEDIR'] && ENV['HOMEDRIVE']
|
23
|
+
ENV['HOME'] = File.join(ENV['HOMEDRIVE'], ENV['HOMEDIR'])
|
24
|
+
elsif ENV['HOMEDIR']
|
25
|
+
ENV['HOME'] = ENV['HOMEDIR']
|
26
|
+
elsif ENV['HOMEDRIVE']
|
27
|
+
ENV['HOME'] = ENV['HOMEDRIVE']
|
28
|
+
elsif ENV['USERPROFILE']
|
29
|
+
ENV['HOME'] = ENV['USERPROFILE']
|
30
|
+
else
|
31
|
+
puts "No suitable HOME environment found. This means that all of"
|
32
|
+
puts "HOME, HOMEDIR, HOMEDRIVE, and USERPROFILE are not set"
|
33
|
+
exit 1
|
34
|
+
end
|
35
|
+
end
|
36
|
+
rescue LoadError
|
37
|
+
puts "Please install the MSpec gem to run the specs."
|
38
|
+
exit 1
|
39
|
+
end
|
40
|
+
end
|
41
|
+
|
42
|
+
minimum_version = "1.5.18"
|
43
|
+
unless MSpec::VERSION >= minimum_version
|
44
|
+
puts "Please install MSpec version >= #{minimum_version} to run the specs"
|
45
|
+
exit 1
|
46
|
+
end
|
47
|
+
|
48
|
+
$VERBOSE = nil unless ENV['OUTPUT_WARNINGS']
|
@@ -0,0 +1,129 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
# Test class delegation
|
4
|
+
class EmTest
|
5
|
+
def self.test_class_method(an_arg=:test_class_method,&block)
|
6
|
+
return block.call if block_given?
|
7
|
+
an_arg
|
8
|
+
end
|
9
|
+
|
10
|
+
def whoami
|
11
|
+
:test
|
12
|
+
end
|
13
|
+
end
|
14
|
+
|
15
|
+
module Empathy
|
16
|
+
module EM
|
17
|
+
class EmTest
|
18
|
+
def self.test_class_method(an_arg=:em_test_class_method,&block)
|
19
|
+
return block.call if block_given?
|
20
|
+
an_arg
|
21
|
+
end
|
22
|
+
|
23
|
+
def whoami
|
24
|
+
:em_test
|
25
|
+
end
|
26
|
+
end
|
27
|
+
end
|
28
|
+
|
29
|
+
create_delegate_module('EmTest',:new, :test_class_method)
|
30
|
+
end
|
31
|
+
|
32
|
+
describe Empathy do
|
33
|
+
|
34
|
+
describe "#run" do
|
35
|
+
it "raise errors when block raises error" do
|
36
|
+
lambda do
|
37
|
+
Empathy.run { raise RuntimeError }
|
38
|
+
end.should raise_error(RuntimeError)
|
39
|
+
EventMachine.reactor_running?.should be_false
|
40
|
+
end
|
41
|
+
end
|
42
|
+
|
43
|
+
shared_examples_for "empathy_delegation" do
|
44
|
+
it "delegates Thread" do
|
45
|
+
t = Empathy::Thread.new() { }
|
46
|
+
t.should be_kind_of(thread_class)
|
47
|
+
Empathy::Thread.list.should == thread_class.list
|
48
|
+
Empathy::Thread.current.should == thread_class.current
|
49
|
+
Empathy::Thread.main.should == thread_class.main
|
50
|
+
Empathy::Thread.singleton_methods.should include(:stop,:pass)
|
51
|
+
end
|
52
|
+
|
53
|
+
it "delegates Queue" do
|
54
|
+
q = Empathy::Queue.new()
|
55
|
+
q.should be_kind_of(queue_class)
|
56
|
+
end
|
57
|
+
|
58
|
+
it "delegates ConditionVariable" do
|
59
|
+
q = Empathy::ConditionVariable.new()
|
60
|
+
q.should be_kind_of(condition_variable_class)
|
61
|
+
end
|
62
|
+
|
63
|
+
it "delegates Mutex" do
|
64
|
+
q = Empathy::Mutex.new()
|
65
|
+
q.should be_kind_of(mutex_class)
|
66
|
+
end
|
67
|
+
|
68
|
+
it "delegates Kernel.sleep" do
|
69
|
+
Empathy::Kernel.singleton_methods.should include(:sleep)
|
70
|
+
end
|
71
|
+
|
72
|
+
it "rescues errors" do
|
73
|
+
lambda do
|
74
|
+
begin
|
75
|
+
raise error_class
|
76
|
+
rescue Empathy::ThreadError
|
77
|
+
# do nothing
|
78
|
+
end
|
79
|
+
end.should_not raise_error
|
80
|
+
end
|
81
|
+
end
|
82
|
+
|
83
|
+
context "in eventmachine" do
|
84
|
+
around(:each) do |example|
|
85
|
+
Empathy.run { example.run }
|
86
|
+
end
|
87
|
+
|
88
|
+
let (:thread_class) { Empathy::EM::Thread }
|
89
|
+
let (:queue_class) { Empathy::EM::Queue }
|
90
|
+
let (:condition_variable_class) { Empathy::EM::ConditionVariable }
|
91
|
+
let (:mutex_class) { Empathy::EM::Mutex }
|
92
|
+
let (:error_class) { ::FiberError }
|
93
|
+
|
94
|
+
it "delegates to Empathy::EM classes" do
|
95
|
+
Empathy.run do
|
96
|
+
Empathy.event_machine?.should be_true
|
97
|
+
t = Empathy::EmTest.new
|
98
|
+
t.should be_kind_of(Empathy::EM::EmTest)
|
99
|
+
t.whoami.should == :em_test
|
100
|
+
Empathy::EmTest.test_class_method.should == :em_test_class_method
|
101
|
+
Empathy::EmTest.test_class_method(:em_hello).should == :em_hello
|
102
|
+
Empathy::EmTest.test_class_method() { :em_with_block }.should == :em_with_block
|
103
|
+
end
|
104
|
+
end
|
105
|
+
|
106
|
+
include_examples "empathy_delegation"
|
107
|
+
end
|
108
|
+
|
109
|
+
context "outside eventmachine" do
|
110
|
+
let (:thread_class) { ::Thread }
|
111
|
+
let (:queue_class) { ::Queue }
|
112
|
+
let (:condition_variable_class) { ::ConditionVariable }
|
113
|
+
let (:mutex_class) { ::Mutex }
|
114
|
+
let (:error_class) { ::ThreadError }
|
115
|
+
|
116
|
+
it "delegate to ruby top level classes" do
|
117
|
+
EventMachine.reactor_running?.should be_false
|
118
|
+
Empathy.event_machine?.should be_false
|
119
|
+
t = Empathy::EmTest.new
|
120
|
+
t.should be_kind_of(EmTest)
|
121
|
+
t.whoami.should == :test
|
122
|
+
Empathy::EmTest.test_class_method.should == :test_class_method
|
123
|
+
Empathy::EmTest.test_class_method(:hello).should == :hello
|
124
|
+
Empathy::EmTest.test_class_method() { :with_block }.should == :with_block
|
125
|
+
end
|
126
|
+
|
127
|
+
include_examples "empathy_delegation"
|
128
|
+
end
|
129
|
+
end
|
@@ -0,0 +1,79 @@
|
|
1
|
+
require 'spec_helper'
|
2
|
+
|
3
|
+
module TestReactorLibrary
|
4
|
+
def self.test_thread_error
|
5
|
+
raise ::FiberError, "oops"
|
6
|
+
rescue ThreadError
|
7
|
+
:rescued
|
8
|
+
end
|
9
|
+
end
|
10
|
+
|
11
|
+
Empathy::EM.empathise(TestReactorLibrary)
|
12
|
+
|
13
|
+
module TestLibrary
|
14
|
+
def self.test_thread_error
|
15
|
+
begin
|
16
|
+
raise ::FiberError, "fiber error"
|
17
|
+
rescue ThreadError
|
18
|
+
end
|
19
|
+
|
20
|
+
begin
|
21
|
+
raise ::ThreadError, "thread error"
|
22
|
+
rescue ThreadError
|
23
|
+
end
|
24
|
+
:ok
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
Empathy.empathise(TestLibrary)
|
29
|
+
|
30
|
+
shared_examples_for "Empathy.empathise" do
|
31
|
+
it "rescues thread and fiber exceptions" do
|
32
|
+
TestLibrary.test_thread_error.should == :ok
|
33
|
+
end
|
34
|
+
end
|
35
|
+
|
36
|
+
describe "Empathy.empathise" do
|
37
|
+
|
38
|
+
it "defines constants in Library namespace" do
|
39
|
+
TestLibrary::Thread.should == Empathy::Thread
|
40
|
+
TestLibrary::Queue.should == Empathy::Queue
|
41
|
+
TestLibrary::ConditionVariable.should == Empathy::ConditionVariable
|
42
|
+
TestLibrary::Mutex.should == Empathy::Mutex
|
43
|
+
TestLibrary::ThreadError.should == Empathy::ThreadError
|
44
|
+
end
|
45
|
+
|
46
|
+
context "in reactor" do
|
47
|
+
around :each do |example|
|
48
|
+
Empathy.run { example.run }
|
49
|
+
end
|
50
|
+
|
51
|
+
include_examples "Empathy.empathise"
|
52
|
+
end
|
53
|
+
|
54
|
+
context "outside reactor" do
|
55
|
+
include_examples "Empathy.empathise"
|
56
|
+
end
|
57
|
+
|
58
|
+
end
|
59
|
+
|
60
|
+
describe "Empathy::EM.empathise" do
|
61
|
+
|
62
|
+
it "defines constants in Library namespace" do
|
63
|
+
TestReactorLibrary::Thread.should == Empathy::EM::Thread
|
64
|
+
TestReactorLibrary::Queue.should == Empathy::EM::Queue
|
65
|
+
TestReactorLibrary::ConditionVariable.should == Empathy::EM::ConditionVariable
|
66
|
+
TestReactorLibrary::Mutex.should == Empathy::EM::Mutex
|
67
|
+
TestReactorLibrary::ThreadError.should == FiberError
|
68
|
+
end
|
69
|
+
|
70
|
+
context "in reactor" do
|
71
|
+
around :each do |example|
|
72
|
+
Empathy.run { example.run }
|
73
|
+
end
|
74
|
+
|
75
|
+
it "rescues fiber errors" do
|
76
|
+
TestReactorLibrary.test_thread_error.should == :rescued
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|