cucumber 0.3.0 → 0.3.1
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/History.txt +26 -1
- data/Manifest.txt +20 -1
- data/config/hoe.rb +5 -4
- data/examples/i18n/hu/Rakefile +6 -0
- data/examples/i18n/hu/features/addition.feature +16 -0
- data/examples/i18n/hu/features/division.feature +9 -0
- data/examples/i18n/hu/features/step_definitons/calculator_steps.rb +25 -0
- data/examples/i18n/hu/lib/calculator.rb +14 -0
- data/examples/i18n/lv/Rakefile +6 -0
- data/examples/i18n/lv/features/addition.feature +16 -0
- data/examples/i18n/lv/features/division.feature +9 -0
- data/examples/i18n/lv/features/step_definitons/calculator_steps.rb +24 -0
- data/examples/i18n/lv/lib/calculator.rb +14 -0
- data/examples/self_test/features/background/failing_background.feature +1 -0
- data/examples/self_test/features/multiline_name.feature +27 -0
- data/examples/self_test/features/search_sample.feature +22 -0
- data/examples/self_test/features/step_definitions/sample_steps.rb +3 -2
- data/examples/tickets/Rakefile +3 -3
- data/examples/tickets/features/236.feature +9 -9
- data/examples/tickets/features/272/hooks.feature +26 -0
- data/examples/tickets/features/272/hooks_steps.rb +53 -0
- data/examples/tickets/features/301/filter_background_tagged_hooks.feature +6 -0
- data/examples/tickets/features/301/filter_background_tagged_hooks_steps.rb +12 -0
- data/examples/tickets/features/306/only_background.feature +4 -0
- data/features/background.feature +2 -1
- data/features/cucumber_cli.feature +88 -12
- data/features/cucumber_cli_outlines.feature +32 -0
- data/features/custom_formatter.feature +2 -2
- data/features/multiline_names.feature +43 -0
- data/features/report_called_undefined_steps.feature +1 -1
- data/features/usage.feature +13 -4
- data/lib/cucumber/ast/background.rb +10 -13
- data/lib/cucumber/ast/feature.rb +5 -0
- data/lib/cucumber/ast/feature_element.rb +23 -12
- data/lib/cucumber/ast/outline_table.rb +10 -0
- data/lib/cucumber/ast/py_string.rb +5 -1
- data/lib/cucumber/ast/scenario.rb +17 -6
- data/lib/cucumber/ast/scenario_outline.rb +1 -6
- data/lib/cucumber/ast/step.rb +6 -3
- data/lib/cucumber/ast/step_collection.rb +9 -1
- data/lib/cucumber/ast/table.rb +8 -0
- data/lib/cucumber/ast/visitor.rb +2 -2
- data/lib/cucumber/cli/configuration.rb +15 -14
- data/lib/cucumber/formatter/console.rb +1 -1
- data/lib/cucumber/formatter/html.rb +1 -1
- data/lib/cucumber/formatter/pretty.rb +7 -8
- data/lib/cucumber/languages.yml +30 -0
- data/lib/cucumber/parser/feature.rb +214 -14
- data/lib/cucumber/parser/feature.tt +44 -14
- data/lib/cucumber/parser/treetop_ext.rb +3 -3
- data/lib/cucumber/rails/world.rb +6 -0
- data/lib/cucumber/step_mother.rb +2 -1
- data/lib/cucumber/version.rb +1 -1
- data/lib/cucumber/world.rb +2 -2
- data/rails_generators/cucumber/templates/paths.rb +11 -13
- data/rails_generators/feature/feature_generator.rb +1 -1
- data/spec/cucumber/ast/feature_element_spec.rb +40 -0
- data/spec/cucumber/ast/py_string_spec.rb +4 -0
- data/spec/cucumber/ast/table_spec.rb +20 -4
- data/spec/cucumber/ast/visitor_spec.rb +27 -0
- data/spec/cucumber/cli/configuration_spec.rb +4 -13
- data/spec/cucumber/cli/main_spec.rb +55 -153
- data/spec/cucumber/parser/feature_parser_spec.rb +79 -0
- data/spec/cucumber/step_mother_spec.rb +12 -5
- metadata +22 -13
- data/spec/cucumber/formatters/profile_formatter_spec.rb +0 -198
data/features/background.feature
CHANGED
@@ -72,6 +72,7 @@ Feature: backgrounds
|
|
72
72
|
When I run cucumber -q features/background/failing_background.feature --require features
|
73
73
|
Then it should fail with
|
74
74
|
"""
|
75
|
+
@after_file
|
75
76
|
Feature: Failing background sample
|
76
77
|
|
77
78
|
Background:
|
@@ -79,7 +80,7 @@ Feature: backgrounds
|
|
79
80
|
FAIL (RuntimeError)
|
80
81
|
./features/step_definitions/sample_steps.rb:2:in `flunker'
|
81
82
|
./features/step_definitions/sample_steps.rb:16:in `/^failing without a table$/'
|
82
|
-
features/background/failing_background.feature:
|
83
|
+
features/background/failing_background.feature:5:in `Given failing without a table'
|
83
84
|
And '10' cukes
|
84
85
|
|
85
86
|
Scenario: failing background
|
@@ -191,6 +191,36 @@ Feature: Cucumber command line
|
|
191
191
|
When I stop procrastinating
|
192
192
|
And there is world peace
|
193
193
|
|
194
|
+
Feature: multiline
|
195
|
+
|
196
|
+
Background: I'm a multiline name
|
197
|
+
which goes on and on and on for three lines
|
198
|
+
yawn
|
199
|
+
Given passing without a table
|
200
|
+
|
201
|
+
Scenario: I'm a multiline name
|
202
|
+
which goes on and on and on for three lines
|
203
|
+
yawn
|
204
|
+
Given passing without a table
|
205
|
+
|
206
|
+
Scenario Outline: I'm a multiline name
|
207
|
+
which goes on and on and on for three lines
|
208
|
+
yawn
|
209
|
+
Given <state> without a table
|
210
|
+
|
211
|
+
Examples:
|
212
|
+
| state |
|
213
|
+
| passing |
|
214
|
+
|
215
|
+
Scenario Outline: name
|
216
|
+
Given <state> without a table
|
217
|
+
|
218
|
+
Examples: I'm a multiline name
|
219
|
+
which goes on and on and on for three lines
|
220
|
+
yawn
|
221
|
+
| state |
|
222
|
+
| passing |
|
223
|
+
|
194
224
|
Feature: Outline Sample
|
195
225
|
|
196
226
|
Scenario: I have no steps
|
@@ -229,6 +259,31 @@ Feature: Cucumber command line
|
|
229
259
|
hello
|
230
260
|
\"\"\"
|
231
261
|
|
262
|
+
Feature: search examples
|
263
|
+
|
264
|
+
Background: Hantu Pisang background match
|
265
|
+
Given passing without a table
|
266
|
+
|
267
|
+
Scenario: should match Hantu Pisang
|
268
|
+
Given passing without a table
|
269
|
+
|
270
|
+
Scenario: Ignore me
|
271
|
+
Given failing without a table
|
272
|
+
|
273
|
+
Scenario Outline: Ignore me
|
274
|
+
Given <state> without a table
|
275
|
+
|
276
|
+
Examples:
|
277
|
+
| state |
|
278
|
+
| failing |
|
279
|
+
|
280
|
+
Scenario Outline: Hantu Pisang match
|
281
|
+
Given <state> without a table
|
282
|
+
|
283
|
+
Examples:
|
284
|
+
| state |
|
285
|
+
| passing |
|
286
|
+
|
232
287
|
Feature: undefined multiline args
|
233
288
|
|
234
289
|
Scenario: pystring
|
@@ -242,8 +297,8 @@ Feature: Cucumber command line
|
|
242
297
|
| table |
|
243
298
|
| example |
|
244
299
|
|
245
|
-
|
246
|
-
|
300
|
+
21 scenarios
|
301
|
+
26 skipped steps
|
247
302
|
9 undefined steps
|
248
303
|
|
249
304
|
"""
|
@@ -274,24 +329,45 @@ Feature: Cucumber command line
|
|
274
329
|
|
275
330
|
"""
|
276
331
|
|
277
|
-
Scenario: Run
|
278
|
-
When I run cucumber --
|
332
|
+
Scenario: Run feature elements which matches a name using --name
|
333
|
+
When I run cucumber --name Pisang -q features/
|
279
334
|
Then it should pass with
|
280
335
|
"""
|
281
|
-
|
282
|
-
Feature: Sample
|
336
|
+
Feature: search examples
|
283
337
|
|
284
|
-
|
285
|
-
|
286
|
-
Given passing
|
287
|
-
| a | b |
|
288
|
-
| c | d |
|
338
|
+
Background: Hantu Pisang background match
|
339
|
+
Given passing without a table
|
289
340
|
|
290
|
-
|
341
|
+
Scenario: should match Hantu Pisang
|
342
|
+
Given passing without a table
|
343
|
+
|
344
|
+
Scenario Outline: Hantu Pisang match
|
345
|
+
Given <state> without a table
|
346
|
+
|
347
|
+
Examples:
|
348
|
+
| state |
|
349
|
+
| passing |
|
350
|
+
|
351
|
+
2 scenarios
|
352
|
+
4 passed steps
|
353
|
+
|
354
|
+
"""
|
355
|
+
|
356
|
+
Scenario: Run a single background which matches a name using --name
|
357
|
+
When I run cucumber --name 'Hantu Pisang background' -q features/
|
358
|
+
Then it should pass with
|
359
|
+
"""
|
360
|
+
Feature: search examples
|
361
|
+
|
362
|
+
Background: Hantu Pisang background match
|
363
|
+
Given passing without a table
|
364
|
+
|
365
|
+
0 scenarios
|
291
366
|
1 passed step
|
292
367
|
|
293
368
|
"""
|
294
369
|
|
370
|
+
|
295
371
|
Scenario: Run with a tag that exists on 2 scenarios
|
296
372
|
When I run cucumber -q features --tags three
|
297
373
|
Then it should pass with
|
@@ -2,6 +2,38 @@ Feature: Cucumber command line
|
|
2
2
|
In order to write better software
|
3
3
|
Developers should be able to execute requirements as tests
|
4
4
|
|
5
|
+
Scenario: Run scenario outline with filtering on outline name
|
6
|
+
When I run cucumber -q features --name "Test state"
|
7
|
+
Then it should fail with
|
8
|
+
"""
|
9
|
+
Feature: Outline Sample
|
10
|
+
|
11
|
+
Scenario Outline: Test state
|
12
|
+
Given <state> without a table
|
13
|
+
Given <other_state> without a table
|
14
|
+
|
15
|
+
Examples: Rainbow colours
|
16
|
+
| state | other_state |
|
17
|
+
| missing | passing |
|
18
|
+
| passing | passing |
|
19
|
+
| failing | passing |
|
20
|
+
FAIL (RuntimeError)
|
21
|
+
./features/step_definitions/sample_steps.rb:2:in `flunker'
|
22
|
+
./features/step_definitions/sample_steps.rb:16:in `/^failing without a table$/'
|
23
|
+
features/outline_sample.feature:6:in `Given <state> without a table'
|
24
|
+
|
25
|
+
Examples: Only passing
|
26
|
+
| state | other_state |
|
27
|
+
| passing | passing |
|
28
|
+
|
29
|
+
4 scenarios
|
30
|
+
1 failed step
|
31
|
+
2 skipped steps
|
32
|
+
1 undefined step
|
33
|
+
4 passed steps
|
34
|
+
|
35
|
+
"""
|
36
|
+
|
5
37
|
Scenario: Run scenario outline steps only
|
6
38
|
When I run cucumber -q features/outline_sample.feature:7
|
7
39
|
Then it should fail with
|
@@ -4,8 +4,8 @@ Feature: Custom Formatter
|
|
4
4
|
When I run cucumber --format Tag::Count features
|
5
5
|
Then it should fail with
|
6
6
|
"""
|
7
|
-
| four | lots | one | three | two |
|
8
|
-
| 1 | 1 | 1 | 2 | 1 |
|
7
|
+
| after_file | four | lots | one | three | two |
|
8
|
+
| 1 | 1 | 1 | 1 | 2 | 1 |
|
9
9
|
|
10
10
|
"""
|
11
11
|
|
@@ -0,0 +1,43 @@
|
|
1
|
+
Feature: Multiline description names
|
2
|
+
In order to accurately document feature elements
|
3
|
+
As a cucumberist
|
4
|
+
I want to have multiline names
|
5
|
+
|
6
|
+
Scenario: multiline scenario
|
7
|
+
When I run cucumber features/multiline_name.feature --no-snippets
|
8
|
+
Then it should pass with
|
9
|
+
"""
|
10
|
+
Feature: multiline
|
11
|
+
|
12
|
+
Background: I'm a multiline name # features/multiline_name.feature:3
|
13
|
+
which goes on and on and on for three lines
|
14
|
+
yawn
|
15
|
+
Given passing without a table # features/step_definitions/sample_steps.rb:12
|
16
|
+
|
17
|
+
Scenario: I'm a multiline name # features/multiline_name.feature:8
|
18
|
+
which goes on and on and on for three lines
|
19
|
+
yawn
|
20
|
+
Given passing without a table # features/step_definitions/sample_steps.rb:12
|
21
|
+
|
22
|
+
Scenario Outline: I'm a multiline name # features/multiline_name.feature:13
|
23
|
+
which goes on and on and on for three lines
|
24
|
+
yawn
|
25
|
+
Given <state> without a table # features/step_definitions/sample_steps.rb:12
|
26
|
+
|
27
|
+
Examples:
|
28
|
+
| state |
|
29
|
+
| passing |
|
30
|
+
|
31
|
+
Scenario Outline: name # features/multiline_name.feature:21
|
32
|
+
Given <state> without a table # features/step_definitions/sample_steps.rb:12
|
33
|
+
|
34
|
+
Examples: I'm a multiline name
|
35
|
+
which goes on and on and on for three lines
|
36
|
+
yawn
|
37
|
+
| state |
|
38
|
+
| passing |
|
39
|
+
|
40
|
+
3 scenarios
|
41
|
+
6 passed steps
|
42
|
+
|
43
|
+
"""
|
@@ -23,7 +23,7 @@ Feature: Cucumber command line
|
|
23
23
|
2 scenarios
|
24
24
|
2 undefined steps
|
25
25
|
|
26
|
-
You can implement step definitions for
|
26
|
+
You can implement step definitions for undefined steps with these snippets:
|
27
27
|
|
28
28
|
Given /^this does not exist$/ do
|
29
29
|
pending
|
data/features/usage.feature
CHANGED
@@ -9,18 +9,27 @@ Feature: Cucumber command line
|
|
9
9
|
"""
|
10
10
|
/^passing without a table$/ # features/step_definitions/sample_steps.rb:12
|
11
11
|
Given passing without a table # features/background/failing_background_after_success.feature:4
|
12
|
+
Given passing without a table # features/multiline_name.feature:6
|
13
|
+
Given passing without a table # features/multiline_name.feature:11
|
14
|
+
Given <state> without a table # features/multiline_name.feature:16
|
15
|
+
Given <state> without a table # features/multiline_name.feature:22
|
12
16
|
Given <state> without a table # features/outline_sample.feature:6
|
13
17
|
Given <other_state> without a table # features/outline_sample.feature:7
|
18
|
+
Given passing without a table # features/search_sample.feature:4
|
19
|
+
Given passing without a table # features/search_sample.feature:7
|
20
|
+
Given <state> without a table # features/search_sample.feature:19
|
14
21
|
/^failing without a table$/ # features/step_definitions/sample_steps.rb:15
|
15
|
-
Given failing without a table # features/background/failing_background.feature:
|
22
|
+
Given failing without a table # features/background/failing_background.feature:5
|
16
23
|
Given failing without a table # features/background/scenario_outline_failing_background.feature:4
|
24
|
+
Given failing without a table # features/search_sample.feature:10
|
25
|
+
Given <state> without a table # features/search_sample.feature:13
|
17
26
|
/^a step definition that calls an undefined step$/ # features/step_definitions/sample_steps.rb:19
|
18
27
|
Given a step definition that calls an undefined step # features/call_undefined_step_from_step_def.feature:4
|
19
28
|
/^call step "(.*)"$/ # features/step_definitions/sample_steps.rb:23
|
20
29
|
Given call step "a step definition that calls an undefined step" # features/call_undefined_step_from_step_def.feature:7
|
21
30
|
/^'(.+)' cukes$/ # features/step_definitions/sample_steps.rb:27
|
22
31
|
Given '10' cukes # features/background/background_with_name.feature:4
|
23
|
-
And '10' cukes # features/background/failing_background.feature:
|
32
|
+
And '10' cukes # features/background/failing_background.feature:6
|
24
33
|
Given '10' cukes # features/background/passing_background.feature:4
|
25
34
|
Given '10' cukes # features/background/scenario_outline_passing_background.feature:4
|
26
35
|
Given '2' cukes # features/tons_of_cukes.feature:4
|
@@ -74,8 +83,8 @@ Feature: Cucumber command line
|
|
74
83
|
Given '2' cukes # features/tons_of_cukes.feature:52
|
75
84
|
/^I should have '(.+)' cukes$/ # features/step_definitions/sample_steps.rb:31
|
76
85
|
Then I should have '10' cukes # features/background/background_with_name.feature:7
|
77
|
-
Then I should have '10' cukes # features/background/failing_background.feature:
|
78
|
-
Then I should have '10' cukes # features/background/failing_background.feature:
|
86
|
+
Then I should have '10' cukes # features/background/failing_background.feature:9
|
87
|
+
Then I should have '10' cukes # features/background/failing_background.feature:12
|
79
88
|
Then I should have '10' cukes # features/background/passing_background.feature:7
|
80
89
|
Then I should have '10' cukes # features/background/passing_background.feature:10
|
81
90
|
Then I should have '10' cukes # features/background/pending_background.feature:7
|
@@ -4,12 +4,13 @@ module Cucumber
|
|
4
4
|
module Ast
|
5
5
|
class Background
|
6
6
|
include FeatureElement
|
7
|
-
|
7
|
+
attr_reader :feature_elements
|
8
8
|
|
9
9
|
def initialize(comment, line, keyword, name, steps)
|
10
10
|
@comment, @line, @keyword, @name, @steps = comment, line, keyword, name, StepCollection.new(steps)
|
11
11
|
attach_steps(steps)
|
12
12
|
@step_invocations = @steps.step_invocations(true)
|
13
|
+
@feature_elements = []
|
13
14
|
end
|
14
15
|
|
15
16
|
def step_collection(step_invocations)
|
@@ -23,32 +24,28 @@ module Cucumber
|
|
23
24
|
|
24
25
|
def accept(visitor)
|
25
26
|
visitor.visit_comment(@comment)
|
26
|
-
visitor.visit_background_name(@keyword, @name, file_colon_line(@line), source_indent(
|
27
|
-
visitor.step_mother.before(
|
27
|
+
visitor.visit_background_name(@keyword, @name, file_colon_line(@line), source_indent(first_line_length))
|
28
|
+
visitor.step_mother.before(hook_context)
|
28
29
|
visitor.visit_steps(@step_invocations)
|
29
30
|
@failed = @step_invocations.detect{|step_invocation| step_invocation.exception}
|
30
|
-
visitor.step_mother.after(
|
31
|
+
visitor.step_mother.after(hook_context) if @failed
|
31
32
|
end
|
32
33
|
|
33
34
|
def accept_hook?(hook)
|
34
|
-
|
35
|
-
# the current implementation. All hooks will be executed. This is because of the line
|
36
|
-
# visitor.step_mother.before(self)
|
37
|
-
# in the #accept method above. Instead, we should really be passing the first scenario
|
38
|
-
# here. We currently don't have access to that, so a refactoring is in order to make that happen.
|
39
|
-
true
|
35
|
+
false
|
40
36
|
end
|
41
37
|
|
42
38
|
def failed?
|
43
39
|
@failed
|
44
40
|
end
|
45
41
|
|
46
|
-
def
|
47
|
-
@
|
42
|
+
def hook_context
|
43
|
+
@feature_elements.first || self
|
48
44
|
end
|
49
45
|
|
50
46
|
def to_sexp
|
51
47
|
sexp = [:background, @line, @keyword]
|
48
|
+
sexp += [@name] unless @name.empty?
|
52
49
|
comment = @comment.to_sexp
|
53
50
|
sexp += [comment] if comment
|
54
51
|
steps = @steps.to_sexp
|
@@ -57,4 +54,4 @@ module Cucumber
|
|
57
54
|
end
|
58
55
|
end
|
59
56
|
end
|
60
|
-
end
|
57
|
+
end
|
data/lib/cucumber/ast/feature.rb
CHANGED
@@ -8,6 +8,7 @@ module Cucumber
|
|
8
8
|
def initialize(background, comment, tags, name, feature_elements)
|
9
9
|
@background, @comment, @tags, @name, @feature_elements = background, comment, tags, name, feature_elements
|
10
10
|
|
11
|
+
background.feature = self if background
|
11
12
|
@feature_elements.each do |feature_element|
|
12
13
|
feature_element.feature = self
|
13
14
|
end
|
@@ -23,6 +24,10 @@ module Cucumber
|
|
23
24
|
end
|
24
25
|
end
|
25
26
|
|
27
|
+
def accept_hook?(hook)
|
28
|
+
@tags.accept_hook?(hook)
|
29
|
+
end
|
30
|
+
|
26
31
|
def next_feature_element(feature_element, &proc)
|
27
32
|
index = @feature_elements.index(feature_element)
|
28
33
|
next_one = @feature_elements[index+1]
|
@@ -1,5 +1,9 @@
|
|
1
|
+
require 'enumerator'
|
2
|
+
|
1
3
|
module Cucumber
|
2
4
|
module FeatureElement
|
5
|
+
attr_writer :feature
|
6
|
+
|
3
7
|
def attach_steps(steps)
|
4
8
|
steps.each {|step| step.feature_element = self}
|
5
9
|
end
|
@@ -9,13 +13,27 @@ module Cucumber
|
|
9
13
|
end
|
10
14
|
|
11
15
|
def text_length
|
12
|
-
|
16
|
+
name_line_lengths.max
|
17
|
+
end
|
18
|
+
|
19
|
+
def first_line_length
|
20
|
+
name_line_lengths[0]
|
13
21
|
end
|
14
22
|
|
15
|
-
def
|
16
|
-
|
23
|
+
def name_line_lengths
|
24
|
+
if @name.empty?
|
25
|
+
[@keyword.jlength]
|
26
|
+
else
|
27
|
+
@name.split("\n").enum_for(:each_with_index).map do |line, line_number|
|
28
|
+
line_number == 0 ? @keyword.jlength + line.jlength : line.jlength + Ast::Step::INDENT - 1 # We -1 as names which are not keyword lines are missing a space between keyword and name
|
29
|
+
end
|
30
|
+
end
|
17
31
|
end
|
18
32
|
|
33
|
+
def matches_scenario_names?(scenario_name_regexps)
|
34
|
+
scenario_name_regexps.detect{|name| name =~ @name}
|
35
|
+
end
|
36
|
+
|
19
37
|
def backtrace_line(name = "#{@keyword} #{@name}", line = @line)
|
20
38
|
@feature.backtrace_line(name, line) if @feature
|
21
39
|
end
|
@@ -29,14 +47,7 @@ module Cucumber
|
|
29
47
|
end
|
30
48
|
|
31
49
|
def accept_hook?(hook)
|
32
|
-
@tags.accept_hook?(hook)
|
33
|
-
end
|
34
|
-
|
35
|
-
# TODO: Remove when we use StepCollection everywhere
|
36
|
-
def previous_step(step)
|
37
|
-
i = @steps.index(step) || -1
|
38
|
-
@steps[i-1]
|
50
|
+
@tags.accept_hook?(hook) || @feature.accept_hook?(hook)
|
39
51
|
end
|
40
|
-
|
41
52
|
end
|
42
|
-
end
|
53
|
+
end
|