resurrected_god 0.14.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (141) hide show
  1. checksums.yaml +7 -0
  2. data/Announce.txt +135 -0
  3. data/Gemfile +5 -0
  4. data/LICENSE +22 -0
  5. data/README.md +33 -0
  6. data/Rakefile +129 -0
  7. data/bin/god +134 -0
  8. data/doc/god.asciidoc +1592 -0
  9. data/doc/intro.asciidoc +20 -0
  10. data/ext/god/.gitignore +5 -0
  11. data/ext/god/extconf.rb +56 -0
  12. data/ext/god/kqueue_handler.c +133 -0
  13. data/ext/god/netlink_handler.c +182 -0
  14. data/lib/god/behavior.rb +52 -0
  15. data/lib/god/behaviors/clean_pid_file.rb +21 -0
  16. data/lib/god/behaviors/clean_unix_socket.rb +21 -0
  17. data/lib/god/behaviors/notify_when_flapping.rb +51 -0
  18. data/lib/god/cli/command.rb +268 -0
  19. data/lib/god/cli/run.rb +170 -0
  20. data/lib/god/cli/version.rb +23 -0
  21. data/lib/god/compat19.rb +33 -0
  22. data/lib/god/condition.rb +96 -0
  23. data/lib/god/conditions/always.rb +36 -0
  24. data/lib/god/conditions/complex.rb +86 -0
  25. data/lib/god/conditions/cpu_usage.rb +80 -0
  26. data/lib/god/conditions/degrading_lambda.rb +52 -0
  27. data/lib/god/conditions/disk_usage.rb +32 -0
  28. data/lib/god/conditions/file_mtime.rb +28 -0
  29. data/lib/god/conditions/file_touched.rb +44 -0
  30. data/lib/god/conditions/flapping.rb +128 -0
  31. data/lib/god/conditions/http_response_code.rb +184 -0
  32. data/lib/god/conditions/lambda.rb +25 -0
  33. data/lib/god/conditions/memory_usage.rb +82 -0
  34. data/lib/god/conditions/process_exits.rb +66 -0
  35. data/lib/god/conditions/process_running.rb +63 -0
  36. data/lib/god/conditions/socket_responding.rb +142 -0
  37. data/lib/god/conditions/tries.rb +44 -0
  38. data/lib/god/configurable.rb +57 -0
  39. data/lib/god/contact.rb +114 -0
  40. data/lib/god/contacts/airbrake.rb +44 -0
  41. data/lib/god/contacts/campfire.rb +121 -0
  42. data/lib/god/contacts/email.rb +130 -0
  43. data/lib/god/contacts/hipchat.rb +117 -0
  44. data/lib/god/contacts/jabber.rb +75 -0
  45. data/lib/god/contacts/prowl.rb +57 -0
  46. data/lib/god/contacts/scout.rb +55 -0
  47. data/lib/god/contacts/sensu.rb +59 -0
  48. data/lib/god/contacts/slack.rb +98 -0
  49. data/lib/god/contacts/statsd.rb +46 -0
  50. data/lib/god/contacts/twitter.rb +51 -0
  51. data/lib/god/contacts/webhook.rb +74 -0
  52. data/lib/god/driver.rb +238 -0
  53. data/lib/god/errors.rb +24 -0
  54. data/lib/god/event_handler.rb +112 -0
  55. data/lib/god/event_handlers/dummy_handler.rb +13 -0
  56. data/lib/god/event_handlers/kqueue_handler.rb +17 -0
  57. data/lib/god/event_handlers/netlink_handler.rb +13 -0
  58. data/lib/god/logger.rb +109 -0
  59. data/lib/god/metric.rb +87 -0
  60. data/lib/god/process.rb +381 -0
  61. data/lib/god/registry.rb +32 -0
  62. data/lib/god/simple_logger.rb +59 -0
  63. data/lib/god/socket.rb +113 -0
  64. data/lib/god/sugar.rb +62 -0
  65. data/lib/god/sys_logger.rb +45 -0
  66. data/lib/god/system/portable_poller.rb +42 -0
  67. data/lib/god/system/process.rb +50 -0
  68. data/lib/god/system/slash_proc_poller.rb +92 -0
  69. data/lib/god/task.rb +552 -0
  70. data/lib/god/timeline.rb +25 -0
  71. data/lib/god/trigger.rb +43 -0
  72. data/lib/god/version.rb +4 -0
  73. data/lib/god/watch.rb +340 -0
  74. data/lib/god.rb +777 -0
  75. data/test/configs/child_events/child_events.god +44 -0
  76. data/test/configs/child_events/simple_server.rb +3 -0
  77. data/test/configs/child_polls/child_polls.god +37 -0
  78. data/test/configs/child_polls/simple_server.rb +12 -0
  79. data/test/configs/complex/complex.god +59 -0
  80. data/test/configs/complex/simple_server.rb +3 -0
  81. data/test/configs/contact/contact.god +118 -0
  82. data/test/configs/contact/simple_server.rb +3 -0
  83. data/test/configs/daemon_events/daemon_events.god +37 -0
  84. data/test/configs/daemon_events/simple_server.rb +8 -0
  85. data/test/configs/daemon_events/simple_server_stop.rb +11 -0
  86. data/test/configs/daemon_polls/daemon_polls.god +17 -0
  87. data/test/configs/daemon_polls/simple_server.rb +6 -0
  88. data/test/configs/degrading_lambda/degrading_lambda.god +31 -0
  89. data/test/configs/degrading_lambda/tcp_server.rb +15 -0
  90. data/test/configs/keepalive/keepalive.god +9 -0
  91. data/test/configs/keepalive/keepalive.rb +12 -0
  92. data/test/configs/lifecycle/lifecycle.god +25 -0
  93. data/test/configs/matias/matias.god +50 -0
  94. data/test/configs/real.rb +59 -0
  95. data/test/configs/running_load/running_load.god +16 -0
  96. data/test/configs/stop_options/simple_server.rb +12 -0
  97. data/test/configs/stop_options/stop_options.god +39 -0
  98. data/test/configs/stress/simple_server.rb +3 -0
  99. data/test/configs/stress/stress.god +15 -0
  100. data/test/configs/task/logs/.placeholder +0 -0
  101. data/test/configs/task/task.god +26 -0
  102. data/test/configs/test.rb +61 -0
  103. data/test/configs/usr1_trapper.rb +10 -0
  104. data/test/helper.rb +172 -0
  105. data/test/suite.rb +6 -0
  106. data/test/test_airbrake.rb +14 -0
  107. data/test/test_behavior.rb +18 -0
  108. data/test/test_campfire.rb +22 -0
  109. data/test/test_condition.rb +52 -0
  110. data/test/test_conditions_disk_usage.rb +50 -0
  111. data/test/test_conditions_http_response_code.rb +109 -0
  112. data/test/test_conditions_process_running.rb +40 -0
  113. data/test/test_conditions_socket_responding.rb +176 -0
  114. data/test/test_conditions_tries.rb +67 -0
  115. data/test/test_contact.rb +109 -0
  116. data/test/test_driver.rb +26 -0
  117. data/test/test_email.rb +34 -0
  118. data/test/test_event_handler.rb +82 -0
  119. data/test/test_god.rb +710 -0
  120. data/test/test_god_system.rb +201 -0
  121. data/test/test_handlers_kqueue_handler.rb +16 -0
  122. data/test/test_hipchat.rb +23 -0
  123. data/test/test_jabber.rb +29 -0
  124. data/test/test_logger.rb +55 -0
  125. data/test/test_metric.rb +74 -0
  126. data/test/test_process.rb +263 -0
  127. data/test/test_prowl.rb +15 -0
  128. data/test/test_registry.rb +15 -0
  129. data/test/test_sensu.rb +11 -0
  130. data/test/test_slack.rb +57 -0
  131. data/test/test_socket.rb +34 -0
  132. data/test/test_statsd.rb +22 -0
  133. data/test/test_sugar.rb +42 -0
  134. data/test/test_system_portable_poller.rb +17 -0
  135. data/test/test_system_process.rb +30 -0
  136. data/test/test_task.rb +246 -0
  137. data/test/test_timeline.rb +37 -0
  138. data/test/test_trigger.rb +63 -0
  139. data/test/test_watch.rb +286 -0
  140. data/test/test_webhook.rb +22 -0
  141. metadata +476 -0
data/test/test_god.rb ADDED
@@ -0,0 +1,710 @@
1
+ require File.dirname(__FILE__) + '/helper'
2
+ class TestGod < MiniTest::Test
3
+ def setup
4
+ God::Socket.stubs(:new).returns(true)
5
+ God.stubs(:setup).returns(true)
6
+ God.stubs(:validater).returns(true)
7
+ God.reset
8
+ God.pid_file_directory = '/var/run/god'
9
+ end
10
+
11
+ def teardown
12
+ God.main && God.main.kill
13
+ if God.watches
14
+ God.watches.each do |k, w|
15
+ w.driver.thread.kill
16
+ end
17
+ end
18
+ God.reset
19
+ #Some of the tests in this file intentionally set pid_file_directory to an invalid value
20
+ #This can cause a later test failure since God will call abort if pid_file_directory is not writable
21
+ God.pid_file_directory = '~/.god/pids'
22
+ end
23
+
24
+ # applog
25
+
26
+ def test_applog
27
+ LOG.expects(:log).with(nil, :debug, 'foo')
28
+ applog(nil, :debug, 'foo')
29
+ end
30
+
31
+ # internal_init
32
+
33
+ def test_init_should_initialize_watches_to_empty_array
34
+ God.internal_init { }
35
+ assert_equal Hash.new, God.watches
36
+ end
37
+
38
+ # # init
39
+
40
+ def test_pid_file_directory_should_abort_if_called_after_watch
41
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
42
+ assert_abort do
43
+ God.pid_file_directory = 'foo'
44
+ end
45
+ end
46
+
47
+ # pid_file_directory
48
+
49
+ def test_pid_file_directory_should_return_default_if_not_set_explicitly
50
+ God.internal_init
51
+ assert_equal '/var/run/god', God.pid_file_directory
52
+ end
53
+
54
+ def test_pid_file_directory_equals_should_set
55
+ God.pid_file_directory = '/foo'
56
+ God.internal_init
57
+ assert_equal '/foo', God.pid_file_directory
58
+ end
59
+
60
+ # watch
61
+
62
+ def test_watch_should_get_stored
63
+ watch = nil
64
+ God.watch do |w|
65
+ w.name = 'foo'
66
+ w.start = 'bar'
67
+ watch = w
68
+ end
69
+
70
+ assert_equal 1, God.watches.size
71
+ assert_equal watch, God.watches.values.first
72
+
73
+ assert_equal 0, God.groups.size
74
+ end
75
+
76
+ def test_watch_should_get_stored_in_pending_watches
77
+ watch = nil
78
+ God.watch do |w|
79
+ w.name = 'foo'
80
+ w.start = 'bar'
81
+ watch = w
82
+ end
83
+
84
+ assert_equal 1, God.pending_watches.size
85
+ assert_equal watch, God.pending_watches.first
86
+ end
87
+
88
+ def test_watch_should_register_processes
89
+ assert_nil God.registry['foo']
90
+ God.watch do |w|
91
+ w.name = 'foo'
92
+ w.start = 'bar'
93
+ end
94
+ assert_kind_of God::Process, God.registry['foo']
95
+ end
96
+
97
+ def test_watch_should_get_stored_by_group
98
+ a = nil
99
+
100
+ God.watch do |w|
101
+ a = w
102
+ w.name = 'foo'
103
+ w.start = 'bar'
104
+ w.group = 'test'
105
+ end
106
+
107
+ assert_equal({'test' => [a]}, God.groups)
108
+ end
109
+
110
+ def test_watches_should_get_stored_by_group
111
+ a = nil
112
+ b = nil
113
+
114
+ God.watch do |w|
115
+ a = w
116
+ w.name = 'foo'
117
+ w.start = 'bar'
118
+ w.group = 'test'
119
+ end
120
+
121
+ God.watch do |w|
122
+ b = w
123
+ w.name = 'bar'
124
+ w.start = 'baz'
125
+ w.group = 'test'
126
+ end
127
+
128
+ assert_equal({'test' => [a, b]}, God.groups)
129
+ end
130
+
131
+ def test_watch_should_allow_multiple_watches
132
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
133
+
134
+ assert_nothing_raised do
135
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
136
+ end
137
+ end
138
+
139
+ def test_watch_should_disallow_duplicate_watch_names
140
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
141
+
142
+ assert_abort do
143
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
144
+ end
145
+ end
146
+
147
+ def test_watch_should_disallow_identical_watch_and_group_names
148
+ God.watch { |w| w.name = 'foo'; w.group = 'bar'; w.start = 'bar' }
149
+
150
+ assert_abort do
151
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
152
+ end
153
+ end
154
+
155
+ def test_watch_should_disallow_identical_watch_and_group_names_other_way
156
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
157
+
158
+ assert_abort do
159
+ God.watch { |w| w.name = 'foo'; w.group = 'bar'; w.start = 'bar' }
160
+ end
161
+ end
162
+
163
+ def test_watch_should_unwatch_new_watch_if_running_and_duplicate_watch
164
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
165
+ God.running = true
166
+
167
+ assert_nothing_raised do
168
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
169
+ end
170
+ end
171
+
172
+ # unwatch
173
+
174
+ def test_unwatch_should_unmonitor_watch
175
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
176
+ w = God.watches['bar']
177
+ w.state = :up
178
+ w.expects(:unmonitor)
179
+ God.unwatch(w)
180
+ end
181
+
182
+ def test_unwatch_should_unregister_watch
183
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
184
+ w = God.watches['bar']
185
+ w.expects(:unregister!)
186
+ God.unwatch(w)
187
+ end
188
+
189
+ def test_unwatch_should_remove_same_name_watches
190
+ God.watch { |w| w.name = 'bar'; w.start = 'bar' }
191
+ w = God.watches['bar']
192
+ God.unwatch(w)
193
+ assert_equal 0, God.watches.size
194
+ end
195
+
196
+ def test_unwatch_should_remove_from_group
197
+ God.watch do |w|
198
+ w.name = 'bar'
199
+ w.start = 'baz'
200
+ w.group = 'test'
201
+ end
202
+ w = God.watches['bar']
203
+ God.unwatch(w)
204
+ assert !God.groups[w.group].include?(w)
205
+ end
206
+
207
+ # contact
208
+
209
+ def test_contact_should_ensure_init_is_called
210
+ God.contact(:fake_contact) { |c| c.name = 'tom' }
211
+ assert God.inited
212
+ end
213
+
214
+ def test_contact_should_abort_on_invalid_contact_kind
215
+ assert_abort do
216
+ God.contact(:foo) { |c| c.name = 'tom' }
217
+ end
218
+ end
219
+
220
+ def test_contact_should_create_and_store_contact
221
+ contact = nil
222
+ God.contact(:fake_contact) { |c| c.name = 'tom'; contact = c }
223
+ assert_equal({"tom" => contact}, God.contacts)
224
+ end
225
+
226
+ def test_contact_should_add_to_group
227
+ God.contact(:fake_contact) { |c| c.name = 'tom'; c.group = 'devs' }
228
+ God.contact(:fake_contact) { |c| c.name = 'chris'; c.group = 'devs' }
229
+ assert_equal 2, God.contacts.size
230
+ assert_equal 1, God.contact_groups.size
231
+ end
232
+
233
+ def test_contact_should_abort_on_no_name
234
+ assert_abort do
235
+ God.contact(:fake_contact) { |c| }
236
+ end
237
+ end
238
+
239
+ def test_contact_should_abort_on_duplicate_contact_name
240
+ God.contact(:fake_contact) { |c| c.name = 'tom' }
241
+ assert_nothing_raised do
242
+ God.contact(:fake_contact) { |c| c.name = 'tom' }
243
+ end
244
+ end
245
+
246
+ def test_contact_should_abort_on_contact_with_same_name_as_group
247
+ God.contact(:fake_contact) { |c| c.name = 'tom'; c.group = 'devs' }
248
+ assert_nothing_raised do
249
+ God.contact(:fake_contact) { |c| c.name = 'devs' }
250
+ end
251
+ end
252
+
253
+ def test_contact_should_abort_on_contact_with_same_group_as_name
254
+ God.contact(:fake_contact) { |c| c.name = 'tom' }
255
+ assert_abort do
256
+ God.contact(:fake_contact) { |c| c.name = 'chris'; c.group = 'tom' }
257
+ end
258
+ end
259
+
260
+ def test_contact_should_abort_if_contact_is_invalid
261
+ assert_abort do
262
+ God.contact(:fake_contact) do |c|
263
+ c.name = 'tom'
264
+ c.stubs(:valid?).returns(false)
265
+ end
266
+ end
267
+ end
268
+
269
+ # control
270
+
271
+ def test_control_should_monitor_on_start
272
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
273
+
274
+ w = God.watches['foo']
275
+ w.expects(:monitor)
276
+ God.control('foo', 'start')
277
+ end
278
+
279
+ def test_control_should_move_to_restart_on_restart
280
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
281
+
282
+ w = God.watches['foo']
283
+ w.expects(:move).with(:restart)
284
+ God.control('foo', 'restart')
285
+ end
286
+
287
+ def test_control_should_unmonitor_and_stop_on_stop
288
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
289
+
290
+ w = God.watches['foo']
291
+ w.state = :up
292
+ w.expects(:unmonitor).returns(w)
293
+ w.expects(:action).with(:stop)
294
+ God.control('foo', 'stop')
295
+ end
296
+
297
+ def test_control_should_unmonitor_on_unmonitor
298
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
299
+
300
+ w = God.watches['foo']
301
+ w.state = :up
302
+ w.expects(:unmonitor).returns(w)
303
+ God.control('foo', 'unmonitor')
304
+ end
305
+
306
+ def test_control_should_unwatch_on_remove
307
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
308
+
309
+ w = God.watches['foo']
310
+ w.state = :up
311
+ God.expects(:unwatch)
312
+ God.control('foo', 'remove')
313
+ end
314
+
315
+ def test_control_should_raise_on_invalid_command
316
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
317
+
318
+ assert_raises InvalidCommandError do
319
+ God.control('foo', 'invalid')
320
+ end
321
+ end
322
+
323
+ def test_control_should_operate_on_each_watch_in_group
324
+ God.watch do |w|
325
+ w.name = 'foo1'
326
+ w.start = 'go'
327
+ w.group = 'bar'
328
+ end
329
+
330
+ God.watch do |w|
331
+ w.name = 'foo2'
332
+ w.start = 'go'
333
+ w.group = 'bar'
334
+ end
335
+
336
+ God.watch do |w|
337
+ w.name = 'bar1'
338
+ w.start = 'go'
339
+ w.group = 'foo'
340
+ end
341
+
342
+ God.watches['foo1'].expects(:monitor)
343
+ God.watches['foo2'].expects(:monitor)
344
+ God.watches['bar1'].expects(:monitor).never
345
+
346
+ God.control('bar', 'start')
347
+ end
348
+
349
+ def test_control_should_operate_on_all_watches_on_nil
350
+ God.watch do |w|
351
+ w.name = 'foo1'
352
+ w.start = 'go'
353
+ w.group = 'foo'
354
+ end
355
+
356
+ God.watch do |w|
357
+ w.name = 'foo2'
358
+ w.start = 'go'
359
+ w.group = 'foo'
360
+ end
361
+
362
+ God.watch do |w|
363
+ w.name = 'bar1'
364
+ w.start = 'go'
365
+ w.group = 'bar'
366
+ end
367
+
368
+ God.watches['foo1'].expects(:monitor)
369
+ God.watches['foo2'].expects(:monitor)
370
+ God.watches['bar1'].expects(:monitor)
371
+
372
+ God.control(nil, 'start')
373
+ end
374
+
375
+ def test_control_should_operate_on_all_watches_on_empty_string
376
+ God.watch do |w|
377
+ w.name = 'foo1'
378
+ w.start = 'go'
379
+ w.group = 'foo'
380
+ end
381
+
382
+ God.watch do |w|
383
+ w.name = 'foo2'
384
+ w.start = 'go'
385
+ w.group = 'foo'
386
+ end
387
+
388
+ God.watch do |w|
389
+ w.name = 'bar1'
390
+ w.start = 'go'
391
+ w.group = 'bar'
392
+ end
393
+
394
+ God.watches['foo1'].expects(:monitor)
395
+ God.watches['foo2'].expects(:monitor)
396
+ God.watches['bar1'].expects(:monitor)
397
+
398
+ God.control('', 'start')
399
+ end
400
+
401
+
402
+ # stop_all
403
+
404
+ # terminate
405
+
406
+ def test_terminate_should_exit
407
+ God.pid = nil
408
+ FileUtils.expects(:rm_f).never
409
+ God.expects(:exit!)
410
+ God.terminate
411
+ end
412
+
413
+ def test_terminate_should_delete_pid
414
+ God.pid = '/foo/bar'
415
+ FileUtils.expects(:rm_f).with("/foo/bar")
416
+ God.expects(:exit!)
417
+ God.terminate
418
+ end
419
+
420
+ # status
421
+
422
+ def test_status_should_show_state
423
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
424
+
425
+ w = God.watches['foo']
426
+ w.state = :up
427
+ assert_equal({'foo' => {:state => :up, :group => nil}}, God.status)
428
+ end
429
+
430
+ def test_status_should_show_state_with_group
431
+ God.watch { |w| w.name = 'foo'; w.start = 'bar'; w.group = 'g' }
432
+
433
+ w = God.watches['foo']
434
+ w.state = :up
435
+ assert_equal({'foo' => {:state => :up, :group => 'g'}}, God.status)
436
+ end
437
+
438
+ def test_status_should_show_unmonitored_for_nil_state
439
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
440
+
441
+ w = God.watches['foo']
442
+ assert_equal({'foo' => {:state => :unmonitored, :group => nil}}, God.status)
443
+ end
444
+
445
+ # running_log
446
+
447
+ def test_running_log_should_call_watch_log_since_on_main_log
448
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
449
+ t = Time.now
450
+ LOG.expects(:watch_log_since).with('foo', t)
451
+ God.running_log('foo', t)
452
+ end
453
+
454
+ def test_running_log_should_raise_on_unknown_watch
455
+ God.internal_init
456
+ assert_raises(NoSuchWatchError) do
457
+ God.running_log('foo', Time.now)
458
+ end
459
+ end
460
+
461
+ # running_load
462
+
463
+ def test_running_load_should_eval_code
464
+ code = <<-EOF
465
+ God.watch do |w|
466
+ w.name = 'foo'
467
+ w.start = 'go'
468
+ end
469
+ EOF
470
+
471
+ God.running_load(code, '/foo/bar.god')
472
+
473
+ assert_equal 1, God.watches.size
474
+ end
475
+
476
+ def test_running_load_should_monitor_new_watches
477
+ code = <<-EOF
478
+ God.watch do |w|
479
+ w.name = 'foo'
480
+ w.start = 'go'
481
+ end
482
+ EOF
483
+
484
+ Watch.any_instance.expects(:monitor)
485
+ God.running_load(code, '/foo/bar.god')
486
+ end
487
+
488
+ def test_running_load_should_not_monitor_new_watches_with_autostart_false
489
+ code = <<-EOF
490
+ God.watch do |w|
491
+ w.name = 'foo'
492
+ w.start = 'go'
493
+ w.autostart = false
494
+ end
495
+ EOF
496
+
497
+ Watch.any_instance.expects(:monitor).never
498
+ God.running_load(code, '/foo/bar.god')
499
+ end
500
+
501
+ def test_running_load_should_return_array_of_affected_watches
502
+ code = <<-EOF
503
+ God.watch do |w|
504
+ w.name = 'foo'
505
+ w.start = 'go'
506
+ end
507
+ EOF
508
+
509
+ w = nil
510
+ w, e = *God.running_load(code, '/foo/bar.god')
511
+ assert_equal 1, w.size
512
+ assert_equal 'foo', w.first
513
+ end
514
+
515
+ def test_running_load_should_clear_pending_watches
516
+ code = <<-EOF
517
+ God.watch do |w|
518
+ w.name = 'foo'
519
+ w.start = 'go'
520
+ end
521
+ EOF
522
+
523
+ God.running_load(code, '/foo/bar.god')
524
+ assert_equal 0, God.pending_watches.size
525
+ end
526
+
527
+ def test_running_load_with_stop
528
+ code_one = <<-EOF
529
+ God.watch do |w|
530
+ w.name = 'foo'
531
+ w.start = 'go'
532
+ end
533
+ EOF
534
+
535
+ code_two = <<-EOF
536
+ God.watch do |w|
537
+ w.name = 'bar'
538
+ w.start = 'go'
539
+ end
540
+ EOF
541
+
542
+ a, e, r = *God.running_load(code_one, '/foo/one.god', 'stop')
543
+
544
+ assert_equal 1, a.size
545
+ assert_equal 0, r.size
546
+
547
+ a, e, r = *God.running_load(code_two, '/foo/two.god', 'stop')
548
+
549
+ assert_equal 1, a.size
550
+ assert_equal 1, r.size
551
+ end
552
+
553
+ def test_running_load_with_remove
554
+ code_one = <<-EOF
555
+ God.watch do |w|
556
+ w.name = 'foo'
557
+ w.start = 'go'
558
+ end
559
+ EOF
560
+
561
+ code_two = <<-EOF
562
+ God.watch do |w|
563
+ w.name = 'bar'
564
+ w.start = 'go'
565
+ end
566
+ EOF
567
+
568
+ a, e, r = *God.running_load(code_one, '/foo/one.god', 'remove')
569
+
570
+ assert_equal 1, a.size
571
+ assert_equal 0, r.size
572
+
573
+ a, e, r = *God.running_load(code_two, '/foo/two.god', 'remove')
574
+
575
+ assert_equal 1, a.size
576
+ assert_equal 1, r.size
577
+ end
578
+
579
+ def test_running_load_with_leave
580
+ code_one = <<-EOF
581
+ God.watch do |w|
582
+ w.name = 'foo'
583
+ w.start = 'go'
584
+ end
585
+ EOF
586
+
587
+ code_two = <<-EOF
588
+ God.watch do |w|
589
+ w.name = 'bar'
590
+ w.start = 'go'
591
+ end
592
+ EOF
593
+
594
+ a, e, r = *God.running_load(code_one, '/foo/one.god', 'leave')
595
+
596
+ assert_equal 1, a.size
597
+ assert_equal 0, r.size
598
+
599
+ a, e, r = *God.running_load(code_two, '/foo/two.god', 'leave')
600
+
601
+ assert_equal 1, a.size
602
+ assert_equal 0, r.size
603
+ end
604
+
605
+ # load
606
+
607
+ def test_load_should_collect_and_load_globbed_path
608
+ Dir.expects(:[]).with('/path/to/*.thing').returns(['a', 'b'])
609
+ Kernel.expects(:load).with('a').once
610
+ Kernel.expects(:load).with('b').once
611
+ God.load('/path/to/*.thing')
612
+ end
613
+
614
+ # start
615
+
616
+ def test_start_should_kick_off_a_server_instance
617
+ God::Socket.expects(:new).returns(true)
618
+ God.start
619
+ end
620
+
621
+ def test_start_should_begin_monitoring_autostart_watches
622
+ God.watch do |w|
623
+ w.name = 'foo'
624
+ w.start = 'go'
625
+ end
626
+
627
+ Watch.any_instance.expects(:monitor).once
628
+ God.start
629
+ end
630
+
631
+ def test_start_should_not_begin_monitoring_non_autostart_watches
632
+ God.watch do |w|
633
+ w.name = 'foo'
634
+ w.start = 'go'
635
+ w.autostart = false
636
+ end
637
+
638
+ Watch.any_instance.expects(:monitor).never
639
+ God.start
640
+ end
641
+
642
+ def test_start_should_get_and_join_timer
643
+ God.watch { |w| w.name = 'foo'; w.start = 'bar' }
644
+ God.start
645
+ end
646
+
647
+ # at_exit
648
+
649
+ def test_at_exit_should_call_start
650
+ God.expects(:start).once
651
+ God.at_exit
652
+ end
653
+
654
+ # pattern_match
655
+
656
+ def test_pattern_match
657
+ list = %w{ mongrel-3000 mongrel-3001 fuzed22 fuzed fuzed2 apache mysql}
658
+
659
+ assert_equal %w{ mongrel-3000 }, God.pattern_match('m3000', list)
660
+ assert_equal %w{ mongrel-3001 }, God.pattern_match('m31', list)
661
+ assert_equal %w{ fuzed fuzed2 fuzed22}, God.pattern_match('fu', list)
662
+ assert_equal %w{ mysql }, God.pattern_match('sql', list)
663
+ end
664
+ end
665
+
666
+
667
+ # class TestGodOther < Minitest::Test
668
+ # def setup
669
+ # God::Socket.stubs(:new).returns(true)
670
+ # God.internal_init
671
+ # God.reset
672
+ # end
673
+ #
674
+ # def teardown
675
+ # God.main && God.main.kill
676
+ # end
677
+ #
678
+ # # setup
679
+ #
680
+ # def test_setup_should_create_pid_file_directory_if_it_doesnt_exist
681
+ # God.expects(:test).returns(false)
682
+ # FileUtils.expects(:mkdir_p).with(God.pid_file_directory)
683
+ # God.setup
684
+ # end
685
+ #
686
+ # def test_setup_should_raise_if_no_permissions_to_create_pid_file_directory
687
+ # God.expects(:test).returns(false)
688
+ # FileUtils.expects(:mkdir_p).raises(Errno::EACCES)
689
+ #
690
+ # assert_abort do
691
+ # God.setup
692
+ # end
693
+ # end
694
+ #
695
+ # # validate
696
+ #
697
+ # def test_validate_should_abort_if_pid_file_directory_is_unwriteable
698
+ # God.expects(:test).returns(false)
699
+ # assert_abort do
700
+ # God.validater
701
+ # end
702
+ # end
703
+ #
704
+ # def test_validate_should_not_abort_if_pid_file_directory_is_writeable
705
+ # God.expects(:test).returns(true)
706
+ # assert_nothing_raised do
707
+ # God.validater
708
+ # end
709
+ # end
710
+ # end