cuke_modeler 3.3.0 → 3.4.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.
Files changed (38) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +7 -1
  3. data/cuke_modeler.gemspec +23 -14
  4. data/lib/cuke_modeler.rb +1 -1
  5. data/lib/cuke_modeler/adapters/gherkin_10_adapter.rb +2 -1
  6. data/lib/cuke_modeler/adapters/gherkin_11_adapter.rb +2 -1
  7. data/lib/cuke_modeler/adapters/gherkin_12_adapter.rb +2 -1
  8. data/lib/cuke_modeler/adapters/gherkin_13_adapter.rb +2 -1
  9. data/lib/cuke_modeler/adapters/gherkin_14_adapter.rb +2 -1
  10. data/lib/cuke_modeler/adapters/gherkin_15_adapter.rb +2 -1
  11. data/lib/cuke_modeler/adapters/gherkin_9_adapter.rb +261 -242
  12. data/lib/cuke_modeler/containing.rb +31 -89
  13. data/lib/cuke_modeler/described.rb +40 -1
  14. data/lib/cuke_modeler/models/background.rb +11 -11
  15. data/lib/cuke_modeler/models/cell.rb +13 -7
  16. data/lib/cuke_modeler/models/comment.rb +5 -5
  17. data/lib/cuke_modeler/models/directory.rb +13 -17
  18. data/lib/cuke_modeler/models/doc_string.rb +10 -7
  19. data/lib/cuke_modeler/models/example.rb +63 -45
  20. data/lib/cuke_modeler/models/feature.rb +23 -16
  21. data/lib/cuke_modeler/models/feature_file.rb +5 -7
  22. data/lib/cuke_modeler/models/model.rb +2 -1
  23. data/lib/cuke_modeler/models/outline.rb +19 -14
  24. data/lib/cuke_modeler/models/row.rb +10 -7
  25. data/lib/cuke_modeler/models/rule.rb +11 -9
  26. data/lib/cuke_modeler/models/scenario.rb +17 -12
  27. data/lib/cuke_modeler/models/step.rb +40 -18
  28. data/lib/cuke_modeler/models/table.rb +9 -6
  29. data/lib/cuke_modeler/models/tag.rb +9 -5
  30. data/lib/cuke_modeler/named.rb +5 -1
  31. data/lib/cuke_modeler/nested.rb +22 -18
  32. data/lib/cuke_modeler/parsed.rb +8 -0
  33. data/lib/cuke_modeler/parsing.rb +36 -26
  34. data/lib/cuke_modeler/sourceable.rb +8 -0
  35. data/lib/cuke_modeler/stepped.rb +8 -0
  36. data/lib/cuke_modeler/taggable.rb +9 -1
  37. data/lib/cuke_modeler/version.rb +1 -1
  38. metadata +53 -33
@@ -18,10 +18,10 @@ module CukeModeler
18
18
  def initialize(source_text = nil)
19
19
  super(source_text)
20
20
 
21
- if source_text
22
- parsed_tag_data = parse_source(source_text)
23
- populate_tag(self, parsed_tag_data)
24
- end
21
+ return unless source_text
22
+
23
+ parsed_tag_data = parse_source(source_text)
24
+ populate_tag(self, parsed_tag_data)
25
25
  end
26
26
 
27
27
  # Returns a string representation of this model. For a tag model,
@@ -38,10 +38,14 @@ module CukeModeler
38
38
  base_file_string = "\n#{dialect_feature_keyword}: Fake feature to parse"
39
39
  source_text = "# language: #{Parsing.dialect}\n" + source_text + base_file_string
40
40
 
41
- parsed_file = Parsing::parse_text(source_text, 'cuke_modeler_stand_alone_tag.feature')
41
+ parsed_file = Parsing.parse_text(source_text, 'cuke_modeler_stand_alone_tag.feature')
42
42
 
43
43
  parsed_file['feature']['tags'].first
44
44
  end
45
45
 
46
+ def populate_name(model, parsed_model_data)
47
+ model.name = parsed_model_data['name']
48
+ end
49
+
46
50
  end
47
51
  end
@@ -13,7 +13,11 @@ module CukeModeler
13
13
 
14
14
 
15
15
  def name_output_string
16
- (name.nil? || name.empty?) ? '' : " #{name}"
16
+ name.nil? || name.empty? ? '' : " #{name}"
17
+ end
18
+
19
+ def populate_name(model, parsed_model_data)
20
+ model.name = parsed_model_data['name']
17
21
  end
18
22
 
19
23
  end
@@ -12,30 +12,34 @@ module CukeModeler
12
12
 
13
13
  # Returns the ancestor model of this model that matches the given type.
14
14
  def get_ancestor(ancestor_type)
15
- target_type = {:directory => [Directory],
16
- :feature_file => [FeatureFile],
17
- :feature => [Feature],
18
- :test => [Scenario, Outline, Background],
19
- :background => [Background],
20
- :scenario => [Scenario],
21
- :outline => [Outline],
22
- :step => [Step],
23
- :table => [Table],
24
- :example => [Example],
25
- :row => [Row]
26
- }[ancestor_type]
15
+ target_classes = classes_for_type(ancestor_type)
27
16
 
28
- raise(ArgumentError, "Unknown ancestor type '#{ancestor_type}'.") if target_type.nil?
17
+ raise(ArgumentError, "Unknown ancestor type '#{ancestor_type}'.") if target_classes.nil?
29
18
 
19
+ ancestor = parent_model
20
+ ancestor = ancestor.parent_model until target_classes.include?(ancestor.class) || ancestor.nil?
30
21
 
31
- ancestor = self.parent_model
22
+ ancestor
23
+ end
32
24
 
33
- until target_type.include?(ancestor.class) || ancestor.nil?
34
- ancestor = ancestor.parent_model
35
- end
36
25
 
26
+ private
37
27
 
38
- ancestor
28
+
29
+ def classes_for_type(type)
30
+ {
31
+ directory: [Directory],
32
+ feature_file: [FeatureFile],
33
+ feature: [Feature],
34
+ test: [Scenario, Outline, Background],
35
+ background: [Background],
36
+ scenario: [Scenario],
37
+ outline: [Outline],
38
+ step: [Step],
39
+ table: [Table],
40
+ example: [Example],
41
+ row: [Row]
42
+ }[type]
39
43
  end
40
44
 
41
45
  end
@@ -8,5 +8,13 @@ module CukeModeler
8
8
  # The parsing data for this element that was generated by the parsing engine (i.e. the *gherkin* gem)
9
9
  attr_accessor :parsing_data
10
10
 
11
+
12
+ private
13
+
14
+
15
+ def populate_parsing_data(model, parsed_model_data)
16
+ model.parsing_data = parsed_model_data['cuke_modeler_parsing_data']
17
+ end
18
+
11
19
  end
12
20
  end
@@ -1,13 +1,6 @@
1
1
  # Have to at least load some version of the gem before which version of the gem has been loaded can
2
- # be determined and the rest of the needed files can be loaded. The entry points vary across versions,
3
- # so try them all until one of them works.
4
- begin
5
- # Gherkin 9.x
6
- require 'gherkin'
7
- rescue LoadError => e
8
- # Add other entry points again if things change again
9
- raise e
10
- end
2
+ # be determined and the rest of the needed files can be loaded.
3
+ require 'gherkin'
11
4
 
12
5
 
13
6
  # The *cucumber-gherkin* gem loads differently and has different grammar rules across major versions. Parsing
@@ -16,12 +9,16 @@ end
16
9
  gherkin_version = Gem.loaded_specs['cucumber-gherkin'].version.version
17
10
  gherkin_major_version = gherkin_version.match(/^(\d+)\./)[1].to_i
18
11
 
12
+ # Previous versions of the gem did not use the conventional entry point, so I'm leaving this here in case it
13
+ # changes again
14
+ # rubocop:disable Lint/EmptyWhen
19
15
  case gherkin_major_version
20
16
  when 9, 10, 11, 12, 13, 14, 15
21
17
  # Currently nothing else to load beyond the entry point to the gem
22
18
  else
23
19
  raise("Unknown Gherkin version: '#{gherkin_version}'")
24
20
  end
21
+ # rubocop:enable Lint/EmptyWhen
25
22
 
26
23
  require "cuke_modeler/adapters/gherkin_#{gherkin_major_version}_adapter"
27
24
 
@@ -45,18 +42,16 @@ module CukeModeler
45
42
 
46
43
  # The dialects currently known by the gherkin gem
47
44
  def dialects
48
- unless @dialects
49
- @dialects = Gherkin::DIALECTS
50
- end
51
-
52
- @dialects
45
+ @dialects ||= Gherkin::DIALECTS
53
46
  end
54
47
 
55
48
  # Parses the Cucumber feature given in *source_text* and returns a hash representation of
56
49
  # its logical structure. This is a standardized AST that should remain consistent across
57
50
  # different versions of `cucumber-gherkin`
58
51
  def parse_text(source_text, filename = 'cuke_modeler_fake_file.feature')
59
- raise(ArgumentError, "Text to parse must be a String but got #{source_text.class}") unless source_text.is_a?(String)
52
+ unless source_text.is_a?(String)
53
+ raise(ArgumentError, "Text to parse must be a String but got #{source_text.class}")
54
+ end
60
55
 
61
56
  begin
62
57
  parsed_result = parsing_method(source_text.encode('UTF-8'), filename)
@@ -71,13 +66,20 @@ module CukeModeler
71
66
  gherkin_version = Gem.loaded_specs['cucumber-gherkin'].version.version
72
67
  gherkin_major_version = gherkin_version.match(/^(\d+)\./)[1].to_i
73
68
 
69
+ # Previous versions of the gem had more variation between their parsing methods and so it was more
70
+ # understandable to have different methods instead of a single method with lots of conditional statements
71
+ # inside of it, so I'm leaving this here in case it changes again
72
+ # rubocop:disable Lint/DuplicateMethods
74
73
  case gherkin_major_version
75
74
  when 13, 14, 15
76
- # todo - make these methods private?
75
+ # TODO: make these methods private?
77
76
  # NOT A PART OF THE PUBLIC API
78
77
  # The method to use for parsing Gherkin text
79
78
  def parsing_method(source_text, filename)
80
- messages = Gherkin.from_source(filename, source_text, { :include_gherkin_document => true }).to_a.map(&:to_hash)
79
+ messages = Gherkin.from_source(filename,
80
+ source_text,
81
+ { include_gherkin_document: true })
82
+ .to_a.map(&:to_hash)
81
83
 
82
84
  error_message = messages.find { |message| message[:parse_error] }
83
85
  gherkin_ast_message = messages.find { |message| message[:gherkin_document] }
@@ -87,33 +89,39 @@ module CukeModeler
87
89
  gherkin_ast_message[:gherkin_document]
88
90
  end
89
91
  when 12
90
- # todo - make these methods private?
92
+ # TODO: make these methods private?
91
93
  # NOT A PART OF THE PUBLIC API
92
94
  # The method to use for parsing Gherkin text
93
95
  def parsing_method(source_text, filename)
94
- messages = Gherkin.from_source(filename, source_text, { :include_gherkin_document => true }).to_a.map(&:to_hash)
96
+ messages = Gherkin.from_source(filename,
97
+ source_text,
98
+ { include_gherkin_document: true })
99
+ .to_a.map(&:to_hash)
95
100
 
96
101
  potential_error_message = messages.find { |message| message[:attachment] }
97
102
  gherkin_ast_message = messages.find { |message| message[:gherkin_document] }
98
103
 
99
- if potential_error_message
100
- raise potential_error_message[:attachment][:body] if potential_error_message[:attachment][:body] =~ /expected.*got/
104
+ if potential_error_message && potential_error_message[:attachment][:body] =~ /expected.*got/
105
+ raise potential_error_message[:attachment][:body]
101
106
  end
102
107
 
103
108
  gherkin_ast_message[:gherkin_document]
104
109
  end
105
110
  when 9, 10, 11
106
- # todo - make these methods private?
111
+ # TODO: make these methods private?
107
112
  # NOT A PART OF THE PUBLIC API
108
113
  # The method to use for parsing Gherkin text
109
114
  def parsing_method(source_text, filename)
110
- messages = Gherkin.from_source(filename, source_text, { :include_gherkin_document => true }).to_a.map(&:to_hash)
115
+ messages = Gherkin.from_source(filename,
116
+ source_text,
117
+ { include_gherkin_document: true })
118
+ .to_a.map(&:to_hash)
111
119
 
112
120
  potential_error_message = messages.find { |message| message[:attachment] }
113
121
  gherkin_ast_message = messages.find { |message| message[:gherkin_document] }
114
122
 
115
- if potential_error_message
116
- raise potential_error_message[:attachment][:text] if potential_error_message[:attachment][:text] =~ /expected.*got/
123
+ if potential_error_message && potential_error_message[:attachment][:text] =~ /expected.*got/
124
+ raise potential_error_message[:attachment][:text]
117
125
  end
118
126
 
119
127
  gherkin_ast_message[:gherkin_document]
@@ -121,6 +129,7 @@ module CukeModeler
121
129
  else
122
130
  raise("Unknown Gherkin version: '#{gherkin_version}'")
123
131
  end
132
+ # rubocop:enable Lint/DuplicateMethods
124
133
 
125
134
  # NOT A PART OF THE PUBLIC API
126
135
  # The adapter to use when converting an AST to a standard internal shape
@@ -143,7 +152,8 @@ module CukeModeler
143
152
  end
144
153
 
145
154
  def dialect_outline_keyword
146
- get_word(Parsing.dialects[Parsing.dialect]['scenarioOutline'] || Parsing.dialects[Parsing.dialect]['scenario_outline'])
155
+ get_word(Parsing.dialects[Parsing.dialect]['scenarioOutline'] ||
156
+ Parsing.dialects[Parsing.dialect]['scenario_outline'])
147
157
  end
148
158
 
149
159
  def dialect_step_keyword
@@ -9,5 +9,13 @@ module CukeModeler
9
9
  # The line number where the element began in the source code
10
10
  attr_accessor :source_line
11
11
 
12
+
13
+ private
14
+
15
+
16
+ def populate_source_line(model, parsed_model_data)
17
+ model.source_line = parsed_model_data['line']
18
+ end
19
+
12
20
  end
13
21
  end
@@ -21,5 +21,13 @@ module CukeModeler
21
21
  step.to_s.split("\n").collect { |line| " #{line}" }.join("\n")
22
22
  end
23
23
 
24
+ def populate_steps(model, parsed_model_data)
25
+ return unless parsed_model_data['steps']
26
+
27
+ parsed_model_data['steps'].each do |step_data|
28
+ model.steps << build_child_model(Step, step_data)
29
+ end
30
+ end
31
+
24
32
  end
25
33
  end
@@ -25,7 +25,15 @@ module CukeModeler
25
25
 
26
26
 
27
27
  def tag_output_string
28
- tags.collect { |tag| tag.name }.join(' ')
28
+ tags.map(&:name).join(' ')
29
+ end
30
+
31
+ def populate_tags(model, parsed_model_data)
32
+ return unless parsed_model_data['tags']
33
+
34
+ parsed_model_data['tags'].each do |tag|
35
+ model.tags << build_child_model(Tag, tag)
36
+ end
29
37
  end
30
38
 
31
39
  end
@@ -1,4 +1,4 @@
1
1
  module CukeModeler
2
2
  # The gem version
3
- VERSION = '3.3.0'
3
+ VERSION = '3.4.0'.freeze
4
4
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: cuke_modeler
3
3
  version: !ruby/object:Gem::Version
4
- version: 3.3.0
4
+ version: 3.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Eric Kessler
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2020-08-16 00:00:00.000000000 Z
11
+ date: 2020-09-02 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: cucumber-gherkin
@@ -39,103 +39,123 @@ dependencies:
39
39
  - !ruby/object:Gem::Version
40
40
  version: '3.0'
41
41
  - !ruby/object:Gem::Dependency
42
- name: rake
42
+ name: coveralls
43
43
  requirement: !ruby/object:Gem::Requirement
44
44
  requirements:
45
45
  - - "<"
46
46
  - !ruby/object:Gem::Version
47
- version: 13.0.0
47
+ version: 1.0.0
48
48
  type: :development
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "<"
53
53
  - !ruby/object:Gem::Version
54
- version: 13.0.0
54
+ version: 1.0.0
55
55
  - !ruby/object:Gem::Dependency
56
56
  name: cucumber
57
57
  requirement: !ruby/object:Gem::Requirement
58
58
  requirements:
59
+ - - ">="
60
+ - !ruby/object:Gem::Version
61
+ version: 4.0.0
59
62
  - - "<"
60
63
  - !ruby/object:Gem::Version
61
- version: 5.0.0
64
+ version: 6.0.0
62
65
  type: :development
63
66
  prerelease: false
64
67
  version_requirements: !ruby/object:Gem::Requirement
65
68
  requirements:
69
+ - - ">="
70
+ - !ruby/object:Gem::Version
71
+ version: 4.0.0
66
72
  - - "<"
67
73
  - !ruby/object:Gem::Version
68
- version: 5.0.0
74
+ version: 6.0.0
69
75
  - !ruby/object:Gem::Dependency
70
- name: rspec
76
+ name: racatt
71
77
  requirement: !ruby/object:Gem::Requirement
72
78
  requirements:
73
79
  - - "~>"
74
80
  - !ruby/object:Gem::Version
75
- version: '3.0'
81
+ version: '1.0'
76
82
  type: :development
77
83
  prerelease: false
78
84
  version_requirements: !ruby/object:Gem::Requirement
79
85
  requirements:
80
86
  - - "~>"
81
87
  - !ruby/object:Gem::Version
82
- version: '3.0'
88
+ version: '1.0'
83
89
  - !ruby/object:Gem::Dependency
84
- name: simplecov
90
+ name: rainbow
85
91
  requirement: !ruby/object:Gem::Requirement
86
92
  requirements:
87
- - - "<="
93
+ - - "<"
88
94
  - !ruby/object:Gem::Version
89
- version: 0.16.1
95
+ version: 4.0.0
90
96
  type: :development
91
97
  prerelease: false
92
98
  version_requirements: !ruby/object:Gem::Requirement
93
99
  requirements:
94
- - - "<="
100
+ - - "<"
95
101
  - !ruby/object:Gem::Version
96
- version: 0.16.1
102
+ version: 4.0.0
97
103
  - !ruby/object:Gem::Dependency
98
- name: racatt
104
+ name: rake
105
+ requirement: !ruby/object:Gem::Requirement
106
+ requirements:
107
+ - - "<"
108
+ - !ruby/object:Gem::Version
109
+ version: 14.0.0
110
+ type: :development
111
+ prerelease: false
112
+ version_requirements: !ruby/object:Gem::Requirement
113
+ requirements:
114
+ - - "<"
115
+ - !ruby/object:Gem::Version
116
+ version: 14.0.0
117
+ - !ruby/object:Gem::Dependency
118
+ name: rspec
99
119
  requirement: !ruby/object:Gem::Requirement
100
120
  requirements:
101
121
  - - "~>"
102
122
  - !ruby/object:Gem::Version
103
- version: '1.0'
123
+ version: '3.0'
104
124
  type: :development
105
125
  prerelease: false
106
126
  version_requirements: !ruby/object:Gem::Requirement
107
127
  requirements:
108
128
  - - "~>"
109
129
  - !ruby/object:Gem::Version
110
- version: '1.0'
130
+ version: '3.0'
111
131
  - !ruby/object:Gem::Dependency
112
- name: coveralls
132
+ name: rubocop
113
133
  requirement: !ruby/object:Gem::Requirement
114
134
  requirements:
115
135
  - - "<"
116
136
  - !ruby/object:Gem::Version
117
- version: 1.0.0
137
+ version: 0.82.0
118
138
  type: :development
119
139
  prerelease: false
120
140
  version_requirements: !ruby/object:Gem::Requirement
121
141
  requirements:
122
142
  - - "<"
123
143
  - !ruby/object:Gem::Version
124
- version: 1.0.0
144
+ version: 0.82.0
125
145
  - !ruby/object:Gem::Dependency
126
- name: rainbow
146
+ name: simplecov
127
147
  requirement: !ruby/object:Gem::Requirement
128
148
  requirements:
129
- - - "<"
149
+ - - "<="
130
150
  - !ruby/object:Gem::Version
131
- version: 4.0.0
151
+ version: 0.16.1
132
152
  type: :development
133
153
  prerelease: false
134
154
  version_requirements: !ruby/object:Gem::Requirement
135
155
  requirements:
136
- - - "<"
156
+ - - "<="
137
157
  - !ruby/object:Gem::Version
138
- version: 4.0.0
158
+ version: 0.16.1
139
159
  - !ruby/object:Gem::Dependency
140
160
  name: test-unit
141
161
  requirement: !ruby/object:Gem::Requirement
@@ -150,13 +170,13 @@ dependencies:
150
170
  - - "<"
151
171
  - !ruby/object:Gem::Version
152
172
  version: 4.0.0
153
- description: This gem facilitates modeling a test suite that is written in Gherkin
154
- (e.g. Cucumber, SpecFlow, Lettuce, etc.). It does this by providing an abstraction
155
- layer on top of the Abstract Syntax Tree that the 'cucumber-gherkin' gem generates
156
- when parsing features, as well as providing models for feature files and directories
157
- in order to be able to have a fully traversable model tree of a test suite's structure.
158
- These models can then be analyzed or manipulated more easily than the underlying
159
- AST layer.
173
+ description: "This gem facilitates modeling a test suite that is written in Gherkin
174
+ (e.g. Cucumber, \nSpecFlow, Lettuce, etc.). It does this by providing an abstraction
175
+ layer on top of the \nAbstract Syntax Tree that the 'cucumber-gherkin' gem generates
176
+ when parsing features, \nas well as providing models for feature files and directories
177
+ in order to be able to \nhave a fully traversable model tree of a test suite's structure.
178
+ These models can then \nbe analyzed or manipulated more easily than the underlying
179
+ AST layer."
160
180
  email:
161
181
  - morrow748@gmail.com
162
182
  executables: []