cuke_sniffer 0.0.7 → 0.0.8

Sign up to get free protection for your applications and to get access to all the features.
@@ -1,62 +1,78 @@
1
- require 'roxml'
2
- module CukeSniffer
3
-
4
- # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
5
- # Copyright:: Copyright (C) 2013 Robert Cochran
6
- # License:: Distributes under the MIT License
7
- # Parent class for all objects that have rules executed against it
8
- # Mixins: CukeSniffer::Constants, CukeSniffer::RuleConfig, ROXML
9
- class RuleTarget
10
- include CukeSniffer::Constants
11
- include CukeSniffer::RuleConfig
12
- include ROXML
13
-
14
- xml_accessor :score, :location
15
- xml_accessor :rules_hash, :as => {:key => "phrase", :value => "score"}, :in => "rules", :from => "rule"
16
-
17
- # int: Sum of the rules fired
18
- attr_accessor :score
19
-
20
- # string: Location in which the object was found
21
- attr_accessor :location
22
-
23
- # hash: Contains the phrase every rule fired against the object and times it fired
24
- # * Key: string
25
- # * Value: int
26
- attr_accessor :rules_hash
27
-
28
- # Location must be in the format of "file_path\file_name.rb:line_number"
29
- def initialize(location)
30
- @location = location
31
- @score = 0
32
- @rules_hash = {}
33
- @class_type = self.class.to_s.gsub(/.*::/, "")
34
- end
35
-
36
- # Compares the score against the objects threshold
37
- # If a score is below the threshold it is good and returns true
38
- # Return: Boolean
39
- def good?
40
- score <= Constants::THRESHOLDS[@class_type]
41
- end
42
-
43
- # Calculates the score to threshold percentage of an object
44
- # Return: Float
45
- def problem_percentage
46
- score.to_f / Constants::THRESHOLDS[@class_type].to_f
47
- end
48
-
49
- def == (comparison_object) # :nodoc:
50
- comparison_object.location == location &&
51
- comparison_object.score == score &&
52
- comparison_object.rules_hash == rules_hash
53
- end
54
-
55
- private
56
-
57
- #TODO Abstraction needed for this regex matcher (constants?)
58
- def is_comment?(line)
59
- true if line =~ /^\#.*$/
60
- end
61
- end
62
- end
1
+ require 'cuke_sniffer/constants'
2
+ require 'cuke_sniffer/rule_config'
3
+
4
+ module CukeSniffer
5
+
6
+ # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
7
+ # Copyright:: Copyright (C) 2014 Robert Cochran
8
+ # License:: Distributes under the MIT License
9
+ # Parent class for all objects that have rules executed against it
10
+ # Mixins: CukeSniffer::Constants, CukeSniffer::RuleConfig, ROXML
11
+ class RuleTarget
12
+ include CukeSniffer::Constants
13
+ include CukeSniffer::RuleConfig
14
+ include ROXML
15
+
16
+ xml_accessor :score, :location
17
+ xml_accessor :rules_hash, :as => {:key => "phrase", :value => "score"}, :in => "rules", :from => "rule"
18
+ xml_accessor :type
19
+
20
+ # int: Sum of the rules fired
21
+ attr_accessor :score
22
+
23
+ # string: Location in which the object was found
24
+ attr_accessor :location
25
+
26
+ # hash: Contains the phrase every rule fired against the object and times it fired
27
+ # * Key: string
28
+ # * Value: int
29
+ attr_accessor :rules_hash
30
+
31
+ # string: Type of the object being evaluated
32
+ attr_accessor :type
33
+
34
+ # Location must be in the format of "file_path\file_name.rb:line_number"
35
+ def initialize(location)
36
+ @location = location
37
+ @score = 0
38
+ @rules_hash = {}
39
+ @class_type = self.class.to_s.gsub(/.*::/, "")
40
+ end
41
+
42
+ # Compares the score against the objects threshold
43
+ # If a score is below the threshold it is good and returns true
44
+ # Return: Boolean
45
+ def good?
46
+ score <= Constants::THRESHOLDS[@class_type]
47
+ end
48
+
49
+ # Calculates the score to threshold percentage of an object
50
+ # Return: Float
51
+ def problem_percentage
52
+ score.to_f / Constants::THRESHOLDS[@class_type].to_f
53
+ end
54
+
55
+ def == (comparison_object) # :nodoc:
56
+ comparison_object.location == location &&
57
+ comparison_object.score == score &&
58
+ comparison_object.rules_hash == rules_hash
59
+ end
60
+
61
+ #TODO Abstraction needed for this regex matcher (constants?)
62
+ def is_comment?(line)
63
+ true if line =~ /^\#.*$/
64
+ end
65
+
66
+ def store_rule(rule, phrase = rule.phrase)
67
+ @score += rule.score
68
+ @rules_hash[phrase] ||= 0
69
+ @rules_hash[phrase] += 1
70
+ end
71
+
72
+ def store_rule_many_times(rule, count, phrase = rule.phrase)
73
+ count.times do
74
+ store_rule(rule, phrase)
75
+ end
76
+ end
77
+ end
78
+ end
@@ -1,65 +1,53 @@
1
- require 'roxml'
2
-
3
- module CukeSniffer
4
-
5
- # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
6
- # Copyright:: Copyright (C) 2013 Robert Cochran
7
- # License:: Distributes under the MIT License
8
- # Evaluates all cucumber components found in CukeSniffer with the passed rules
9
- class RulesEvaluator
10
- include CukeSniffer::Constants
11
- attr_accessor :rules
12
-
13
- def initialize(cli, rules)
14
- raise "A CLI must be provided for evaluation." if cli.nil?
15
- raise "Rules must be provided for evaluation." if rules.nil? or rules.empty?
16
- @rules = rules
17
- judge_features(cli.features)
18
- judge_objects(cli.step_definitions, "StepDefinition")
19
- judge_objects(cli.hooks, "Hook")
20
- end
21
-
22
- private
23
-
24
- def judge_features(features)
25
- features.each do |feature|
26
- judge_feature(feature)
27
- end
28
- end
29
-
30
- def judge_feature(feature)
31
- judge_object(feature, "Feature")
32
- judge_object(feature.background, "Background") unless feature.background.nil?
33
- judge_objects(feature.scenarios, "Scenario")
34
- feature.total_score += feature.update_score
35
-
36
- end
37
-
38
- def judge_objects(objects, type)
39
- objects.each do | object |
40
- judge_object(object, type)
41
- end
42
- end
43
-
44
- def judge_object(object, type)
45
- @rules.each do |rule|
46
- fail "No targets for rule: #{rule.phrase}" if rule.targets.nil? or rule.targets.empty?
47
- next unless rule.targets.include? type and rule.enabled
48
- if eval(rule.reason) == true
49
- phrase = rule.phrase.gsub("{class}", type)
50
- store_rule(object, rule, phrase)
51
- end
52
- end
53
- end
54
-
55
- def store_rule(object, rule, phrase = rule.phrase)
56
- object.score += rule.score
57
- object.rules_hash[phrase] ||= 0
58
- object.rules_hash[phrase] += 1
59
- end
60
-
61
- def is_comment?(line)
62
- true if line =~ /^\#.*$/
63
- end
64
- end
1
+ module CukeSniffer
2
+
3
+ # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
4
+ # Copyright:: Copyright (C) 2014 Robert Cochran
5
+ # License:: Distributes under the MIT License
6
+ # Evaluates all cucumber components found in CukeSniffer with the passed rules
7
+ class RulesEvaluator
8
+ include CukeSniffer::Constants
9
+ attr_accessor :rules
10
+
11
+ def initialize(cli, rules)
12
+ raise "A CLI must be provided for evaluation." if cli.nil?
13
+ raise "Rules must be provided for evaluation." if rules.nil? or rules.empty?
14
+ @rules = rules
15
+ judge_features(cli.features)
16
+ judge_objects(cli.step_definitions, "StepDefinition")
17
+ judge_objects(cli.hooks, "Hook")
18
+ end
19
+
20
+ private
21
+
22
+ def judge_features(features)
23
+ features.each do |feature|
24
+ judge_feature(feature)
25
+ end
26
+ end
27
+
28
+ def judge_feature(feature)
29
+ judge_object(feature, "Feature")
30
+ judge_object(feature.background, "Background") unless feature.background.nil?
31
+ judge_objects(feature.scenarios, "Scenario")
32
+ feature.total_score += feature.update_score
33
+
34
+ end
35
+
36
+ def judge_objects(objects, type)
37
+ objects.each do | object |
38
+ judge_object(object, type)
39
+ end
40
+ end
41
+
42
+ def judge_object(object, type)
43
+ @rules.each do |rule|
44
+ fail "No targets for rule: #{rule.phrase}" if rule.targets.nil? or rule.targets.empty?
45
+ next unless rule.targets.include? type and rule.enabled
46
+ if rule.reason.(object, rule) == true
47
+ phrase = rule.phrase.gsub("{class}", type)
48
+ object.store_rule(rule, phrase)
49
+ end
50
+ end
51
+ end
52
+ end
65
53
  end
@@ -1,102 +1,123 @@
1
- module CukeSniffer
2
-
3
- # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
4
- # Copyright:: Copyright (C) 2013 Robert Cochran
5
- # License:: Distributes under the MIT License
6
- # This class is a representation of the cucumber objects
7
- # Background, Scenario, Scenario Outline
8
- #
9
- # Extends CukeSniffer::FeatureRulesEvaluator
10
- class Scenario < FeatureRuleTarget
11
-
12
- xml_accessor :start_line
13
- xml_accessor :steps, :as => [], :in => "steps"
14
- xml_accessor :examples_table, :as => [], :in => "examples"
15
-
16
- # int: Line on which the scenario begins
17
- attr_accessor :start_line
18
-
19
- # string: The type of scenario
20
- # Background, Scenario, Scenario Outline
21
- attr_accessor :type
22
-
23
- # string array: List of each step call in a scenario
24
- attr_accessor :steps
25
-
26
- # hash: Keeps each location and content of an inline table
27
- # * Key: Step string the inline table is attached to
28
- # * Value: Array of all of the lines in the table
29
- attr_accessor :inline_tables
30
-
31
- # string array: List of each example row in a scenario outline
32
- attr_accessor :examples_table
33
-
34
- # Location must be in the format of "file_path\file_name.rb:line_number"
35
- # Scenario must be a string array containing everything from the first tag to the last example table
36
- # where applicable.
37
- def initialize(location, scenario)
38
- super(location)
39
- @start_line = location.match(/:(?<line>\d*)$/)[:line].to_i
40
- @steps = []
41
- @inline_tables = {}
42
- @examples_table = []
43
- split_scenario(scenario)
44
- end
45
-
46
- def ==(comparison_object) # :nodoc:
47
- super(comparison_object) &&
48
- comparison_object.steps == steps &&
49
- comparison_object.examples_table == examples_table
50
- end
51
-
52
- def get_step_order
53
- order = []
54
- @steps.each do |line|
55
- next if is_comment?(line)
56
- match = line.match(STEP_REGEX)
57
- order << match[:style] unless match.nil?
58
- end
59
- order
60
- end
61
-
62
- private
63
-
64
- def split_scenario(scenario)
65
- index = 0
66
- until index >= scenario.length or scenario[index] =~ SCENARIO_TITLE_STYLES
67
- update_tag_list(scenario[index])
68
- index += 1
69
- end
70
-
71
- until index >= scenario.length or scenario[index].match STEP_REGEX or scenario[index].include?("Examples:")
72
- match = scenario[index].match(SCENARIO_TITLE_STYLES)
73
- @type = match[:type] unless match.nil?
74
- create_name(scenario[index], SCENARIO_TITLE_STYLES)
75
- index += 1
76
- end
77
-
78
- until index >= scenario.length or scenario[index].include?("Examples:")
79
- if scenario[index] =~ /^\|.*\|/
80
- step = scenario[index - 1]
81
- @inline_tables[step] = []
82
- until index >= scenario.length or scenario[index] =~ /(#{STEP_REGEX}|^\s*Examples:)/
83
- @inline_tables[step] << scenario[index]
84
- index += 1
85
- end
86
- else
87
- @steps << scenario[index] if scenario[index] =~ STEP_REGEX
88
- index += 1
89
- end
90
- end
91
-
92
- if index < scenario.length and scenario[index].include?("Examples:")
93
- index += 1
94
- until index >= scenario.length
95
- index += 2 if scenario[index].include?("Examples:")
96
- @examples_table << scenario[index] if scenario[index] =~ /#{COMMENT_REGEX}\|.*\|/
97
- index += 1
98
- end
99
- end
100
- end
101
- end
102
- end
1
+ module CukeSniffer
2
+
3
+ # Author:: Robert Cochran (mailto:cochrarj@miamioh.edu)
4
+ # Copyright:: Copyright (C) 2014 Robert Cochran
5
+ # License:: Distributes under the MIT License
6
+ # This class is a representation of the cucumber objects
7
+ # Background, Scenario, Scenario Outline
8
+ #
9
+ # Extends CukeSniffer::FeatureRulesEvaluator
10
+ class Scenario < FeatureRuleTarget
11
+
12
+ xml_accessor :start_line
13
+ xml_accessor :steps, :as => [], :in => "steps"
14
+ xml_accessor :examples_table, :as => [], :in => "examples"
15
+
16
+ # int: Line on which the scenario begins
17
+ attr_accessor :start_line
18
+
19
+ # string: The type of scenario
20
+ # Background, Scenario, Scenario Outline
21
+ attr_accessor :type
22
+
23
+ # string array: List of each step call in a scenario
24
+ attr_accessor :steps
25
+
26
+ # hash: Keeps each location and content of an inline table
27
+ # * Key: Step string the inline table is attached to
28
+ # * Value: Array of all of the lines in the table
29
+ attr_accessor :inline_tables
30
+
31
+ # string array: List of each example row in a scenario outline
32
+ attr_accessor :examples_table
33
+
34
+ # Location must be in the format of "file_path\file_name.rb:line_number"
35
+ # Scenario must be a string array containing everything from the first tag to the last example table
36
+ # where applicable.
37
+ def initialize(location, scenario)
38
+ super(location)
39
+ @start_line = location.match(/:(?<line>\d*)$/)[:line].to_i
40
+ @steps = []
41
+ @inline_tables = {}
42
+ @examples_table = []
43
+ split_scenario(scenario)
44
+ end
45
+
46
+ def ==(comparison_object) # :nodoc:
47
+ super(comparison_object) &&
48
+ comparison_object.steps == steps &&
49
+ comparison_object.examples_table == examples_table
50
+ end
51
+
52
+ def get_step_order
53
+ order = []
54
+ @steps.each do |line|
55
+ next if is_comment?(line)
56
+ match = line.match(STEP_REGEX)
57
+ order << match[:style] unless match.nil?
58
+ end
59
+ order
60
+ end
61
+
62
+ def outline?
63
+ type === 'Scenario Outline'
64
+ end
65
+
66
+ def commented_examples
67
+ @examples_table.select do |example|
68
+ is_comment?(example)
69
+ end
70
+ end
71
+
72
+ def get_steps(step_start)
73
+ if step_start != "*"
74
+ regex = /^\s*#{step_start}/
75
+ else
76
+ regex = /^\s*[*]/
77
+ end
78
+ @steps.select do |step|
79
+ step =~ regex
80
+ end
81
+ end
82
+
83
+ private
84
+
85
+ def split_scenario(scenario)
86
+ index = 0
87
+ until index >= scenario.length or scenario[index] =~ SCENARIO_TITLE_STYLES
88
+ update_tag_list(scenario[index])
89
+ index += 1
90
+ end
91
+
92
+ until index >= scenario.length or scenario[index].match STEP_REGEX or scenario[index].include?("Examples:")
93
+ match = scenario[index].match(SCENARIO_TITLE_STYLES)
94
+ @type = match[:type] unless match.nil?
95
+ create_name(scenario[index], SCENARIO_TITLE_STYLES)
96
+ index += 1
97
+ end
98
+
99
+ until index >= scenario.length or scenario[index].include?("Examples:")
100
+ if scenario[index] =~ /^\|.*\|/
101
+ step = scenario[index - 1]
102
+ @inline_tables[step] = []
103
+ until index >= scenario.length or scenario[index] =~ /(#{STEP_REGEX}|^\s*Examples:)/
104
+ @inline_tables[step] << scenario[index]
105
+ index += 1
106
+ end
107
+ else
108
+ @steps << scenario[index] if scenario[index] =~ STEP_REGEX
109
+ index += 1
110
+ end
111
+ end
112
+
113
+ if index < scenario.length and scenario[index].include?("Examples:")
114
+ index += 1
115
+ until index >= scenario.length
116
+ index += 2 if scenario[index].include?("Examples:")
117
+ @examples_table << scenario[index] if scenario[index] =~ /#{COMMENT_REGEX}\|.*\|/
118
+ index += 1
119
+ end
120
+ end
121
+ end
122
+ end
123
+ end