danielsdeleo-em-spec 0.1.3

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.
data/README.rdoc ADDED
@@ -0,0 +1,84 @@
1
+ Simple BDD API for testing asynchronous Ruby/EventMachine code
2
+ (c) 2008 Aman Gupta (tmm1)
3
+
4
+ em-spec can be used with either bacon or rspec.
5
+
6
+ =Rspec
7
+ There are two ways to use the Rspec extension. To use it as a helper, include EM::SpecHelper in your describe block. You then use the em method to wrap your evented test code. Inside the em block, you must call #done after your expectations. Everything works normally otherwise.
8
+
9
+ require "em-spec/rspec"
10
+ describe EventMachine do
11
+ include EM::SpecHelper
12
+
13
+ it "works normally when not using #em" do
14
+ 1.should == 1
15
+ end
16
+
17
+ it "makes testing evented code easy with #em" do
18
+ em do
19
+ start = Time.now
20
+
21
+ EM.add_timer(0.5){
22
+ (Time.now-start).should be_close( 0.5, 0.1 )
23
+ done
24
+ }
25
+ end
26
+ end
27
+ end
28
+ The other option is to include EM::Spec in your describe block. This will patch Rspec so that all of your examples run inside an em block automatically:
29
+ require "em-spec/rspec"
30
+ describe EventMachine do
31
+ include EM::Spec
32
+
33
+ it "requires a call to #done every time" do
34
+ 1.should == 1
35
+ done
36
+ end
37
+
38
+ it "runs test code in an em block automatically" do
39
+ start = Time.now
40
+
41
+ EM.add_timer(0.5){
42
+ (Time.now-start).should be_close( 0.5, 0.1 )
43
+ done
44
+ }
45
+ end
46
+ end
47
+
48
+ =Bacon
49
+ The API is identical to Bacon, except that you must explicitly call 'done' after all the current behavior's assertions have been made:
50
+
51
+ require 'em-spec/bacon'
52
+
53
+ EM.describe EventMachine do
54
+
55
+ should 'have timers' do
56
+ start = Time.now
57
+
58
+ EM.add_timer(0.5){
59
+ (Time.now-start).should.be.close 0.5, 0.1
60
+ done
61
+ }
62
+ end
63
+
64
+ should 'have periodic timers' do
65
+ num = 0
66
+ start = Time.now
67
+
68
+ timer = EM.add_periodic_timer(0.5){
69
+ if (num += 1) == 2
70
+ (Time.now-start).should.be.close 1.0, 0.1
71
+ EM.__send__ :cancel_timer, timer
72
+ done
73
+ end
74
+ }
75
+ end
76
+
77
+ end
78
+
79
+
80
+ Resources:
81
+
82
+ * Git repository: http://github.com/tmm1/em-spec
83
+ * Bacon: http://groups.google.com/group/comp.lang.ruby/browse_thread/thread/30b07b651b0662fd
84
+ * Initial announcement: http://groups.google.com/group/eventmachine/browse_thread/thread/8b4e7ead72f9d013
data/Rakefile ADDED
@@ -0,0 +1,18 @@
1
+ task :gem => :gemspec do
2
+ sh 'gem build em-spec.gemspec'
3
+ end
4
+
5
+ task :gemspec do
6
+
7
+ end
8
+
9
+ task :install => :gem do
10
+ sh 'sudo gem install em-spec-*.gem'
11
+ end
12
+
13
+ task :default => :gem
14
+
15
+ task :spec do
16
+ sh 'bacon test/bacon_spec.rb'
17
+ sh 'spec -f specdoc test/rspec_spec.rb test/rspec_fail_examples.rb'
18
+ end
@@ -0,0 +1,65 @@
1
+ require File.dirname(__FILE__) + '/../ext/fiber18'
2
+ require 'rubygems'
3
+ require 'eventmachine'
4
+
5
+ module EventMachine
6
+
7
+ def self.spec_backend=( backend )
8
+ @spec_backend = backend
9
+ end
10
+
11
+ def self.spec_backend
12
+ @spec_backend
13
+ end
14
+
15
+ def self.spec *args, &blk
16
+ raise ArgumentError, 'block required' unless block_given?
17
+ raise 'EventMachine reactor already running' if EM.reactor_running?
18
+
19
+ spec_backend.spec( args, blk )
20
+ end
21
+ class << self; alias :describe :spec; end
22
+
23
+ def self.bacon( *args, &block )
24
+ require File.dirname(__FILE__) + '/spec/bacon'
25
+ self.spec_backend = EventMachine::Spec::Bacon
26
+ self.spec( args, &block )
27
+ end
28
+
29
+ end
30
+
31
+ module EventMachine
32
+ module Spec
33
+ module Bacon
34
+
35
+ def self.spec( args, blk )
36
+ EM.run do
37
+ ::Bacon.summary_on_exit
38
+ ($em_spec_fiber = Fiber.new{
39
+ ::Bacon::FiberedContext.new(args.join(' '), &blk).run
40
+ EM.stop_event_loop
41
+ }).resume
42
+ end
43
+ end
44
+
45
+ end
46
+ end
47
+ end
48
+
49
+ class Bacon::FiberedContext < Bacon::Context
50
+ def it *args
51
+ super{
52
+ if block_given?
53
+ yield
54
+ Fiber.yield
55
+ end
56
+ }
57
+ end
58
+
59
+ def done
60
+ EM.next_tick{
61
+ :done.should == :done
62
+ $em_spec_fiber.resume if $em_spec_fiber
63
+ }
64
+ end
65
+ end
@@ -0,0 +1,55 @@
1
+ require 'eventmachine'
2
+ require File.dirname(__FILE__) + '/../ext/fiber18'
3
+
4
+ module EventMachine
5
+ module SpecHelper
6
+
7
+ def em(&block)
8
+
9
+ EM.run do
10
+ em_spec_exception = nil
11
+ @_em_spec_fiber = Fiber.new do
12
+ begin
13
+ block.call
14
+ rescue Exception => em_spec_exception
15
+ done
16
+ end
17
+ Fiber.yield
18
+ end
19
+
20
+ @_em_spec_fiber.resume
21
+
22
+ raise em_spec_exception if em_spec_exception
23
+ end
24
+ end
25
+
26
+ def done
27
+ EM.next_tick{
28
+ finish_em_spec_fiber
29
+ }
30
+ end
31
+
32
+ private
33
+
34
+ def finish_em_spec_fiber
35
+ EM.stop_event_loop if EM.reactor_running?
36
+ @_em_spec_fiber.resume if @_em_spec_fiber.alive?
37
+ end
38
+
39
+ end
40
+
41
+ module Spec
42
+
43
+ include SpecHelper
44
+
45
+ def instance_eval(&block)
46
+ em do
47
+ super(&block)
48
+ end
49
+ end
50
+
51
+ end
52
+
53
+ end
54
+
55
+
@@ -0,0 +1,81 @@
1
+ # Poor Man's Fiber (API compatible Thread based Fiber implementation for Ruby 1.8)
2
+ # (c) 2008 Aman Gupta (tmm1)
3
+
4
+ unless defined? Fiber
5
+ require 'thread'
6
+
7
+ class FiberError < StandardError; end
8
+
9
+ class Fiber
10
+ def initialize
11
+ raise ArgumentError, 'new Fiber requires a block' unless block_given?
12
+
13
+ @yield = Queue.new
14
+ @resume = Queue.new
15
+
16
+ @thread = Thread.new{ @yield.push [ *yield(*@resume.pop) ] }
17
+ @thread.abort_on_exception = true
18
+ @thread[:fiber] = self
19
+ end
20
+ attr_reader :thread
21
+
22
+ def alive?
23
+ @thread.alive?
24
+ end
25
+
26
+ def resume *args
27
+ raise FiberError, 'dead fiber called' unless @thread.alive?
28
+ raise FiberError, 'double resume' if @thread == Thread.current
29
+ @resume.push(args)
30
+ result = @yield.pop
31
+ result.size > 1 ? result : result.first
32
+ end
33
+
34
+ def resume!
35
+ @resume.push []
36
+ end
37
+
38
+ def yield *args
39
+ @yield.push(args)
40
+ result = @resume.pop
41
+ result.size > 1 ? result : result.first
42
+ end
43
+
44
+ def self.yield *args
45
+ raise FiberError, "can't yield from root fiber" unless fiber = Thread.current[:fiber]
46
+ fiber.yield(*args)
47
+ end
48
+
49
+ def self.current
50
+ Thread.current[:fiber] or raise FiberError, 'not inside a fiber'
51
+ end
52
+
53
+ def inspect
54
+ "#<#{self.class}:0x#{self.object_id.to_s(16)}>"
55
+ end
56
+ end
57
+ else
58
+ require 'fiber'
59
+ end
60
+
61
+ if __FILE__ == $0
62
+ f = Fiber.new{ puts 'hi'; p Fiber.yield(1); puts 'bye'; :done }
63
+ p f.resume
64
+ p f.resume(2)
65
+ end
66
+
67
+ __END__
68
+
69
+ $ ruby fbr.rb
70
+ hi
71
+ 1
72
+ 2
73
+ bye
74
+ :done
75
+
76
+ $ ruby1.9 fbr.rb
77
+ hi
78
+ 1
79
+ 2
80
+ bye
81
+ :done
@@ -0,0 +1,51 @@
1
+ require 'bacon'
2
+ require File.dirname(__FILE__) + '/../lib/em-spec/bacon'
3
+
4
+ EM.spec_backend = EventMachine::Spec::Bacon
5
+
6
+ describe 'Bacon' do
7
+ should 'work as normal outside EM.describe' do
8
+ 1.should == 1
9
+ end
10
+ end
11
+
12
+ EM.describe EventMachine do
13
+ should 'work' do
14
+ done
15
+ end
16
+
17
+ should 'have timers' do
18
+ start = Time.now
19
+
20
+ EM.add_timer(0.5){
21
+ (Time.now-start).should.be.close 0.5, 0.1
22
+ done
23
+ }
24
+ end
25
+
26
+ should 'have periodic timers' do
27
+ num = 0
28
+ start = Time.now
29
+
30
+ timer = EM.add_periodic_timer(0.5){
31
+ if (num += 1) == 2
32
+ (Time.now-start).should.be.close 1.0, 0.1
33
+ EM.__send__ :cancel_timer, timer
34
+ done
35
+ end
36
+ }
37
+ end
38
+
39
+ should 'have deferrables' do
40
+ defr = EM::DefaultDeferrable.new
41
+ defr.timeout(1)
42
+ defr.errback{
43
+ done
44
+ }
45
+ end
46
+
47
+ # it "should not block on failure" do
48
+ # 1.should == 2
49
+ # end
50
+
51
+ end
@@ -0,0 +1,18 @@
1
+ require File.dirname(__FILE__) + '/../lib/em-spec/rspec'
2
+
3
+ describe EventMachine, "when running failing examples" do
4
+ include EM::Spec
5
+
6
+ it "should not bubble failures beyond rspec" do
7
+ EM.add_timer(0.1) do
8
+ :should_not_bubble.should == :failures
9
+ done
10
+ end
11
+ end
12
+
13
+ it "should not block on failure" do
14
+ 1.should == 2
15
+ end
16
+
17
+
18
+ end
@@ -0,0 +1,71 @@
1
+ require File.dirname(__FILE__) + '/../lib/em-spec/rspec'
2
+
3
+ describe 'Rspec' do
4
+ it 'should work as normal outside EM.describe' do
5
+ 1.should == 1
6
+ end
7
+ end
8
+
9
+ describe EventMachine, "when testing with EM::SpecHelper" do
10
+ include EM::SpecHelper
11
+
12
+ it "should not require a call to done when #em is not used" do
13
+ 1.should == 1
14
+ end
15
+
16
+ it "should have timers" do
17
+ em do
18
+ start = Time.now
19
+
20
+ EM.add_timer(0.5){
21
+ (Time.now-start).should be_close( 0.5, 0.1 )
22
+ done
23
+ }
24
+ end
25
+ end
26
+ end
27
+
28
+ describe EventMachine, "when testing with EM::Spec" do
29
+ include EM::Spec
30
+
31
+ it 'should work' do
32
+ done
33
+ end
34
+
35
+ it 'should have timers' do
36
+ start = Time.now
37
+
38
+ EM.add_timer(0.5){
39
+ (Time.now-start).should be_close( 0.5, 0.1 )
40
+ done
41
+ }
42
+ end
43
+
44
+ it 'should have periodic timers' do
45
+ num = 0
46
+ start = Time.now
47
+
48
+ timer = EM.add_periodic_timer(0.5){
49
+ if (num += 1) == 2
50
+ (Time.now-start).should be_close( 1.0, 0.1 )
51
+ EM.__send__ :cancel_timer, timer
52
+ done
53
+ end
54
+ }
55
+ end
56
+
57
+ it 'should have deferrables' do
58
+ defr = EM::DefaultDeferrable.new
59
+ defr.timeout(1)
60
+ defr.errback{
61
+ done
62
+ }
63
+ end
64
+
65
+ end
66
+
67
+ describe "Rspec", "when running an example group after another group that uses EMSpec " do
68
+ it "should work normally" do
69
+ :does_not_hang.should_not be_false
70
+ end
71
+ end
metadata ADDED
@@ -0,0 +1,91 @@
1
+ --- !ruby/object:Gem::Specification
2
+ name: danielsdeleo-em-spec
3
+ version: !ruby/object:Gem::Version
4
+ version: 0.1.3
5
+ platform: ruby
6
+ authors:
7
+ - Aman Gupta
8
+ - "Lourens Naud\xC3\xA9"
9
+ - Daniel DeLeo
10
+ autorequire:
11
+ bindir: bin
12
+ cert_chain: []
13
+
14
+ date: 2009-04-20 00:00:00 -07:00
15
+ default_executable:
16
+ dependencies:
17
+ - !ruby/object:Gem::Dependency
18
+ name: eventmachine
19
+ type: :runtime
20
+ version_requirement:
21
+ version_requirements: !ruby/object:Gem::Requirement
22
+ requirements:
23
+ - - ">="
24
+ - !ruby/object:Gem::Version
25
+ version: 0.12.6
26
+ version:
27
+ - !ruby/object:Gem::Dependency
28
+ name: bacon
29
+ type: :runtime
30
+ version_requirement:
31
+ version_requirements: !ruby/object:Gem::Requirement
32
+ requirements:
33
+ - - ">="
34
+ - !ruby/object:Gem::Version
35
+ version: 1.1.0
36
+ version:
37
+ - !ruby/object:Gem::Dependency
38
+ name: rspec
39
+ type: :runtime
40
+ version_requirement:
41
+ version_requirements: !ruby/object:Gem::Requirement
42
+ requirements:
43
+ - - ">="
44
+ - !ruby/object:Gem::Version
45
+ version: 1.1.12
46
+ version:
47
+ description: Rspec and Bacon based BDD API for Ruby/EventMachine
48
+ email: em-spec@tmm1.net
49
+ executables: []
50
+
51
+ extensions: []
52
+
53
+ extra_rdoc_files: []
54
+
55
+ files:
56
+ - README.rdoc
57
+ - Rakefile
58
+ - lib/em-spec/bacon.rb
59
+ - lib/em-spec/rspec.rb
60
+ - lib/ext/fiber18.rb
61
+ - test/bacon_spec.rb
62
+ - test/rspec_spec.rb
63
+ - test/rspec_fail_examples.rb
64
+ has_rdoc: false
65
+ homepage: http://github.com/tmm1/em-spec
66
+ post_install_message:
67
+ rdoc_options: []
68
+
69
+ require_paths:
70
+ - lib
71
+ required_ruby_version: !ruby/object:Gem::Requirement
72
+ requirements:
73
+ - - ">="
74
+ - !ruby/object:Gem::Version
75
+ version: "0"
76
+ version:
77
+ required_rubygems_version: !ruby/object:Gem::Requirement
78
+ requirements:
79
+ - - ">="
80
+ - !ruby/object:Gem::Version
81
+ version: "0"
82
+ version:
83
+ requirements: []
84
+
85
+ rubyforge_project:
86
+ rubygems_version: 1.2.0
87
+ signing_key:
88
+ specification_version: 2
89
+ summary: Bacon based BDD API for Ruby/EventMachine
90
+ test_files: []
91
+