mutant 0.2.20 → 0.3.0.beta2

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.
Files changed (201) hide show
  1. checksums.yaml +7 -0
  2. data/.travis.yml +10 -11
  3. data/Changelog.md +93 -38
  4. data/Gemfile +3 -1
  5. data/Gemfile.devtools +16 -20
  6. data/Guardfile +1 -1
  7. data/README.md +36 -16
  8. data/Rakefile +21 -2
  9. data/TODO +11 -7
  10. data/bin/mutant +4 -0
  11. data/bin/zombie +4 -0
  12. data/config/devtools.yml +2 -0
  13. data/config/flay.yml +2 -2
  14. data/config/flog.yml +1 -1
  15. data/config/{site.reek → reek.yml} +94 -70
  16. data/lib/mutant/cli/classifier/method.rb +100 -0
  17. data/lib/mutant/cli/classifier/namespace.rb +47 -0
  18. data/lib/mutant/cli/classifier/scope.rb +35 -0
  19. data/lib/mutant/cli/classifier.rb +141 -0
  20. data/lib/mutant/cli.rb +115 -162
  21. data/lib/mutant/color.rb +2 -2
  22. data/lib/mutant/config.rb +27 -0
  23. data/lib/mutant/constants.rb +32 -17
  24. data/lib/mutant/context/scope.rb +33 -51
  25. data/lib/mutant/context.rb +8 -19
  26. data/lib/mutant/differ.rb +5 -5
  27. data/lib/mutant/helper.rb +2 -17
  28. data/lib/mutant/killer/forked.rb +44 -0
  29. data/lib/mutant/killer/forking.rb +3 -57
  30. data/lib/mutant/killer/rspec.rb +16 -20
  31. data/lib/mutant/killer/static.rb +6 -7
  32. data/lib/mutant/killer.rb +48 -74
  33. data/lib/mutant/loader.rb +6 -6
  34. data/lib/mutant/matcher/chain.rb +4 -25
  35. data/lib/mutant/matcher/method/instance.rb +14 -24
  36. data/lib/mutant/matcher/method/singleton.rb +35 -46
  37. data/lib/mutant/matcher/method.rb +95 -83
  38. data/lib/mutant/matcher/{scope_methods.rb → methods.rb} +53 -76
  39. data/lib/mutant/matcher/namespace.rb +71 -0
  40. data/lib/mutant/matcher/scope.rb +34 -0
  41. data/lib/mutant/matcher.rb +24 -34
  42. data/lib/mutant/mutation/evil.rb +35 -0
  43. data/lib/mutant/mutation/filter/code.rb +7 -28
  44. data/lib/mutant/mutation/filter/regexp.rb +6 -18
  45. data/lib/mutant/mutation/filter/whitelist.rb +5 -4
  46. data/lib/mutant/mutation/filter.rb +10 -9
  47. data/lib/mutant/mutation/neutral.rb +35 -0
  48. data/lib/mutant/mutation.rb +21 -61
  49. data/lib/mutant/mutator/node/argument.rb +88 -0
  50. data/lib/mutant/mutator/node/arguments.rb +52 -0
  51. data/lib/mutant/mutator/node/assignment.rb +34 -38
  52. data/lib/mutant/mutator/node/begin.rb +33 -0
  53. data/lib/mutant/mutator/node/block.rb +14 -14
  54. data/lib/mutant/mutator/node/case.rb +59 -0
  55. data/lib/mutant/mutator/node/define.rb +26 -22
  56. data/lib/mutant/mutator/node/if.rb +31 -71
  57. data/lib/mutant/mutator/node/literal/array.rb +25 -9
  58. data/lib/mutant/mutator/node/literal/boolean.rb +13 -30
  59. data/lib/mutant/mutator/node/literal/dynamic.rb +6 -5
  60. data/lib/mutant/mutator/node/literal/fixnum.rb +18 -7
  61. data/lib/mutant/mutator/node/literal/float.rb +15 -8
  62. data/lib/mutant/mutator/node/literal/hash.rb +33 -52
  63. data/lib/mutant/mutator/node/literal/nil.rb +8 -7
  64. data/lib/mutant/mutator/node/literal/range.rb +25 -50
  65. data/lib/mutant/mutator/node/literal/regex.rb +15 -23
  66. data/lib/mutant/mutator/node/literal/string.rb +7 -6
  67. data/lib/mutant/mutator/node/literal/symbol.rb +7 -6
  68. data/lib/mutant/mutator/node/literal.rb +4 -46
  69. data/lib/mutant/mutator/node/mlhs.rb +27 -0
  70. data/lib/mutant/mutator/node/noop.rb +18 -43
  71. data/lib/mutant/mutator/node/return.rb +8 -8
  72. data/lib/mutant/mutator/node/send/binary.rb +31 -0
  73. data/lib/mutant/mutator/node/send.rb +106 -72
  74. data/lib/mutant/mutator/node/super.rb +15 -20
  75. data/lib/mutant/mutator/node/when.rb +32 -7
  76. data/lib/mutant/mutator/node/while.rb +9 -7
  77. data/lib/mutant/mutator/node.rb +116 -66
  78. data/lib/mutant/mutator/registry.rb +14 -11
  79. data/lib/mutant/mutator/util/array.rb +9 -9
  80. data/lib/mutant/mutator/util/symbol.rb +6 -20
  81. data/lib/mutant/mutator/util.rb +6 -3
  82. data/lib/mutant/mutator.rb +12 -28
  83. data/lib/mutant/node_helpers.rb +28 -0
  84. data/lib/mutant/random.rb +3 -2
  85. data/lib/mutant/reporter/cli/printer/config.rb +174 -0
  86. data/lib/mutant/reporter/cli/printer/killer.rb +42 -0
  87. data/lib/mutant/reporter/cli/printer/mutation.rb +55 -0
  88. data/lib/mutant/reporter/cli/printer/subject.rb +147 -0
  89. data/lib/mutant/reporter/cli/printer.rb +165 -0
  90. data/lib/mutant/reporter/cli.rb +9 -277
  91. data/lib/mutant/reporter/null.rb +6 -30
  92. data/lib/mutant/reporter.rb +6 -73
  93. data/lib/mutant/runner/config.rb +82 -0
  94. data/lib/mutant/runner/mutation.rb +58 -0
  95. data/lib/mutant/runner/subject.rb +81 -0
  96. data/lib/mutant/runner.rb +42 -92
  97. data/lib/mutant/singleton_methods.rb +2 -2
  98. data/lib/mutant/strategy/method_expansion.rb +51 -0
  99. data/lib/mutant/strategy/rspec/dm2/lookup/method.rb +142 -0
  100. data/lib/mutant/strategy/rspec/dm2/lookup.rb +61 -0
  101. data/lib/mutant/strategy/rspec/dm2.rb +22 -0
  102. data/lib/mutant/strategy/rspec.rb +20 -22
  103. data/lib/mutant/strategy/static.rb +18 -0
  104. data/lib/mutant/strategy.rb +15 -50
  105. data/lib/mutant/subject/method.rb +100 -0
  106. data/lib/mutant/subject.rb +18 -49
  107. data/lib/mutant/support/method_object.rb +4 -2
  108. data/lib/mutant.rb +40 -35
  109. data/mutant.gemspec +9 -8
  110. data/spec/integration/mutant/rspec_killer_spec.rb +3 -3
  111. data/spec/integration/mutant/test_mutator_handles_types_spec.rb +9 -0
  112. data/spec/integration/mutant/zombie_spec.rb +1 -1
  113. data/spec/shared/method_matcher_behavior.rb +35 -0
  114. data/spec/shared/mutator_behavior.rb +63 -32
  115. data/spec/spec_helper.rb +13 -3
  116. data/spec/support/ice_nine_config.rb +8 -0
  117. data/spec/support/rspec.rb +1 -1
  118. data/spec/support/zombie.rb +1 -1
  119. data/spec/unit/mutant/cli/class_methods/new_spec.rb +42 -28
  120. data/spec/unit/mutant/cli/class_methods/run_spec.rb +15 -13
  121. data/spec/unit/mutant/cli/classifier/class_methods/build_spec.rb +44 -0
  122. data/spec/unit/mutant/context/scope/root_spec.rb +4 -4
  123. data/spec/unit/mutant/killer/rspec/class_methods/new_spec.rb +6 -5
  124. data/spec/unit/mutant/killer/success_predicate_spec.rb +28 -0
  125. data/spec/unit/mutant/loader/eval/class_methods/run_spec.rb +1 -1
  126. data/spec/unit/mutant/matcher/chain/each_spec.rb +1 -1
  127. data/spec/unit/mutant/matcher/chain/matchers_spec.rb +1 -1
  128. data/spec/unit/mutant/matcher/method/instance/each_spec.rb +112 -0
  129. data/spec/unit/mutant/matcher/method/singleton/each_spec.rb +93 -0
  130. data/spec/unit/mutant/matcher/methods/instance/each_spec.rb +59 -0
  131. data/spec/unit/mutant/matcher/methods/singleton/each_spec.rb +53 -0
  132. data/spec/unit/mutant/matcher/namespace/each_spec.rb +37 -0
  133. data/spec/unit/mutant/mutator/node/begin/mutation_spec.rb +33 -0
  134. data/spec/unit/mutant/mutator/node/block/mutation_spec.rb +42 -14
  135. data/spec/unit/mutant/mutator/node/case/mutation_spec.rb +319 -0
  136. data/spec/unit/mutant/mutator/node/define/mutation_spec.rb +31 -27
  137. data/spec/unit/mutant/mutator/node/if/mutation_spec.rb +75 -0
  138. data/spec/unit/mutant/mutator/node/literal/fixnum_spec.rb +1 -1
  139. data/spec/unit/mutant/mutator/node/literal/hash_spec.rb +2 -2
  140. data/spec/unit/mutant/mutator/node/literal/nil_spec.rb +1 -3
  141. data/spec/unit/mutant/mutator/node/literal/regex_spec.rb +1 -9
  142. data/spec/unit/mutant/mutator/node/return/mutation_spec.rb +6 -2
  143. data/spec/unit/mutant/mutator/node/send/mutation_spec.rb +111 -108
  144. data/spec/unit/mutant/mutator/node/super/mutation_spec.rb +0 -33
  145. data/spec/unit/mutant/mutator/node/while/mutation_spec.rb +2 -2
  146. data/spec/unit/mutant/runner/config/subjects_spec.rb +38 -0
  147. data/spec/unit/mutant/runner/config/success_predicate_spec.rb +53 -0
  148. data/spec/unit/mutant/runner/failed_predicte_spec.rb +33 -0
  149. data/spec/unit/mutant/runner/mutation/killer_spec.rb +39 -0
  150. data/spec/unit/mutant/runner/subject/success_predicate_spec.rb +49 -0
  151. data/spec/unit/mutant/strategy/method_expansion/class_methods/run_spec.rb +49 -0
  152. data/spec/unit/mutant/strategy/rspec/dm2/lookup/method/instance/spec_files_spec.rb +52 -0
  153. data/spec/unit/mutant/strategy/rspec/dm2/lookup/method/singleton/spec_files_spec.rb +42 -0
  154. data/spec/unit/mutant/subject/context_spec.rb +6 -3
  155. data/spec/unit/mutant/subject/each_spec.rb +11 -8
  156. data/spec/unit/mutant/subject/node_spec.rb +6 -2
  157. data/test_app/spec/shared/method_filter_parse_behavior.rb +0 -2
  158. data/test_app/spec/shared/method_match_behavior.rb +1 -1
  159. data/test_app/spec/spec_helper.rb +4 -2
  160. metadata +101 -109
  161. data/config/roodi.yml +0 -26
  162. data/lib/mutant/matcher/method/classifier.rb +0 -141
  163. data/lib/mutant/matcher/object_space.rb +0 -114
  164. data/lib/mutant/mutator/node/actual_arguments.rb +0 -25
  165. data/lib/mutant/mutator/node/default_arguments.rb +0 -25
  166. data/lib/mutant/mutator/node/formal_arguments_19/default_mutations.rb +0 -33
  167. data/lib/mutant/mutator/node/formal_arguments_19/pattern_argument_expansion.rb +0 -35
  168. data/lib/mutant/mutator/node/formal_arguments_19/require_defaults.rb +0 -37
  169. data/lib/mutant/mutator/node/formal_arguments_19.rb +0 -41
  170. data/lib/mutant/mutator/node/iter_19.rb +0 -27
  171. data/lib/mutant/mutator/node/literal/empty_array.rb +0 -26
  172. data/lib/mutant/mutator/node/pattern_arguments.rb +0 -41
  173. data/lib/mutant/mutator/node/pattern_variable.rb +0 -23
  174. data/lib/mutant/mutator/node/receiver_case.rb +0 -122
  175. data/lib/mutant/mutator/node/send/binary_operator_method.rb +0 -61
  176. data/lib/mutant/mutator/node/send/with_arguments.rb +0 -81
  177. data/lib/mutant/reporter/stats.rb +0 -120
  178. data/lib/mutant/strategy/rspec/example_lookup.rb +0 -163
  179. data/spec/integration/mutant/method_matching_spec.rb +0 -269
  180. data/spec/shared/method_match_behavior.rb +0 -39
  181. data/spec/unit/mutant/killer/fail_ques_spec.rb +0 -39
  182. data/spec/unit/mutant/matcher/class_methods/from_string_spec.rb +0 -49
  183. data/spec/unit/mutant/matcher/class_methods/parse_spec.rb +0 -12
  184. data/spec/unit/mutant/matcher/method/class_methods/parse_spec.rb +0 -21
  185. data/spec/unit/mutant/matcher/method/classifier/class_methods/run_spec.rb +0 -52
  186. data/spec/unit/mutant/matcher/object_space/class_methods/parse_spec.rb +0 -24
  187. data/spec/unit/mutant/matcher/object_space/each_spec.rb +0 -31
  188. data/spec/unit/mutant/mutator/node/if_statement/mutation_spec.rb +0 -60
  189. data/spec/unit/mutant/mutator/node/receiver_case/mutation_spec.rb +0 -27
  190. data/spec/unit/mutant/strategy/rspec/example_lookup/spec_file_spec.rb +0 -236
  191. data/spec/unit/mutant/subject/class_methods/new_spec.rb +0 -13
  192. data/tasks/metrics/ci.rake +0 -7
  193. data/tasks/metrics/flay.rake +0 -41
  194. data/tasks/metrics/flog.rake +0 -43
  195. data/tasks/metrics/heckle.rake +0 -216
  196. data/tasks/metrics/metric_fu.rake +0 -31
  197. data/tasks/metrics/reek.rake +0 -15
  198. data/tasks/metrics/roodi.rake +0 -15
  199. data/tasks/metrics/yardstick.rake +0 -23
  200. data/tasks/spec.rake +0 -45
  201. data/tasks/yard.rake +0 -9
@@ -4,9 +4,7 @@ describe Mutant::Mutator::Node::Literal, 'nil' do
4
4
  let(:source) { 'nil' }
5
5
 
6
6
  let(:mutations) do
7
- mutations = []
8
-
9
- mutations << 'Object.new'
7
+ [ '::Object.new' ]
10
8
  end
11
9
 
12
10
  it_should_behave_like 'a mutator'
@@ -1,23 +1,15 @@
1
1
  require 'spec_helper'
2
2
 
3
3
  describe Mutant::Mutator::Node::Literal, 'regex' do
4
- let(:random_string) { 'bar' }
5
4
 
6
5
  let(:source) { '/foo/' }
7
6
 
8
- let(:base_mutations) do
7
+ let(:mutations) do
9
8
  mutations = []
10
9
  mutations << 'nil'
11
- mutations << "/#{random_string}/"
12
10
  mutations << '//' # match all
13
11
  mutations << '/a\A/' # match nothing
14
12
  end
15
13
 
16
- before do
17
- Mutant::Random.stub(:hex_string => random_string)
18
- end
19
-
20
- let(:mutations) { base_mutations }
21
-
22
14
  it_should_behave_like 'a mutator'
23
15
  end
@@ -11,9 +11,13 @@ describe Mutant::Mutator, 'return' do
11
11
  end
12
12
 
13
13
  context 'return with value' do
14
- let(:source) { 'return foo' }
14
+ let(:source) { 'return nil' }
15
15
 
16
- let(:mutations) { ['foo'] }
16
+ let(:mutations) do
17
+ mutations = []
18
+ mutations << 'nil'
19
+ mutations << 'return ::Object.new'
20
+ end
17
21
 
18
22
  it_should_behave_like 'a mutator'
19
23
  end
@@ -2,129 +2,119 @@ require 'spec_helper'
2
2
 
3
3
  # FIXME: This spec needs to be structured better!
4
4
  describe Mutant::Mutator, 'send' do
5
- context 'send without arguments' do
6
- context 'with self as receiver' do
7
- context 'implicit' do
8
- let(:source) { 'foo' }
9
5
 
10
- it_should_behave_like 'a noop mutator'
11
- end
12
-
13
- context 'explict' do
14
- let(:source) { 'self.foo' }
15
-
16
- let(:mutations) do
17
- mutations = []
18
- # with implicit receiver (send privately)
19
- mutations << 'foo'
20
- end
6
+ context 'index assign' do
7
+ let(:source) { 'foo[bar]=baz' }
21
8
 
22
- it_should_behave_like 'a mutator'
23
- end
24
-
25
- context 'explicit with keyword message name' do
26
- Mutant::KEYWORDS.each do |keyword|
27
- context "with keyword: #{keyword}" do
28
- let(:source) { "self.#{keyword}" }
29
- it_should_behave_like 'a noop mutator'
30
- end
31
- end
32
- end
9
+ let(:mutations) do
10
+ mutations = []
11
+ mutations << 'foo'
33
12
  end
34
13
 
35
- context 'to some object' do
36
- let(:source) { 'foo.bar' }
14
+ it_should_behave_like 'a mutator'
15
+ end
37
16
 
38
- let(:mutations) do
39
- mutations = []
40
- mutations << 'foo'
41
- end
42
17
 
43
- it_should_behave_like 'a mutator'
18
+ context 'with only a splat arg' do
19
+ let(:source) { 'foo(*bar)' }
20
+
21
+ let(:mutations) do
22
+ mutations = []
23
+ mutations << 'foo'
44
24
  end
45
25
 
46
- context 'to self.class.foo' do
47
- let(:source) { 'self.class.foo' }
26
+ it_should_behave_like 'a mutator'
27
+ end
48
28
 
49
- let(:mutations) do
50
- mutations = []
51
- mutations << 'self.class'
52
- end
29
+ context 'with only a block arg' do
30
+ let(:source) { 'foo(&bar)' }
53
31
 
54
- it_should_behave_like 'a mutator'
32
+ let(:mutations) do
33
+ mutations = []
34
+ mutations << 'foo'
55
35
  end
36
+
37
+ it_should_behave_like 'a mutator'
56
38
  end
57
39
 
58
- context 'with block' do
59
- let(:source) { 'foo() { a; b }' }
40
+ context 'single splat arg splat' do
41
+ let(:source) { 'foo[*bar]' }
60
42
 
61
- let(:mutations) do
43
+ let(:mutations) do
62
44
  mutations = []
63
- mutations << 'foo() { a }'
64
- mutations << 'foo() { b }'
65
- mutations << 'foo() { }'
66
45
  mutations << 'foo'
67
46
  end
68
47
 
69
48
  it_should_behave_like 'a mutator'
70
49
  end
71
50
 
72
- context 'with block args' do
73
-
74
- let(:source) { 'foo { |a, b| }' }
51
+ context 'with self as' do
52
+ context 'implicit' do
53
+ let(:source) { 'foo' }
75
54
 
76
- before do
77
- Mutant::Random.stub(:hex_string => :random)
55
+ it_should_behave_like 'a noop mutator'
78
56
  end
79
57
 
80
- let(:mutations) do
81
- mutations = []
82
- mutations << 'foo'
83
- mutations << 'foo { |a, b| Object.new }'
84
- mutations << 'foo { |a, srandom| }'
85
- mutations << 'foo { |srandom, b| }'
86
- mutations << 'foo { |a| }'
87
- mutations << 'foo { |b| }'
88
- mutations << 'foo { || }'
58
+ context 'explict receiver' do
59
+ let(:source) { 'self.foo' }
60
+
61
+ let(:mutations) do
62
+ mutations = []
63
+ mutations << 'foo'
64
+ mutations << 'self'
65
+ end
66
+
67
+ it_should_behave_like 'a mutator'
89
68
  end
90
69
 
91
- it_should_behave_like 'a mutator'
70
+ context 'explicit receiver with keyword message name' do
71
+ Unparser::Constants::KEYWORDS.each do |keyword|
72
+ context "with keyword: #{keyword}" do
73
+ let(:source) { "self.#{keyword}" }
74
+ let(:mutations) do
75
+ ['self']
76
+ end
77
+ end
78
+ end
79
+ end
92
80
  end
93
81
 
94
- context 'with block pattern args' do
82
+ context 'without arguments' do
95
83
 
96
- before do
97
- Mutant::Random.stub(:hex_string => :random)
98
- end
84
+ context 'to some object' do
85
+ let(:source) { 'foo.bar' }
99
86
 
100
- let(:source) { 'foo { |(a, b), c| }' }
87
+ let(:mutations) do
88
+ mutations = []
89
+ mutations << 'foo'
90
+ end
101
91
 
102
- let(:mutations) do
103
- mutations = []
104
- mutations << 'foo { || }'
105
- mutations << 'foo { |a, b, c| }'
106
- mutations << 'foo { |(a, b), c| Object.new }'
107
- mutations << 'foo { |(a, b)| }'
108
- mutations << 'foo { |c| }'
109
- mutations << 'foo { |(srandom, b), c| }'
110
- mutations << 'foo { |(a, srandom), c| }'
111
- mutations << 'foo { |(a, b), srandom| }'
112
- mutations << 'foo'
92
+ it_should_behave_like 'a mutator'
113
93
  end
114
94
 
115
- it_should_behave_like 'a mutator'
95
+ context 'to self.class.foo' do
96
+ let(:source) { 'self.class.foo' }
97
+
98
+ let(:mutations) do
99
+ mutations = []
100
+ mutations << 'self.class'
101
+ mutations << 'self.foo'
102
+ end
103
+
104
+ it_should_behave_like 'a mutator'
105
+ end
116
106
  end
117
107
 
118
- context 'send with arguments' do
108
+ context 'with arguments' do
119
109
 
120
110
  context 'one argument' do
121
111
  let(:source) { 'foo(nil)' }
122
112
 
123
- let(:mutations) do
113
+ let(:mutations) do
124
114
  mutations = []
125
115
  mutations << 'foo'
126
116
  mutations << 'nil'
127
- mutations << 'foo(Object.new)'
117
+ mutations << 'foo(::Object.new)'
128
118
  end
129
119
 
130
120
  it_should_behave_like 'a mutator'
@@ -133,28 +123,29 @@ describe Mutant::Mutator, 'send' do
133
123
  context 'with explicit self as receiver' do
134
124
  let(:source) { 'self.foo(nil)' }
135
125
 
136
- let(:mutations) do
126
+ let(:mutations) do
137
127
  mutations = []
128
+ mutations << 'self'
138
129
  mutations << 'self.foo'
139
130
  mutations << 'foo(nil)'
140
131
  mutations << 'nil'
141
- mutations << 'self.foo(Object.new)'
132
+ mutations << 'self.foo(::Object.new)'
142
133
  end
143
134
 
144
135
  it_should_behave_like 'a mutator'
145
136
  end
146
137
 
147
138
  context 'to some object with keyword in method name' do
148
- Mutant::KEYWORDS.each do |keyword|
139
+ Unparser::Constants::KEYWORDS.each do |keyword|
149
140
  context "with keyword #{keyword}" do
150
141
  let(:source) { "foo.#{keyword}(nil)" }
151
142
 
152
- let(:mutations) do
143
+ let(:mutations) do
153
144
  mutations = []
154
145
  mutations << "foo.#{keyword}"
155
- mutations << "foo"
146
+ mutations << 'foo'
156
147
  mutations << 'nil'
157
- mutations << "foo.#{keyword}(Object.new)"
148
+ mutations << "foo.#{keyword}(::Object.new)"
158
149
  end
159
150
 
160
151
  it_should_behave_like 'a mutator'
@@ -162,37 +153,49 @@ describe Mutant::Mutator, 'send' do
162
153
  end
163
154
  end
164
155
 
165
- context 'binary operator methods' do
166
- Mutant::BINARY_METHOD_OPERATORS.each do |operator|
167
- let(:source) { "true #{operator} false" }
168
-
169
- let(:mutations) do
170
- mutations = []
171
- mutations << "((false) #{operator} (false))"
172
- mutations << "((nil) #{operator} (false))"
173
- mutations << "((true) #{operator} (true))"
174
- mutations << "((true) #{operator} (nil))"
175
- mutations << 'true'
176
- mutations << 'false'
177
- end
178
-
179
- it_should_behave_like 'a mutator'
180
- end
181
- end
182
-
183
156
  context 'two arguments' do
184
157
  let(:source) { 'foo(nil, nil)' }
185
158
 
186
- let(:mutations) do
159
+ let(:mutations) do
187
160
  mutations = []
188
161
  mutations << 'foo()'
189
162
  mutations << 'foo(nil)'
190
- mutations << 'foo(Object.new, nil)'
191
- mutations << 'foo(nil, Object.new)'
163
+ mutations << 'foo(::Object.new, nil)'
164
+ mutations << 'foo(nil, ::Object.new)'
192
165
  end
193
166
 
194
167
  it_should_behave_like 'a mutator'
195
168
  end
196
169
 
170
+ context 'binary operator methods' do
171
+ Mutant::BINARY_METHOD_OPERATORS.each do |operator|
172
+ context 'on literal scalar arguments' do
173
+ let(:source) { "true #{operator} false" }
174
+
175
+ let(:mutations) do
176
+ mutations = []
177
+ mutations << "false #{operator} false"
178
+ mutations << "nil #{operator} false"
179
+ mutations << "true #{operator} true"
180
+ mutations << "true #{operator} nil"
181
+ mutations << 'true'
182
+ mutations << 'false'
183
+ end
184
+
185
+ it_should_behave_like 'a mutator'
186
+ end
187
+
188
+ context 'on non literal scalar arguments' do
189
+ let(:source) { "left #{operator} right" }
190
+ let(:mutations) do
191
+ mutations = []
192
+ mutations << 'left'
193
+ mutations << 'right'
194
+ end
195
+
196
+ it_should_behave_like 'a mutator'
197
+ end
198
+ end
199
+ end
197
200
  end
198
201
  end
@@ -19,21 +19,6 @@ describe Mutant::Mutator, 'super' do
19
19
  it_should_behave_like 'a mutator'
20
20
  end
21
21
 
22
- context 'with explicit empty arguments and block' do
23
- let(:source) { 'super() { foo; bar }' }
24
-
25
- let(:mutations) do
26
- mutations = []
27
- mutations << 'super() { foo }'
28
- mutations << 'super() { bar }'
29
- mutations << 'super() { }'
30
- mutations << 'super()'
31
- mutations << 'super'
32
- end
33
-
34
- it_should_behave_like 'a mutator'
35
- end
36
-
37
22
  context 'super with arguments' do
38
23
  let(:source) { 'super(foo, bar)' }
39
24
 
@@ -47,22 +32,4 @@ describe Mutant::Mutator, 'super' do
47
32
 
48
33
  it_should_behave_like 'a mutator'
49
34
  end
50
-
51
- context 'super with arguments and block' do
52
- let(:source) { 'super(foo, bar) { foo; bar }' }
53
-
54
- let(:mutations) do
55
- mutations = []
56
- mutations << 'super(foo, bar) { foo; }'
57
- mutations << 'super(foo, bar) { bar; }'
58
- mutations << 'super(foo, bar) { nil }'
59
- mutations << 'super(foo, bar)'
60
- mutations << 'super'
61
- mutations << 'super(foo) { foo; bar }'
62
- mutations << 'super(bar) { foo; bar }'
63
- mutations << 'super() { foo; bar }'
64
- end
65
-
66
- it_should_behave_like 'a mutator'
67
- end
68
35
  end
@@ -9,9 +9,9 @@ describe Mutant::Mutator::Node::While do
9
9
  mutations = []
10
10
  mutations << 'while true; bar; end'
11
11
  mutations << 'while true; foo; end'
12
- mutations << 'while true; nil; end'
12
+ mutations << 'while true; end'
13
13
  mutations << 'while false; foo; bar; end'
14
- mutations << 'while nil; foo; bar; end'
14
+ mutations << 'while nil; foo; bar; end'
15
15
  end
16
16
 
17
17
  it_should_behave_like 'a mutator'
@@ -0,0 +1,38 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Runner::Config, '#subjects' do
4
+ let(:object) { described_class.run(config) }
5
+
6
+ subject { object.subjects }
7
+
8
+ let(:config) do
9
+ mock(
10
+ 'Config',
11
+ :subjects => [mutation_subject],
12
+ :strategy => strategy,
13
+ :reporter => reporter
14
+ )
15
+ end
16
+
17
+ let(:reporter) { mock('Reporter') }
18
+ let(:strategy) { mock('Strategy') }
19
+ let(:mutation_subject) { mock('Mutation subject') }
20
+ let(:subject_runner) { mock('Subject runner') }
21
+
22
+ class DummySubjectRunner
23
+ include Concord::Public.new(:config, :mutation)
24
+
25
+ def self.run(*args); new(*args); end
26
+ end
27
+
28
+ before do
29
+ strategy.stub(:setup)
30
+ strategy.stub(:teardown)
31
+ reporter.stub(:report => reporter)
32
+ stub_const('Mutant::Runner::Subject', DummySubjectRunner)
33
+ end
34
+
35
+ it { should eql([DummySubjectRunner.new(object, mutation_subject)]) }
36
+
37
+ it_should_behave_like 'an idempotent method'
38
+ end
@@ -0,0 +1,53 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Runner::Config, '#success?' do
4
+ subject { object.success? }
5
+
6
+ let(:object) { described_class.run(config) }
7
+
8
+ let(:config) do
9
+ mock(
10
+ 'Config',
11
+ :reporter => reporter,
12
+ :strategy => strategy,
13
+ :subjects => subjects
14
+ )
15
+ end
16
+
17
+ let(:reporter) { mock('Reporter') }
18
+ let(:strategy) { mock('Strategy') }
19
+ let(:subjects) { [subject_a, subject_b] }
20
+ let(:subject_a) { mock('Subject A', :fails? => false) }
21
+ let(:subject_b) { mock('Subject B', :fails? => false) }
22
+
23
+ class DummySubjectRunner
24
+ include Concord::Public.new(:config, :subject)
25
+
26
+ def self.run(*args)
27
+ new(*args)
28
+ end
29
+
30
+ def failed?
31
+ @subject.fails?
32
+ end
33
+ end
34
+
35
+ before do
36
+ stub_const('Mutant::Runner::Subject', DummySubjectRunner)
37
+ reporter.stub(:report => reporter)
38
+ strategy.stub(:setup)
39
+ strategy.stub(:teardown)
40
+ end
41
+
42
+ context 'without failed subjects' do
43
+ it { should be(true) }
44
+ end
45
+
46
+ context 'with failing subjects' do
47
+ before do
48
+ subject_a.stub(:fails? => true)
49
+ end
50
+
51
+ it { should be(false) }
52
+ end
53
+ end
@@ -0,0 +1,33 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Runner, '#failed?' do
4
+ subject { object.failed? }
5
+
6
+ let(:object) { class_under_test.run(config) }
7
+
8
+ let(:config) { mock('Config') }
9
+ let(:class_under_test) do
10
+ success = self.success
11
+
12
+ Class.new(described_class) do
13
+ define_method :success? do
14
+ success
15
+ end
16
+
17
+ define_method :run do
18
+ end
19
+ end
20
+ end
21
+
22
+ context 'when runner is successful' do
23
+ let(:success) { true }
24
+
25
+ it { should be(false) }
26
+ end
27
+
28
+ context 'when runner is NOT successful' do
29
+ let(:success) { false }
30
+
31
+ it { should be(true) }
32
+ end
33
+ end
@@ -0,0 +1,39 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Runner::Mutation, '#killer' do
4
+ let(:object) { described_class.run(config, mutation) }
5
+
6
+ let(:config) do
7
+ mock(
8
+ 'Config',
9
+ :reporter => reporter,
10
+ :strategy => strategy
11
+ )
12
+ end
13
+
14
+ let(:reporter) { mock('Reporter') }
15
+ let(:mutation) { mock('Mutation') }
16
+ let(:strategy) { mock('Strategy') }
17
+ let(:killer) { mock('Killer') }
18
+
19
+ subject { object.killer }
20
+
21
+ before do
22
+ reporter.stub(:report => reporter)
23
+ strategy.stub(:kill => killer)
24
+ end
25
+
26
+ it 'should call configuration to identify strategy' do
27
+ config.should_receive(:strategy).with().and_return(strategy)
28
+ should be(killer)
29
+ end
30
+
31
+ it 'should run killer' do
32
+ strategy.should_receive(:kill).with(mutation).and_return(killer)
33
+ should be(killer)
34
+ end
35
+
36
+ it { should be(killer) }
37
+
38
+ it_should_behave_like 'an idempotent method'
39
+ end
@@ -0,0 +1,49 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Runner::Subject, '#success?' do
4
+ subject { object.success? }
5
+
6
+ let(:object) { described_class.run(config, mutation_subject) }
7
+
8
+ let(:reporter) { mock('Reporter') }
9
+ let(:mutation_subject) { mock('Subject', :map => mutations) }
10
+ let(:config) { mock('Config', :reporter => reporter) }
11
+ let(:mutation_a) { mock('Mutation A', :failed? => false) }
12
+ let(:mutation_b) { mock('Mutation B', :failed? => false) }
13
+ let(:mutations) { [mutation_a, mutation_b] }
14
+
15
+ before do
16
+ reporter.stub(:report => reporter)
17
+ end
18
+
19
+ class DummyMutationRunner
20
+ include Concord::Public.new(:config, :mutation)
21
+
22
+ def self.run(*args)
23
+ new(*args)
24
+ end
25
+
26
+ def failed?
27
+ @mutation.failed?
28
+ end
29
+ end
30
+
31
+ before do
32
+ stub_const('Mutant::Runner::Mutation', DummyMutationRunner)
33
+ end
34
+
35
+ context 'without evil failed mutations' do
36
+ it { should be(true) }
37
+ end
38
+
39
+ context 'with failing noop mutation' do
40
+ end
41
+
42
+ context 'with failing evil mutations' do
43
+ before do
44
+ mutation_a.stub(:failed? => true)
45
+ end
46
+
47
+ it { should be(false) }
48
+ end
49
+ end
@@ -0,0 +1,49 @@
1
+ require 'spec_helper'
2
+
3
+ describe Mutant::Strategy::MethodExpansion, '.run' do
4
+ subject { object.run(name) }
5
+
6
+ let(:object) { described_class }
7
+
8
+ context 'unexpandable and unmapped name' do
9
+ let(:name) { :foo }
10
+
11
+ it { should be(:foo) }
12
+ end
13
+
14
+ context 'expanded name' do
15
+
16
+ context 'predicate' do
17
+ let(:name) { :foo? }
18
+
19
+ it { should be(:foo_predicate) }
20
+ end
21
+
22
+ context 'writer' do
23
+ let(:name) { :foo= }
24
+
25
+ it { should be(:foo_writer) }
26
+ end
27
+
28
+ context 'bang' do
29
+ let(:name) { :foo! }
30
+
31
+ it { should be(:foo_bang) }
32
+ end
33
+
34
+ end
35
+
36
+ context 'operator expansions' do
37
+
38
+ Mutant::OPERATOR_EXPANSIONS.each do |name, expansion|
39
+ context "#{name}" do
40
+ let(:name) { name }
41
+
42
+ it "should expand to #{expansion}" do
43
+ should be(expansion)
44
+ end
45
+ end
46
+ end
47
+
48
+ end
49
+ end