stepdown 0.2.1 → 0.3.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/.gitignore +1 -0
- data/bin/stepdown +1 -1
- data/lib/html_reporter.rb +9 -61
- data/lib/options.rb +13 -1
- data/lib/reporter.rb +62 -0
- data/lib/step_down.rb +17 -2
- data/lib/step_instance.rb +5 -1
- data/lib/text_reporter.rb +36 -0
- data/spec/lib/step_instance_spec.rb +26 -0
- data/stepdown.gemspec +4 -4
- metadata +11 -8
data/.gitignore
CHANGED
data/bin/stepdown
CHANGED
data/lib/html_reporter.rb
CHANGED
@@ -1,61 +1,28 @@
|
|
1
1
|
require 'fileutils'
|
2
|
-
|
3
|
-
|
4
|
-
attr_reader :scenarios, :usages, :steps, :grouping
|
5
|
-
|
6
|
-
def initialize(scenarios, usages, grouping, steps)
|
7
|
-
@scenarios = scenarios
|
8
|
-
@usages = usages
|
9
|
-
@steps = steps
|
10
|
-
@grouping = grouping
|
11
|
-
end
|
12
|
-
|
13
|
-
def groupings
|
14
|
-
@grouping
|
15
|
-
end
|
16
|
-
|
17
|
-
def total_scenarios
|
18
|
-
@scenarios.length
|
19
|
-
end
|
20
|
-
|
21
|
-
def total_steps
|
22
|
-
@steps.length
|
23
|
-
end
|
24
|
-
|
25
|
-
def steps_per_scenario
|
26
|
-
steps_scenario(@scenarios)
|
27
|
-
end
|
28
|
-
|
29
|
-
def unique_steps
|
30
|
-
uniq_steps_per_scenario(@scenarios)
|
31
|
-
end
|
32
|
-
|
33
|
-
def usages
|
34
|
-
@usages.select{|use| use.total_usage > 0 }
|
35
|
-
end
|
36
|
-
|
37
|
-
def unused_steps
|
38
|
-
@usages.select{|use| use.total_usage == 0}
|
39
|
-
end
|
2
|
+
require 'reporter'
|
3
|
+
class HTMLReporter < Reporter
|
40
4
|
|
41
5
|
def output_overview()
|
42
|
-
|
6
|
+
puts "Generating report..."
|
7
|
+
FileUtils.mkdir_p(Reporter::OUTPUT_DIR)
|
43
8
|
copy_files
|
44
9
|
|
45
10
|
template = File.open(File.expand_path(File.dirname(__FILE__)) + '/../templates/main.html.haml').read()
|
46
11
|
engine = Haml::Engine.new(template)
|
47
12
|
|
48
|
-
out = File.new(OUTPUT_DIR + '/analysis.html','w+')
|
13
|
+
out = File.new(Reporter::OUTPUT_DIR + '/analysis.html','w+')
|
49
14
|
out.puts engine.render(self)
|
50
15
|
out.close
|
51
16
|
|
52
17
|
template = File.open(File.expand_path(File.dirname(__FILE__)) + '/../templates/style.sass').read
|
53
18
|
sass_engine = Sass::Engine.new(template)
|
54
19
|
|
55
|
-
out = File.new(OUTPUT_DIR + '/style.css', 'w+')
|
20
|
+
out = File.new(Reporter::OUTPUT_DIR + '/style.css', 'w+')
|
56
21
|
out.puts sass_engine.render
|
57
22
|
|
58
23
|
out.close
|
24
|
+
|
25
|
+
$stdout.puts "\nReport output to #{Reporter::OUTPUT_DIR}/analysis.html"
|
59
26
|
end
|
60
27
|
|
61
28
|
protected
|
@@ -67,23 +34,4 @@ class HTMLReporter
|
|
67
34
|
end
|
68
35
|
end
|
69
36
|
|
70
|
-
|
71
|
-
scen_count = scenarios.length
|
72
|
-
step_count = 0.0
|
73
|
-
scenarios.each do |scenario|
|
74
|
-
step_count += scenario.steps.length
|
75
|
-
end
|
76
|
-
step_count / scen_count
|
77
|
-
end
|
78
|
-
|
79
|
-
def uniq_steps_per_scenario(scenarios)
|
80
|
-
total_steps = 0.0
|
81
|
-
uniq_steps = 0.0
|
82
|
-
scenarios.each do |scen|
|
83
|
-
total_steps += scen.steps.length
|
84
|
-
uniq_steps += scen.uniq_steps.length
|
85
|
-
end
|
86
|
-
total_steps / uniq_steps
|
87
|
-
end
|
88
|
-
|
89
|
-
end
|
37
|
+
end
|
data/lib/options.rb
CHANGED
@@ -2,15 +2,23 @@ require 'optparse'
|
|
2
2
|
|
3
3
|
class Options
|
4
4
|
|
5
|
+
OUTPUT_FORMATS = ["html", "text"]
|
6
|
+
|
5
7
|
def self.parse(params)
|
6
8
|
@@steps_dir = "features/step_definitions"
|
7
9
|
@@features_dir = "features"
|
10
|
+
@@reporter = "html"
|
11
|
+
|
8
12
|
|
9
13
|
parser = OptionParser.new do |opts|
|
10
14
|
opts.banner = "Usage: stepdown step_definition_dir feature_file_directory"
|
11
15
|
|
12
16
|
opts.separator("")
|
13
17
|
|
18
|
+
opts.on("--output TYPE", OUTPUT_FORMATS, "Select ouput format (#{OUTPUT_FORMATS.join(',')})") do |o|
|
19
|
+
@@reporter = o
|
20
|
+
end
|
21
|
+
|
14
22
|
opts.on("--steps=directory", "Step definition directory") do |o|
|
15
23
|
@@steps_dir = o
|
16
24
|
end
|
@@ -61,4 +69,8 @@ class Options
|
|
61
69
|
@@features_dir
|
62
70
|
end
|
63
71
|
|
64
|
-
|
72
|
+
def self.reporter
|
73
|
+
@@reporter
|
74
|
+
end
|
75
|
+
|
76
|
+
end
|
data/lib/reporter.rb
ADDED
@@ -0,0 +1,62 @@
|
|
1
|
+
|
2
|
+
class Reporter
|
3
|
+
OUTPUT_DIR = "./stepdown"
|
4
|
+
|
5
|
+
attr_reader :scenarios, :usages, :steps, :grouping
|
6
|
+
|
7
|
+
def initialize(scenarios, usages, grouping, steps)
|
8
|
+
@scenarios = scenarios
|
9
|
+
@usages = usages
|
10
|
+
@steps = steps
|
11
|
+
@grouping = grouping
|
12
|
+
end
|
13
|
+
|
14
|
+
def groupings
|
15
|
+
@grouping
|
16
|
+
end
|
17
|
+
|
18
|
+
def total_scenarios
|
19
|
+
@scenarios.length
|
20
|
+
end
|
21
|
+
|
22
|
+
def total_steps
|
23
|
+
@steps.length
|
24
|
+
end
|
25
|
+
|
26
|
+
def steps_per_scenario
|
27
|
+
steps_scenario(@scenarios)
|
28
|
+
end
|
29
|
+
|
30
|
+
def unique_steps
|
31
|
+
uniq_steps_per_scenario(@scenarios)
|
32
|
+
end
|
33
|
+
|
34
|
+
def usages
|
35
|
+
@usages.select{|use| use.total_usage > 0 }
|
36
|
+
end
|
37
|
+
|
38
|
+
def unused_steps
|
39
|
+
@usages.select{|use| use.total_usage == 0}
|
40
|
+
end
|
41
|
+
|
42
|
+
def uniq_steps_per_scenario(scenarios)
|
43
|
+
total_steps = 0.0
|
44
|
+
uniq_steps = 0.0
|
45
|
+
scenarios.each do |scen|
|
46
|
+
total_steps += scen.steps.length
|
47
|
+
uniq_steps += scen.uniq_steps.length
|
48
|
+
end
|
49
|
+
total_steps / uniq_steps
|
50
|
+
end
|
51
|
+
|
52
|
+
def steps_scenario(scenarios)
|
53
|
+
scen_count = scenarios.length
|
54
|
+
step_count = 0.0
|
55
|
+
scenarios.each do |scenario|
|
56
|
+
step_count += scenario.steps.length
|
57
|
+
end
|
58
|
+
step_count / scen_count
|
59
|
+
end
|
60
|
+
|
61
|
+
end
|
62
|
+
|
data/lib/step_down.rb
CHANGED
@@ -7,14 +7,18 @@ require 'step_instance'
|
|
7
7
|
require 'step_group'
|
8
8
|
require 'step_usage'
|
9
9
|
require 'html_reporter'
|
10
|
+
require 'yaml_reporter'
|
11
|
+
require 'text_reporter'
|
10
12
|
class StepDown
|
11
13
|
|
12
|
-
def initialize(steps_dir, feature_dir)
|
14
|
+
def initialize(steps_dir, feature_dir, reporter)
|
13
15
|
@feature_files = Dir.glob(feature_dir + '/**/*.feature')
|
14
16
|
@step_files = Dir.glob(steps_dir + '/**/*.rb')
|
17
|
+
@reporter = reporter
|
15
18
|
end
|
16
19
|
|
17
20
|
def analyse
|
21
|
+
puts "Parsing feature files..."
|
18
22
|
parser = FeatureParser.new
|
19
23
|
|
20
24
|
scenarios = []
|
@@ -23,17 +27,28 @@ class StepDown
|
|
23
27
|
end
|
24
28
|
scenarios.flatten!
|
25
29
|
|
30
|
+
puts "Performing analysis..."
|
26
31
|
usages = step_usage(scenarios)
|
27
32
|
usages = usages.sort{|a,b| b.total_usage <=> a.total_usage }
|
28
33
|
grouping = grouping(scenarios).sort{|a,b| b.use_count <=> a.use_count}
|
29
34
|
|
30
|
-
reporter =
|
35
|
+
reporter = reporter(@reporter, scenarios, usages, grouping, instance.steps)
|
31
36
|
reporter.output_overview
|
32
37
|
|
33
38
|
# #pp grouping(@scenarios)
|
34
39
|
# puts YAML::dump(scenario) if scenario.use_count > 100 && scenario.use_count < 500
|
35
40
|
# end
|
36
41
|
end
|
42
|
+
|
43
|
+
# don't want a factory just yet
|
44
|
+
def reporter(type, scenarios, usages, grouping, steps)
|
45
|
+
case type
|
46
|
+
when "html"
|
47
|
+
HTMLReporter.new(scenarios, usages, grouping, steps)
|
48
|
+
when "text"
|
49
|
+
TextReporter.new(scenarios, usages, grouping, steps)
|
50
|
+
end
|
51
|
+
end
|
37
52
|
|
38
53
|
def step_usage(scenarios)
|
39
54
|
usages = instance.steps.collect{|step| StepUsage.new(step) }
|
data/lib/step_instance.rb
CHANGED
@@ -22,6 +22,10 @@ class StepInstance
|
|
22
22
|
def method_missing(*args)
|
23
23
|
#nothing
|
24
24
|
end
|
25
|
+
|
26
|
+
def self.const_missing(*args)
|
27
|
+
#nothing
|
28
|
+
end
|
25
29
|
|
26
30
|
def require(*args)
|
27
31
|
# do nothing
|
@@ -49,4 +53,4 @@ class StepInstance
|
|
49
53
|
@step_definitions
|
50
54
|
end
|
51
55
|
|
52
|
-
end
|
56
|
+
end
|
@@ -0,0 +1,36 @@
|
|
1
|
+
require 'reporter'
|
2
|
+
|
3
|
+
class TextReporter < Reporter
|
4
|
+
|
5
|
+
def output_overview
|
6
|
+
puts "Generating report..."
|
7
|
+
output = File.new(Reporter::OUTPUT_DIR + '/analysis.txt', "w+")
|
8
|
+
|
9
|
+
output.puts "Total number of scenarios: #{total_scenarios}"
|
10
|
+
output.puts "Total numer of steps: #{total_steps}"
|
11
|
+
output.puts "Steps per scenario: #{steps_per_scenario}"
|
12
|
+
output.puts "Unique steps per scenario: #{unique_steps}"
|
13
|
+
|
14
|
+
output.puts "Step usages"
|
15
|
+
usages.each{|use| output.puts used_step_line(use) }
|
16
|
+
|
17
|
+
output.puts "Unused steps"
|
18
|
+
unused_steps.each{|use| output.puts unused_step_line(use) }
|
19
|
+
|
20
|
+
output.close
|
21
|
+
|
22
|
+
puts "Report output to #{Reporter::OUTPUT_DIR}/analysis.txt"
|
23
|
+
|
24
|
+
end
|
25
|
+
|
26
|
+
def used_step_line(use)
|
27
|
+
line = [use.step.regex.inspect, use.total_usage, use.number_scenarios, use.use_scenario]
|
28
|
+
line.join("|")
|
29
|
+
end
|
30
|
+
|
31
|
+
def unused_step_line(use)
|
32
|
+
use.step.regex
|
33
|
+
end
|
34
|
+
|
35
|
+
|
36
|
+
end
|
@@ -0,0 +1,26 @@
|
|
1
|
+
require 'rspec'
|
2
|
+
require File.expand_path(File.dirname(__FILE__) + '/../../lib/step_instance')
|
3
|
+
|
4
|
+
|
5
|
+
describe StepInstance do
|
6
|
+
|
7
|
+
before :each do
|
8
|
+
@step_instance = StepInstance.new
|
9
|
+
end
|
10
|
+
|
11
|
+
it "should deal with missing constants" do
|
12
|
+
lambda{ @step_instance.instance_eval("MissingConst") }.should_not raise_error
|
13
|
+
end
|
14
|
+
it "should deal with missing methods" do
|
15
|
+
lambda{ @step_instance.doesnt_exist }.should_not raise_error
|
16
|
+
end
|
17
|
+
|
18
|
+
describe "steps" do
|
19
|
+
|
20
|
+
end
|
21
|
+
|
22
|
+
describe "line matches" do
|
23
|
+
|
24
|
+
end
|
25
|
+
|
26
|
+
end
|
data/stepdown.gemspec
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
|
2
2
|
Gem::Specification.new do |s|
|
3
3
|
s.name = "stepdown"
|
4
|
-
s.version = "0.
|
4
|
+
s.version = "0.3.0"
|
5
5
|
s.platform = Gem::Platform::RUBY
|
6
6
|
s.authors = "Sean Caffery"
|
7
7
|
s.email = "sean@lineonpoint.com"
|
8
|
-
s.summary = "
|
9
|
-
s.homepage = "
|
10
|
-
s.description = "
|
8
|
+
s.summary = "Static analysis tool for Cucumber features"
|
9
|
+
s.homepage = "http://stepdown.lineonpoint.com"
|
10
|
+
s.description = "Stepdown allows you to see where your most used Cucumber steps are, your unused steps and how they are clustered"
|
11
11
|
|
12
12
|
s.required_rubygems_version = ">= 1.3.6"
|
13
13
|
s.rubyforge_project = "stepdown"
|
metadata
CHANGED
@@ -1,13 +1,13 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: stepdown
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
hash:
|
4
|
+
hash: 19
|
5
5
|
prerelease:
|
6
6
|
segments:
|
7
7
|
- 0
|
8
|
-
-
|
9
|
-
-
|
10
|
-
version: 0.
|
8
|
+
- 3
|
9
|
+
- 0
|
10
|
+
version: 0.3.0
|
11
11
|
platform: ruby
|
12
12
|
authors:
|
13
13
|
- Sean Caffery
|
@@ -15,7 +15,7 @@ autorequire:
|
|
15
15
|
bindir: bin
|
16
16
|
cert_chain: []
|
17
17
|
|
18
|
-
date: 2011-02-
|
18
|
+
date: 2011-02-27 00:00:00 +11:00
|
19
19
|
default_executable: stepdown
|
20
20
|
dependencies:
|
21
21
|
- !ruby/object:Gem::Dependency
|
@@ -50,7 +50,7 @@ dependencies:
|
|
50
50
|
version: 2.0.0
|
51
51
|
type: :development
|
52
52
|
version_requirements: *id002
|
53
|
-
description:
|
53
|
+
description: Stepdown allows you to see where your most used Cucumber steps are, your unused steps and how they are clustered
|
54
54
|
email: sean@lineonpoint.com
|
55
55
|
executables:
|
56
56
|
- stepdown
|
@@ -69,20 +69,23 @@ files:
|
|
69
69
|
- lib/feature_parser.rb
|
70
70
|
- lib/html_reporter.rb
|
71
71
|
- lib/options.rb
|
72
|
+
- lib/reporter.rb
|
72
73
|
- lib/scenario.rb
|
73
74
|
- lib/step.rb
|
74
75
|
- lib/step_down.rb
|
75
76
|
- lib/step_group.rb
|
76
77
|
- lib/step_instance.rb
|
77
78
|
- lib/step_usage.rb
|
79
|
+
- lib/text_reporter.rb
|
78
80
|
- public/jquery-1.4.3.min.js
|
79
81
|
- public/step_down.js
|
80
82
|
- spec/lib/step_group_spec.rb
|
83
|
+
- spec/lib/step_instance_spec.rb
|
81
84
|
- stepdown.gemspec
|
82
85
|
- templates/main.html.haml
|
83
86
|
- templates/style.sass
|
84
87
|
has_rdoc: true
|
85
|
-
homepage:
|
88
|
+
homepage: http://stepdown.lineonpoint.com
|
86
89
|
licenses: []
|
87
90
|
|
88
91
|
post_install_message:
|
@@ -116,6 +119,6 @@ rubyforge_project: stepdown
|
|
116
119
|
rubygems_version: 1.4.2
|
117
120
|
signing_key:
|
118
121
|
specification_version: 3
|
119
|
-
summary:
|
122
|
+
summary: Static analysis tool for Cucumber features
|
120
123
|
test_files: []
|
121
124
|
|