spex 0.5.2 → 0.6.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/Rakefile +1 -0
- data/VERSION +1 -1
- data/examples/postfix.rb +16 -0
- data/lib/spex.rb +6 -0
- data/lib/spex/assertions/process_assertion.rb +28 -0
- data/lib/spex/assertions/restarted_assertion.rb +22 -0
- data/lib/spex/assertions/started_assertion.rb +21 -0
- data/lib/spex/assertions/stopped_assertion.rb +20 -0
- data/lib/spex/runner.rb +9 -7
- data/test/helper.rb +18 -0
- data/test/test_modified_assertion.rb +1 -1
- data/test/test_restarted_assertion.rb +77 -0
- data/test/test_started_assertion.rb +63 -0
- data/test/test_stopped_assertion.rb +63 -0
- metadata +28 -4
data/Rakefile
CHANGED
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.6.0
|
data/examples/postfix.rb
ADDED
@@ -0,0 +1,16 @@
|
|
1
|
+
# Note: We use the more specific 'postfix/master' as the process name so
|
2
|
+
# we don't confused with spex running this file (postfix.rb)
|
3
|
+
scenario "Postfix process management" do
|
4
|
+
executing "sudo postfix start" do
|
5
|
+
assert 'postfix/master', :started => true
|
6
|
+
end
|
7
|
+
executing "sudo postfix stop" do
|
8
|
+
assert 'postfix/master', :stopped => true
|
9
|
+
end
|
10
|
+
executing "sudo postfix start" do
|
11
|
+
assert 'postfix/master', :started => true
|
12
|
+
end
|
13
|
+
executing "sudo postfix stop && sudo postfix start" do
|
14
|
+
assert 'postfix/master', :restarted => true
|
15
|
+
end
|
16
|
+
end
|
data/lib/spex.rb
CHANGED
@@ -0,0 +1,28 @@
|
|
1
|
+
module Spex
|
2
|
+
class ProcessAssertion < Assertion
|
3
|
+
|
4
|
+
def pattern
|
5
|
+
@pattern ||= target.is_a?(Regexp) ? target : Regexp.new(target)
|
6
|
+
end
|
7
|
+
|
8
|
+
def ps_executable
|
9
|
+
ps = Facter.value(:ps)
|
10
|
+
if ps && !ps.empty?
|
11
|
+
ps
|
12
|
+
else
|
13
|
+
abort "Facter does not support 'ps' fact."
|
14
|
+
end
|
15
|
+
end
|
16
|
+
|
17
|
+
def current_pid
|
18
|
+
table = IO.popen(ps_executable) { |ps| ps.readlines }
|
19
|
+
table.each do |line|
|
20
|
+
if pattern.match(line)
|
21
|
+
return line.sub(/^\s+/, '').split(/\s+/)[1]
|
22
|
+
end
|
23
|
+
end
|
24
|
+
nil
|
25
|
+
end
|
26
|
+
|
27
|
+
end
|
28
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module Spex
|
2
|
+
class RestartedAssertion < ProcessAssertion
|
3
|
+
as :restarted, 'process restart'
|
4
|
+
example "Process was restarted", "assert 'postfix', :restarted => true"
|
5
|
+
example "Process was not restarted", "assert 'postfix', :restarted => false"
|
6
|
+
|
7
|
+
def before
|
8
|
+
@before_pid = current_pid
|
9
|
+
assert @before_pid, "Process '#{target}' is not running"
|
10
|
+
end
|
11
|
+
|
12
|
+
def after
|
13
|
+
after_pid = current_pid
|
14
|
+
assert after_pid, "Process '#{target}' is not running"
|
15
|
+
if active?
|
16
|
+
assert_not_equal @before_pid, after_pid, "Process '#{target}' pid was not changed (still #{@before_pid})"
|
17
|
+
else
|
18
|
+
assert_equal @before_pid, after_pid, "Process '#{target}' pid was changed (was #{@before_pid}, now #{after_pid})"
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Spex
|
2
|
+
class StartedAssertion < ProcessAssertion
|
3
|
+
as :started, 'process start'
|
4
|
+
example "Process was started", "assert 'postfix', :started => true"
|
5
|
+
example "Process was not started", "assert 'postfix', :started => false"
|
6
|
+
|
7
|
+
def before
|
8
|
+
pid = current_pid
|
9
|
+
assert !pid, "Process '#{target}' is already running (pid #{pid})"
|
10
|
+
end
|
11
|
+
|
12
|
+
def after
|
13
|
+
if active?
|
14
|
+
assert current_pid, "Process '#{target}' was not started"
|
15
|
+
else
|
16
|
+
pid = current_pid
|
17
|
+
assert_nil pid, "Process '#{target}' was started (pid #{pid})"
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,20 @@
|
|
1
|
+
module Spex
|
2
|
+
class StoppedAssertion < ProcessAssertion
|
3
|
+
as :stopped, 'process stop'
|
4
|
+
example "Process was stopped", "assert 'postfix', :stopped => true"
|
5
|
+
example "Process was not stopped", "assert 'postfix', :stopped => false"
|
6
|
+
|
7
|
+
def before
|
8
|
+
assert current_pid, "Process '#{target}' is not running (will not be stopped)"
|
9
|
+
end
|
10
|
+
|
11
|
+
def after
|
12
|
+
pid = current_pid
|
13
|
+
if active?
|
14
|
+
assert_nil pid, "Process '#{target}' is still running (pid #{pid})"
|
15
|
+
else
|
16
|
+
assert_not_nil pid, "Process '#{target}' was stopped"
|
17
|
+
end
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
data/lib/spex/runner.rb
CHANGED
@@ -15,10 +15,10 @@ module Spex
|
|
15
15
|
end
|
16
16
|
|
17
17
|
def run
|
18
|
-
puts %(Running scenario "#{scenario.name}").bold
|
18
|
+
puts %(Running scenario "#{scenario.name}").magenta.bold
|
19
19
|
proceed = true
|
20
20
|
scenario.each do |execution|
|
21
|
-
puts
|
21
|
+
puts %(Preparing to execute "#{execution.command}").bold
|
22
22
|
execution.assertions.each do |assertion|
|
23
23
|
print "Pre-assertions for #{assertion}: "
|
24
24
|
assertion.prepare
|
@@ -26,24 +26,26 @@ module Spex
|
|
26
26
|
break unless proceed
|
27
27
|
end
|
28
28
|
if proceed
|
29
|
-
|
29
|
+
print %(Executing "#{execution.command}": )
|
30
|
+
start = Time.now
|
30
31
|
log = execute(execution)
|
32
|
+
elapsed = Time.now - start
|
33
|
+
puts 'DONE (%.2fs)' % elapsed
|
31
34
|
passed = true
|
32
35
|
execution.assertions.reverse.each do |assertion|
|
33
36
|
print "Post-assertions for #{assertion}: "
|
34
37
|
passed = report { assertion.after }
|
35
38
|
break unless passed
|
36
39
|
end
|
37
|
-
|
38
|
-
|
39
|
-
else
|
40
|
-
abort "SCENARIO FAILED".red.bold
|
40
|
+
unless passed
|
41
|
+
abort "SCENARIO ASSERTIONS FAILED".red.bold
|
41
42
|
end
|
42
43
|
output_log(execution, log)
|
43
44
|
else
|
44
45
|
abort "SCENARIO FAILED (EXECUTION ABORTED)".red.bold
|
45
46
|
end
|
46
47
|
end
|
48
|
+
puts "SCENARIO PASSED".green.bold
|
47
49
|
end
|
48
50
|
|
49
51
|
def report(&block)
|
data/test/helper.rb
CHANGED
@@ -7,6 +7,7 @@ $LOAD_PATH.unshift(File.join(File.dirname(__FILE__), '..', 'lib'))
|
|
7
7
|
$LOAD_PATH.unshift(File.dirname(__FILE__))
|
8
8
|
require 'spex'
|
9
9
|
require 'fakefs/safe'
|
10
|
+
require 'flexmock/test_unit'
|
10
11
|
|
11
12
|
class Test::Unit::TestCase
|
12
13
|
|
@@ -23,10 +24,27 @@ class Test::Unit::TestCase
|
|
23
24
|
@assertion.after
|
24
25
|
end
|
25
26
|
|
27
|
+
def assertion_fails_before
|
28
|
+
assert_raises Test::Unit::AssertionFailedError do
|
29
|
+
@assertion.prepare
|
30
|
+
@assertion.before
|
31
|
+
end
|
32
|
+
end
|
33
|
+
|
26
34
|
def assertion_fails(&block)
|
27
35
|
assert_raises Test::Unit::AssertionFailedError do
|
28
36
|
assertion_passes(&block)
|
29
37
|
end
|
30
38
|
end
|
39
|
+
|
40
|
+
def start_process!(pid = '100')
|
41
|
+
flexmock(@assertion).flexmock_teardown
|
42
|
+
flexmock(@assertion).should_receive(:current_pid).and_return(pid)
|
43
|
+
end
|
44
|
+
|
45
|
+
def stop_process!
|
46
|
+
flexmock(@assertion).flexmock_teardown
|
47
|
+
flexmock(@assertion).should_receive(:current_pid).and_return(nil)
|
48
|
+
end
|
31
49
|
|
32
50
|
end
|
@@ -0,0 +1,77 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
class TestRestartedAssertion < Test::Unit::TestCase
|
4
|
+
|
5
|
+
def set_assertion(options = {})
|
6
|
+
@assertion = Spex::RestartedAssertion.new('testproc', options)
|
7
|
+
end
|
8
|
+
|
9
|
+
context "Restarted Assertion" do
|
10
|
+
context "instances" do
|
11
|
+
context "set to true" do
|
12
|
+
setup do
|
13
|
+
set_assertion(true)
|
14
|
+
end
|
15
|
+
context "process running before execution" do
|
16
|
+
setup do
|
17
|
+
start_process!
|
18
|
+
end
|
19
|
+
context "and process running after execution" do
|
20
|
+
context "with the same pid" do
|
21
|
+
should 'fail' do
|
22
|
+
assertion_fails
|
23
|
+
end
|
24
|
+
end
|
25
|
+
context "with a different pid" do
|
26
|
+
should 'pass' do
|
27
|
+
assertion_passes { start_process!('101') }
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
context "but process not running after execution" do
|
32
|
+
should "fail" do
|
33
|
+
assertion_fails
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
context "process not running before execution" do
|
38
|
+
should "fail" do
|
39
|
+
assertion_fails_before
|
40
|
+
end
|
41
|
+
end
|
42
|
+
end
|
43
|
+
context "set to false" do
|
44
|
+
setup do
|
45
|
+
set_assertion(false)
|
46
|
+
end
|
47
|
+
context "process running before execution" do
|
48
|
+
setup do
|
49
|
+
start_process!
|
50
|
+
end
|
51
|
+
context "and process running after execution" do
|
52
|
+
context "with the same pid" do
|
53
|
+
should 'pass' do
|
54
|
+
assertion_passes
|
55
|
+
end
|
56
|
+
end
|
57
|
+
context "with a different pid" do
|
58
|
+
should 'fail' do
|
59
|
+
assertion_fails { start_process!('101') }
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
context "but process not running after execution" do
|
64
|
+
should "fail" do
|
65
|
+
assertion_fails { stop_process! }
|
66
|
+
end
|
67
|
+
end
|
68
|
+
end
|
69
|
+
context "process not running before execution" do
|
70
|
+
should "fail" do
|
71
|
+
assertion_fails_before
|
72
|
+
end
|
73
|
+
end
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
end
|
@@ -0,0 +1,63 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
class TestStartedAssertion < Test::Unit::TestCase
|
4
|
+
|
5
|
+
def set_assertion(options = {})
|
6
|
+
@assertion = Spex::StartedAssertion.new('testproc', options)
|
7
|
+
end
|
8
|
+
|
9
|
+
context "Started Assertion" do
|
10
|
+
context "instances" do
|
11
|
+
context "set to true" do
|
12
|
+
setup do
|
13
|
+
set_assertion(true)
|
14
|
+
end
|
15
|
+
context "process running before execution" do
|
16
|
+
setup do
|
17
|
+
start_process!
|
18
|
+
end
|
19
|
+
should "fail" do
|
20
|
+
assertion_fails_before
|
21
|
+
end
|
22
|
+
end
|
23
|
+
context "process not running before execution" do
|
24
|
+
context "process running after execution" do
|
25
|
+
should "pass" do
|
26
|
+
assertion_passes { start_process! }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
context "process not running after execution" do
|
30
|
+
should 'fail' do
|
31
|
+
assertion_fails
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
context "set to false" do
|
37
|
+
setup do
|
38
|
+
set_assertion(false)
|
39
|
+
end
|
40
|
+
context "process running before execution" do
|
41
|
+
setup do
|
42
|
+
start_process!
|
43
|
+
end
|
44
|
+
should "fail" do
|
45
|
+
assertion_fails_before
|
46
|
+
end
|
47
|
+
end
|
48
|
+
context "process not running before execution" do
|
49
|
+
context "but process running after execution" do
|
50
|
+
should "fail" do
|
51
|
+
assertion_fails { start_process! }
|
52
|
+
end
|
53
|
+
end
|
54
|
+
context "but process not running after execution" do
|
55
|
+
should 'pass' do
|
56
|
+
assertion_passes
|
57
|
+
end
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
@@ -0,0 +1,63 @@
|
|
1
|
+
require 'helper'
|
2
|
+
|
3
|
+
class TestStoppedAssertion < Test::Unit::TestCase
|
4
|
+
|
5
|
+
def set_assertion(options = {})
|
6
|
+
@assertion = Spex::StoppedAssertion.new('testproc', options)
|
7
|
+
end
|
8
|
+
|
9
|
+
context "Stopped Assertion" do
|
10
|
+
context "instances" do
|
11
|
+
context "set to true" do
|
12
|
+
setup do
|
13
|
+
set_assertion(true)
|
14
|
+
end
|
15
|
+
context "process running before execution" do
|
16
|
+
setup do
|
17
|
+
start_process!
|
18
|
+
end
|
19
|
+
context "and process running after execution" do
|
20
|
+
should 'fail' do
|
21
|
+
assertion_fails
|
22
|
+
end
|
23
|
+
end
|
24
|
+
context "but process not running after execution" do
|
25
|
+
should "pass" do
|
26
|
+
assertion_passes { stop_process! }
|
27
|
+
end
|
28
|
+
end
|
29
|
+
end
|
30
|
+
context "process not running before execution" do
|
31
|
+
should "fail" do
|
32
|
+
assertion_fails_before
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
context "set to false" do
|
37
|
+
setup do
|
38
|
+
set_assertion(false)
|
39
|
+
end
|
40
|
+
context "process running before execution" do
|
41
|
+
setup do
|
42
|
+
start_process!
|
43
|
+
end
|
44
|
+
context "and process running after execution" do
|
45
|
+
should 'pass' do
|
46
|
+
assertion_passes
|
47
|
+
end
|
48
|
+
end
|
49
|
+
context "but process not running after execution" do
|
50
|
+
should "fail" do
|
51
|
+
assertion_fails { stop_process! }
|
52
|
+
end
|
53
|
+
end
|
54
|
+
end
|
55
|
+
context "process not running before execution" do
|
56
|
+
should "fail" do
|
57
|
+
assertion_fails_before
|
58
|
+
end
|
59
|
+
end
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
end
|
metadata
CHANGED
@@ -4,9 +4,9 @@ version: !ruby/object:Gem::Version
|
|
4
4
|
prerelease: false
|
5
5
|
segments:
|
6
6
|
- 0
|
7
|
-
-
|
8
|
-
-
|
9
|
-
version: 0.
|
7
|
+
- 6
|
8
|
+
- 0
|
9
|
+
version: 0.6.0
|
10
10
|
platform: ruby
|
11
11
|
authors:
|
12
12
|
- Bruce Williams
|
@@ -14,7 +14,7 @@ autorequire:
|
|
14
14
|
bindir: bin
|
15
15
|
cert_chain: []
|
16
16
|
|
17
|
-
date: 2010-04-
|
17
|
+
date: 2010-04-15 00:00:00 -07:00
|
18
18
|
default_executable: spex
|
19
19
|
dependencies:
|
20
20
|
- !ruby/object:Gem::Dependency
|
@@ -41,6 +41,18 @@ dependencies:
|
|
41
41
|
version: "0"
|
42
42
|
type: :runtime
|
43
43
|
version_requirements: *id002
|
44
|
+
- !ruby/object:Gem::Dependency
|
45
|
+
name: facter
|
46
|
+
prerelease: false
|
47
|
+
requirement: &id003 !ruby/object:Gem::Requirement
|
48
|
+
requirements:
|
49
|
+
- - ">="
|
50
|
+
- !ruby/object:Gem::Version
|
51
|
+
segments:
|
52
|
+
- 0
|
53
|
+
version: "0"
|
54
|
+
type: :runtime
|
55
|
+
version_requirements: *id003
|
44
56
|
description: An easy-to-use test harness that runs assertions before and after and executable is run
|
45
57
|
email: bruce@codefluency.com
|
46
58
|
executables:
|
@@ -61,6 +73,7 @@ files:
|
|
61
73
|
- examples/chgrp.rb
|
62
74
|
- examples/chmod.rb
|
63
75
|
- examples/chown.rb
|
76
|
+
- examples/postfix.rb
|
64
77
|
- examples/puppet.rb
|
65
78
|
- examples/touch.rb
|
66
79
|
- examples/writing.rb
|
@@ -72,7 +85,11 @@ files:
|
|
72
85
|
- lib/spex/assertions/created_assertion.rb
|
73
86
|
- lib/spex/assertions/file_assertion.rb
|
74
87
|
- lib/spex/assertions/modified_assertion.rb
|
88
|
+
- lib/spex/assertions/process_assertion.rb
|
75
89
|
- lib/spex/assertions/removed_assertion.rb
|
90
|
+
- lib/spex/assertions/restarted_assertion.rb
|
91
|
+
- lib/spex/assertions/started_assertion.rb
|
92
|
+
- lib/spex/assertions/stopped_assertion.rb
|
76
93
|
- lib/spex/cli.rb
|
77
94
|
- lib/spex/execution.rb
|
78
95
|
- lib/spex/runner.rb
|
@@ -81,7 +98,10 @@ files:
|
|
81
98
|
- test/helper.rb
|
82
99
|
- test/test_assertion.rb
|
83
100
|
- test/test_modified_assertion.rb
|
101
|
+
- test/test_restarted_assertion.rb
|
84
102
|
- test/test_script.rb
|
103
|
+
- test/test_started_assertion.rb
|
104
|
+
- test/test_stopped_assertion.rb
|
85
105
|
has_rdoc: true
|
86
106
|
homepage: http://github.com/bruce/spex
|
87
107
|
licenses: []
|
@@ -116,10 +136,14 @@ test_files:
|
|
116
136
|
- test/helper.rb
|
117
137
|
- test/test_assertion.rb
|
118
138
|
- test/test_modified_assertion.rb
|
139
|
+
- test/test_restarted_assertion.rb
|
119
140
|
- test/test_script.rb
|
141
|
+
- test/test_started_assertion.rb
|
142
|
+
- test/test_stopped_assertion.rb
|
120
143
|
- examples/chgrp.rb
|
121
144
|
- examples/chmod.rb
|
122
145
|
- examples/chown.rb
|
146
|
+
- examples/postfix.rb
|
123
147
|
- examples/puppet.rb
|
124
148
|
- examples/touch.rb
|
125
149
|
- examples/writing.rb
|