pigeon 0.1.0 → 0.2.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.
data/README.rdoc CHANGED
@@ -48,7 +48,6 @@ An example would look like:
48
48
  engine = engine
49
49
 
50
50
  options = {
51
- :dir_mode => :normal,
52
51
  :dir => engine.pid_dir,
53
52
  :debug => true, # ((ENV['RAILS_ENV'] == 'production') ? ENV['PINGITY_DEBUG'] : true),
54
53
  :modules => [ ]
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.1.0
1
+ 0.2.0
data/bin/launcher.example CHANGED
@@ -4,7 +4,6 @@ COMMAND_NAME = 'launcher'
4
4
  engine = engine
5
5
 
6
6
  options = {
7
- :dir_mode => :normal,
8
7
  :dir => engine.pid_dir,
9
8
  :debug => true, # ((ENV['RAILS_ENV'] == 'production') ? ENV['PINGITY_DEBUG'] : true),
10
9
  :modules => [ ]
data/lib/pigeon/engine.rb CHANGED
@@ -45,7 +45,13 @@ class Pigeon::Engine
45
45
 
46
46
  def self.launch_with_options(options = nil)
47
47
  EventMachine.run do
48
- new(options_with_defaults(options)).run
48
+ engine = new(options_with_defaults(options))
49
+
50
+ Signal.trap('INT') do
51
+ engine.terminate
52
+ end
53
+
54
+ engine.run
49
55
  end
50
56
  end
51
57
 
@@ -63,29 +69,37 @@ class Pigeon::Engine
63
69
  end
64
70
 
65
71
  pid_file(options).create!(pid)
66
- yield(pid.to_i)
72
+
73
+ yield(pid) if (block_given?)
74
+
75
+ pid
67
76
  end
68
77
 
69
78
  def self.run(options = nil)
70
- yield($$)
79
+ yield($$) if (block_given?)
80
+
71
81
  launch_with_options((options || { }).merge(:foreground => true))
72
82
  end
73
83
 
74
84
  def self.stop(options = nil)
75
85
  pf = pid_file(options)
76
- pid = pf.contents
86
+ pid = pf.running
77
87
 
78
88
  if (pid)
79
89
  begin
80
- Process.kill('QUIT', pid)
90
+ Process.kill('INT', pid)
81
91
  rescue Errno::ESRCH
82
92
  # No such process exception
83
93
  pid = nil
84
94
  end
85
95
  pf.remove!
86
96
  end
97
+
98
+ pid = pid.to_i if (pid)
87
99
 
88
- yield(pid)
100
+ yield(pid) if (block_given?)
101
+
102
+ pid
89
103
  end
90
104
 
91
105
  def self.restart(options = nil)
@@ -94,7 +108,11 @@ class Pigeon::Engine
94
108
  end
95
109
 
96
110
  def self.status(options = nil)
97
- yield(pid_file(options).contents)
111
+ pid = pid_file(options).running
112
+
113
+ yield(pid) if (block_given?)
114
+
115
+ pid
98
116
  end
99
117
 
100
118
  def self.sql_logger
@@ -192,7 +210,9 @@ class Pigeon::Engine
192
210
 
193
211
  # Shuts down the engine.
194
212
  def terminate
213
+ run_chain(:before_stop)
195
214
  EventMachine.stop_event_loop
215
+ run_chain(:after_stop)
196
216
  end
197
217
 
198
218
  # Used to queue a block for immediate processing on a background thread.
@@ -1,5 +1,9 @@
1
1
  class Pigeon::Pidfile
2
2
  # == Constants ============================================================
3
+
4
+ # == Properties ===========================================================
5
+
6
+ attr_reader :path
3
7
 
4
8
  # == Class Methods ========================================================
5
9
 
@@ -11,7 +15,19 @@ class Pigeon::Pidfile
11
15
  @path += '.pid' unless (@path.match(/\./))
12
16
  end
13
17
 
14
- def contents
18
+ def running?
19
+ !!self.running
20
+ end
21
+
22
+ def running
23
+ pid = self.saved_pid
24
+
25
+ (pid and Process.kill(0, pid)) ? pid : nil
26
+ rescue Errno::ESRCH
27
+ nil
28
+ end
29
+
30
+ def saved_pid
15
31
  File.read(@path).to_i
16
32
  rescue Errno::ENOENT
17
33
  nil
@@ -19,17 +35,17 @@ class Pigeon::Pidfile
19
35
 
20
36
  def create!(pid = nil)
21
37
  open(@path, 'w') do |fh|
22
- fh.puts pid || $$
38
+ fh.puts(pid || $$)
23
39
  end
24
40
  end
25
41
 
26
42
  def remove!
27
- return unless (exists?)
43
+ return unless (exist?)
28
44
 
29
45
  File.unlink(@path)
30
46
  end
31
47
 
32
- def exists?
48
+ def exist?
33
49
  File.exist?(@path)
34
50
  end
35
51
  end
data/pigeon.gemspec CHANGED
@@ -5,11 +5,11 @@
5
5
 
6
6
  Gem::Specification.new do |s|
7
7
  s.name = %q{pigeon}
8
- s.version = "0.1.0"
8
+ s.version = "0.2.0"
9
9
 
10
10
  s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
11
11
  s.authors = ["tadman"]
12
- s.date = %q{2010-10-01}
12
+ s.date = %q{2010-10-05}
13
13
  s.default_executable = %q{launcher.example}
14
14
  s.description = %q{Pigeon is a simple way to get started building an EventMachine engine that's intended to run as a background job.}
15
15
  s.email = %q{github@tadman.ca}
@@ -20,8 +20,44 @@ class TestEngine < Pigeon::Engine
20
20
  end
21
21
  end
22
22
 
23
+ class ShutdownEngine < Pigeon::Engine
24
+ after_start do
25
+ self.terminate
26
+ end
27
+ end
28
+
29
+ class CallbackTestEngine < Pigeon::Engine
30
+ after_initialize do
31
+ self.track(:after_initialize)
32
+ end
33
+
34
+ before_start do
35
+ self.track(:before_start)
36
+ end
37
+
38
+ after_start do
39
+ self.track(:after_start)
40
+ end
41
+
42
+ before_stop do
43
+ self.track(:before_stop)
44
+ end
45
+
46
+ after_stop do
47
+ self.track(:after_stop)
48
+ @options[:pipe].close
49
+ end
50
+
51
+ def track(callback)
52
+ pipe = @options[:pipe]
53
+
54
+ pipe.puts(callback.to_s)
55
+ pipe.flush
56
+ end
57
+ end
58
+
23
59
  class TestPigeonEngine < Test::Unit::TestCase
24
- def test_create_subclass
60
+ def test_example_subclass
25
61
  engine_pid = nil
26
62
 
27
63
  read_fd, write_fd = IO.pipe
@@ -31,6 +67,8 @@ class TestPigeonEngine < Test::Unit::TestCase
31
67
  engine_pid = pid
32
68
  end
33
69
 
70
+ write_fd.close
71
+
34
72
  Timeout::timeout(5) do
35
73
  assert_equal "STARTED\n", read_fd.readline
36
74
  end
@@ -47,4 +85,83 @@ class TestPigeonEngine < Test::Unit::TestCase
47
85
  assert_equal nil, pid
48
86
  end
49
87
  end
88
+
89
+ def test_example_subclass_without_blocks
90
+ engine_pid = nil
91
+
92
+ read_fd, write_fd = IO.pipe
93
+
94
+ engine_pid = TestEngine.start(:pipe => write_fd)
95
+
96
+ write_fd.close
97
+
98
+ assert engine_pid
99
+
100
+ Timeout::timeout(5) do
101
+ assert_equal "STARTED\n", read_fd.readline
102
+ end
103
+
104
+ running_pid = TestEngine.status
105
+
106
+ assert_equal engine_pid, running_pid
107
+
108
+ assert_equal engine_pid, TestEngine.stop
109
+
110
+ assert_equal nil, TestEngine.status
111
+ end
112
+
113
+ def test_callbacks
114
+ engine_pid = nil
115
+
116
+ read_fd, write_fd = IO.pipe
117
+
118
+ CallbackTestEngine.start(:pipe => write_fd) do |pid|
119
+ assert pid
120
+ engine_pid = pid
121
+ end
122
+
123
+ write_fd.close
124
+
125
+ CallbackTestEngine.status do |pid|
126
+ assert_equal engine_pid, pid
127
+ end
128
+
129
+ CallbackTestEngine.stop do |pid|
130
+ assert_equal engine_pid, pid
131
+ end
132
+
133
+ CallbackTestEngine.status do |pid|
134
+ assert_equal nil, pid
135
+ end
136
+
137
+ expected_callbacks = [
138
+ :after_initialize,
139
+ :before_start,
140
+ :after_start,
141
+ :before_stop,
142
+ :after_stop
143
+ ].freeze
144
+
145
+ assert_equal expected_callbacks, read_fd.read.split(/\n/).collect(&:to_sym)
146
+ end
147
+
148
+ def test_shutdown_engine
149
+ engine_pid = nil
150
+
151
+ ShutdownEngine.start do |pid|
152
+ engine_pid = pid
153
+ end
154
+
155
+ assert engine_pid
156
+
157
+ sleep(1)
158
+
159
+ running_pid = nil
160
+
161
+ ShutdownEngine.status do |pid|
162
+ running_pid = pid
163
+ end
164
+
165
+ assert_equal nil, running_pid
166
+ end
50
167
  end
metadata CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
6
  - 0
7
- - 1
7
+ - 2
8
8
  - 0
9
- version: 0.1.0
9
+ version: 0.2.0
10
10
  platform: ruby
11
11
  authors:
12
12
  - tadman
@@ -14,7 +14,7 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-10-01 00:00:00 -04:00
17
+ date: 2010-10-05 00:00:00 -04:00
18
18
  default_executable: launcher.example
19
19
  dependencies:
20
20
  - !ruby/object:Gem::Dependency