dtf 0.2.1 → 0.2.2
Sign up to get free protection for your applications and to get access to all the features.
- data/.gitignore +44 -0
- data/.rspec +1 -0
- data/.rvmrc +52 -0
- data/.travis.yml +16 -0
- data/Gemfile +26 -0
- data/History.md +75 -0
- data/LICENSE +19 -10
- data/README.md +67 -45
- data/Rakefile +9 -0
- data/TODO +25 -0
- data/app/models/analysis_case.rb +12 -0
- data/app/models/case_test.rb +10 -0
- data/app/models/user.rb +12 -0
- data/app/models/verification_suite.rb +22 -0
- data/bin/dtf +24 -3
- data/bin/dtf-create_user +11 -0
- data/bin/dtf-create_vs +10 -0
- data/bin/dtf-delete_user +18 -0
- data/bin/dtf-delete_vs +14 -0
- data/bin/dtf-setup +7 -0
- data/db/migrate/20120503050925_create_users.rb +15 -0
- data/db/migrate/20120508000959_create_verification_suites.rb +14 -0
- data/db/migrate/20120616203047_create_analysis_cases.rb +15 -0
- data/db/migrate/20120616203436_create_case_tests.rb +15 -0
- data/db/schema.rb +48 -0
- data/doc/.gitkeep +0 -0
- data/dtf.gemspec +36 -0
- data/examples/db/config.yml +25 -0
- data/lib/config/environment.rb +49 -0
- data/lib/dtf.rb +4 -91
- data/lib/dtf/version.rb +5 -0
- data/lib/tasks/setup.thor +52 -0
- data/spec/acceptance/0001_create_basic_models.feature +9 -0
- data/spec/acceptance/0002_create_basic_associations.feature +11 -0
- data/spec/acceptance/0003_execute_help_switch.feature +7 -0
- data/spec/fabricators/analysis_case_fabricator.rb +7 -0
- data/spec/fabricators/case_test_fabricator.rb +6 -0
- data/spec/fabricators/user_fabricator.rb +8 -0
- data/spec/fabricators/verification_suite_fabricator.rb +6 -0
- data/spec/models/analysis_case_spec.rb +21 -0
- data/spec/models/case_test_spec.rb +20 -0
- data/spec/models/user_spec.rb +21 -0
- data/spec/models/verification_suite_spec.rb +21 -0
- data/spec/spec_helper.rb +18 -0
- data/spec/steps/feature_steps.rb +18 -0
- data/spec/support/custom_matchers/model_steps.rb +46 -0
- data/spec/support/helpers/.gitkeep +0 -0
- metadata +303 -70
- data/lib/dtf/active_patches.rb +0 -21
- data/lib/dtf/plugins.rb +0 -102
- data/lib/plugins/dtf/comment_test_input.rb +0 -40
- data/lib/plugins/dtf/env_match_test.rb +0 -18
- data/lib/plugins/dtf/error_summary_output.rb +0 -93
- data/lib/plugins/dtf/output_match_test.rb +0 -17
- data/lib/plugins/dtf/stats_output.rb +0 -73
- data/lib/plugins/dtf/status_test.rb +0 -17
- data/lib/plugins/dtf/text_output.rb +0 -52
data/lib/dtf/active_patches.rb
DELETED
@@ -1,21 +0,0 @@
|
|
1
|
-
unless String.method_defined? :blank?
|
2
|
-
String.class_eval do
|
3
|
-
def blank?
|
4
|
-
self == ""
|
5
|
-
end
|
6
|
-
end
|
7
|
-
end
|
8
|
-
unless Array.method_defined? :blank?
|
9
|
-
Array.class_eval do
|
10
|
-
def blank?
|
11
|
-
size == 0
|
12
|
-
end
|
13
|
-
end
|
14
|
-
end
|
15
|
-
unless NilClass.method_defined? :blank?
|
16
|
-
NilClass.class_eval do
|
17
|
-
def blank?
|
18
|
-
true
|
19
|
-
end
|
20
|
-
end
|
21
|
-
end
|
data/lib/dtf/plugins.rb
DELETED
@@ -1,102 +0,0 @@
|
|
1
|
-
class DTF::Plugins
|
2
|
-
include Singleton
|
3
|
-
|
4
|
-
def initialize
|
5
|
-
detect
|
6
|
-
@additional_plugins = []
|
7
|
-
@input_plugins = []
|
8
|
-
@output_plugins = []
|
9
|
-
@test_plugins = []
|
10
|
-
end
|
11
|
-
|
12
|
-
def detect
|
13
|
-
@plugins = Gem.find_files('plugins/dtf/*.rb')
|
14
|
-
end
|
15
|
-
|
16
|
-
def add plugin
|
17
|
-
@additional_plugins << plugin
|
18
|
-
end
|
19
|
-
|
20
|
-
def delete plugin
|
21
|
-
@additional_plugins.delete plugin
|
22
|
-
end
|
23
|
-
|
24
|
-
def file_to_class item
|
25
|
-
File.basename(item,'.rb').capitalize.gsub(/_(.)/){ $1.upcase }
|
26
|
-
end
|
27
|
-
|
28
|
-
def list pattern=nil
|
29
|
-
# collect to lists
|
30
|
-
_list = @plugins + @additional_plugins
|
31
|
-
# filter by pattern if given
|
32
|
-
_list = _list.select{|item| item.match("_#{pattern}.rb$") } unless pattern.nil?
|
33
|
-
# get path and class name
|
34
|
-
_list.map!{|item| [ item, file_to_class(item), pattern ] }
|
35
|
-
# TODO: limit plugin versions (highest || use bundler)
|
36
|
-
_list.each{|item, klass, type| require item }
|
37
|
-
_list
|
38
|
-
end
|
39
|
-
|
40
|
-
def load wanted
|
41
|
-
[ :input, :test, :output ].each do |type|
|
42
|
-
_list = list(type)
|
43
|
-
if ! wanted.include?("all") && ! wanted.include?("all_#{type}")
|
44
|
-
_list = _list.select{|item, klass, _type| wanted.include?(klass) }
|
45
|
-
end
|
46
|
-
_list.each{|item, klass, _type|
|
47
|
-
klass = DTF.const_get(klass)
|
48
|
-
instance_variable_get("@#{type}_plugins".to_sym) << klass.new
|
49
|
-
}
|
50
|
-
end
|
51
|
-
end
|
52
|
-
|
53
|
-
def match_arg_klass arg, klass, type
|
54
|
-
klass = DTF.const_get(klass)
|
55
|
-
return nil unless klass.respond_to? :argument_matches?
|
56
|
-
matches = klass.argument_matches? arg
|
57
|
-
return nil if matches.nil?
|
58
|
-
matches.each do |match|
|
59
|
-
case match
|
60
|
-
when :load
|
61
|
-
instance_variable_get("@#{type}_plugins".to_sym) << klass.new
|
62
|
-
when :input
|
63
|
-
@input_files << [klass.new, arg]
|
64
|
-
else
|
65
|
-
return nil
|
66
|
-
end
|
67
|
-
end
|
68
|
-
return matches
|
69
|
-
rescue NameError
|
70
|
-
return nil
|
71
|
-
end
|
72
|
-
|
73
|
-
def parse_args args
|
74
|
-
@input_files, not_processed = [], []
|
75
|
-
available_plugins = [ :input, :test, :output ].map{ |type| list(type) }.flatten(1)
|
76
|
-
args.each do |arg|
|
77
|
-
matched = available_plugins.map do |item, klass, type|
|
78
|
-
match_arg_klass arg, klass, type
|
79
|
-
end.flatten.reject(&:nil?)
|
80
|
-
if matched.empty?
|
81
|
-
not_processed << arg
|
82
|
-
end
|
83
|
-
end
|
84
|
-
[ @input_files, not_processed ]
|
85
|
-
end
|
86
|
-
|
87
|
-
def input_plugins
|
88
|
-
@input_plugins
|
89
|
-
end
|
90
|
-
|
91
|
-
def output_plugins *args
|
92
|
-
if args.empty?
|
93
|
-
@output_plugins
|
94
|
-
else
|
95
|
-
@output_plugins.each{|plugin| plugin.send(*args) }
|
96
|
-
end
|
97
|
-
end
|
98
|
-
|
99
|
-
def test_plugins
|
100
|
-
@test_plugins
|
101
|
-
end
|
102
|
-
end
|
@@ -1,40 +0,0 @@
|
|
1
|
-
class DTF::CommentTestInput
|
2
|
-
def initialize
|
3
|
-
end
|
4
|
-
|
5
|
-
def self.argument_matches? argument
|
6
|
-
if argument =~ /_comment_test\.sh$/ && File.exist?(argument)
|
7
|
-
[:load, :input]
|
8
|
-
else
|
9
|
-
nil
|
10
|
-
end
|
11
|
-
end
|
12
|
-
|
13
|
-
def load file_name
|
14
|
-
lines = []
|
15
|
-
File.readlines(file_name).each{|line|
|
16
|
-
# Fix jruby-1.6.6-d19 bug with empty strings from files
|
17
|
-
line = "#{line}"
|
18
|
-
# remove human comments
|
19
|
-
line.sub!(/##.*$/,'')
|
20
|
-
# reject empty lines
|
21
|
-
line.strip!
|
22
|
-
next if line =~ /^$/
|
23
|
-
# extract command and tests
|
24
|
-
cmd, tests = line.split("#")
|
25
|
-
cmd.strip!
|
26
|
-
tests = if tests.blank?
|
27
|
-
[]
|
28
|
-
else
|
29
|
-
tests.split(";").map(&:strip)
|
30
|
-
end
|
31
|
-
if cmd.blank?
|
32
|
-
lines.last[:tests] += tests unless lines.last.nil?
|
33
|
-
else
|
34
|
-
lines << { :cmd => cmd, :tests => tests }
|
35
|
-
end
|
36
|
-
}
|
37
|
-
name = file_name.gsub(/^.*\//,'').sub(/_comment_test\.sh$/,'')
|
38
|
-
{ :name => name, :commands => lines }
|
39
|
-
end
|
40
|
-
end
|
@@ -1,18 +0,0 @@
|
|
1
|
-
class DTF::EnvMatchTest
|
2
|
-
MATCHER = /^env\[(.*)\]([!]?=)[~]?\/(.*)\//
|
3
|
-
|
4
|
-
def matches? test
|
5
|
-
test =~ DTF::EnvMatchTest::MATCHER
|
6
|
-
end
|
7
|
-
|
8
|
-
def execute test, _stdout, _stderr, _stdboth, _status, env
|
9
|
-
test =~ DTF::EnvMatchTest::MATCHER
|
10
|
-
variable, sign, value = $1.strip, $2, $3
|
11
|
-
var_val = env[ variable ]
|
12
|
-
if ( sign == "=" ) ^ ( Regexp.new(value) =~ "#{var_val}" )
|
13
|
-
[ false, "failed: env #{variable} #{sign} /#{value}/ # was '#{var_val}'" ]
|
14
|
-
else
|
15
|
-
[ true, "passed: env #{variable} #{sign} /#{value}/" ]
|
16
|
-
end
|
17
|
-
end
|
18
|
-
end
|
@@ -1,93 +0,0 @@
|
|
1
|
-
class DTF::ErrorSummaryOutput
|
2
|
-
RED = `tput setaf 1`
|
3
|
-
GREEN = `tput setaf 2`
|
4
|
-
YELLOW = `tput setaf 3`
|
5
|
-
BLUE = `tput setaf 4`
|
6
|
-
RESET = `tput setaf 9`
|
7
|
-
|
8
|
-
def self.argument_matches? argument
|
9
|
-
[:load] if argument == "--dotted"
|
10
|
-
end
|
11
|
-
|
12
|
-
def initialize output=nil
|
13
|
-
@counts={}
|
14
|
-
@counts[:commands] = 0
|
15
|
-
@counts[:tests] = 0
|
16
|
-
@counts[:commands_started] = 0
|
17
|
-
@counts[:commands_finished] = 0
|
18
|
-
@counts[:tests_success] = 0
|
19
|
-
@counts[:tests_failure] = 0
|
20
|
-
@counter_id = 0
|
21
|
-
@summary = {}
|
22
|
-
@output = output || $stdout
|
23
|
-
end
|
24
|
-
|
25
|
-
def start_processing
|
26
|
-
end
|
27
|
-
|
28
|
-
def status
|
29
|
-
text = "#{BLUE}##### Processed commands #{@counts[:commands_finished]} of #{@counts[:commands]}"
|
30
|
-
if @counts[:tests_success] > 0
|
31
|
-
text += ", #{GREEN}success tests #{@counts[:tests_success]} of #{@counts[:tests]}"
|
32
|
-
end
|
33
|
-
if @counts[:tests_failure] > 0
|
34
|
-
text += ", #{RED}failure tests #{@counts[:tests_failure]} of #{@counts[:tests]}"
|
35
|
-
end
|
36
|
-
skipped = @counts[:tests] - @counts[:tests_success] - @counts[:tests_failure]
|
37
|
-
if skipped > 0
|
38
|
-
text += ", #{YELLOW}skipped tests #{skipped} of #{@counts[:tests]}"
|
39
|
-
end
|
40
|
-
text += ".#{RESET}"
|
41
|
-
text
|
42
|
-
end
|
43
|
-
|
44
|
-
def summary
|
45
|
-
@summary.sort{|a,b| ak,_=a ; bk,_=b ; ak <=> bk }.each{|k,v|
|
46
|
-
@output.puts "#{YELLOW}$ #{v[:cmd]}#{RESET}"
|
47
|
-
v[:failed_tests].each{|t| puts "#{RED}# #{t}#{RESET}" }
|
48
|
-
}
|
49
|
-
text = ""
|
50
|
-
text
|
51
|
-
end
|
52
|
-
|
53
|
-
def end_processing
|
54
|
-
@output.printf "\n"
|
55
|
-
@output.puts status
|
56
|
-
@output.puts summary
|
57
|
-
end
|
58
|
-
|
59
|
-
def start_test test, env
|
60
|
-
@counts[:commands] += test[:commands].size
|
61
|
-
tests_counts = test[:commands].map{|line| line[:tests].nil? ? 0 : line[:tests].size }
|
62
|
-
@counts[:tests] += tests_counts.empty? ? 0 : tests_counts.inject(&:+)
|
63
|
-
end
|
64
|
-
|
65
|
-
def end_test test
|
66
|
-
end
|
67
|
-
|
68
|
-
def start_command line
|
69
|
-
@counts[:commands_started] += 1
|
70
|
-
@current_line = line.merge(:counter_id => @counts[:commands_started])
|
71
|
-
end
|
72
|
-
|
73
|
-
def end_command line, status, env
|
74
|
-
@counts[:commands_finished] += 1
|
75
|
-
end
|
76
|
-
|
77
|
-
def command_out out
|
78
|
-
end
|
79
|
-
|
80
|
-
def command_err err
|
81
|
-
end
|
82
|
-
|
83
|
-
def test_processed test, status, msg
|
84
|
-
@output.printf status ? "." : "F"
|
85
|
-
if status
|
86
|
-
@counts[:tests_success] += 1
|
87
|
-
else
|
88
|
-
@counts[:tests_failure] += 1
|
89
|
-
@summary[@current_line[:counter_id]] ||= @current_line.merge({:failed_tests=>[]})
|
90
|
-
@summary[@current_line[:counter_id]][:failed_tests] << msg
|
91
|
-
end
|
92
|
-
end
|
93
|
-
end
|
@@ -1,17 +0,0 @@
|
|
1
|
-
class DTF::OutputMatchTest
|
2
|
-
MATCHER = /^match([!]?=)[~]?\/(.*)\//
|
3
|
-
|
4
|
-
def matches? test
|
5
|
-
test =~ DTF::OutputMatchTest::MATCHER
|
6
|
-
end
|
7
|
-
|
8
|
-
def execute test, _stdout, _stderr, _stdboth, _status, env
|
9
|
-
test =~ DTF::OutputMatchTest::MATCHER
|
10
|
-
sign, value = $1, $2
|
11
|
-
if ( sign == "=" ) ^ ( Regexp.new(value) =~ "#{_stdboth}" )
|
12
|
-
[ false, "failed: match #{sign} /#{value}/" ]
|
13
|
-
else
|
14
|
-
[ true, "passed: match #{sign} /#{value}/" ]
|
15
|
-
end
|
16
|
-
end
|
17
|
-
end
|
@@ -1,73 +0,0 @@
|
|
1
|
-
class DTF::StatsOutput
|
2
|
-
RED = `tput setaf 1`
|
3
|
-
GREEN = `tput setaf 2`
|
4
|
-
YELLOW = `tput setaf 3`
|
5
|
-
BLUE = `tput setaf 4`
|
6
|
-
RESET = `tput setaf 9`
|
7
|
-
|
8
|
-
def self.argument_matches? argument
|
9
|
-
[:load] if argument == "--text"
|
10
|
-
end
|
11
|
-
|
12
|
-
def initialize
|
13
|
-
@counts={}
|
14
|
-
@counts[:commands] = 0
|
15
|
-
@counts[:tests] = 0
|
16
|
-
@counts[:commands_finished] = 0
|
17
|
-
@counts[:tests_success] = 0
|
18
|
-
@counts[:tests_failure] = 0
|
19
|
-
end
|
20
|
-
|
21
|
-
def start_processing
|
22
|
-
end
|
23
|
-
|
24
|
-
def status
|
25
|
-
text = "#{BLUE}##### Processed commands #{@counts[:commands_finished]} of #{@counts[:commands]}"
|
26
|
-
if @counts[:tests_success] > 0
|
27
|
-
text += ", #{GREEN}success tests #{@counts[:tests_success]} of #{@counts[:tests]}"
|
28
|
-
end
|
29
|
-
if @counts[:tests_failure] > 0
|
30
|
-
text += ", #{RED}failure tests #{@counts[:tests_failure]} of #{@counts[:tests]}"
|
31
|
-
end
|
32
|
-
skipped = @counts[:tests] - @counts[:tests_success] - @counts[:tests_failure]
|
33
|
-
if skipped > 0
|
34
|
-
text += ", #{YELLOW}skipped tests #{skipped} of #{@counts[:tests]}"
|
35
|
-
end
|
36
|
-
text += ".#{RESET}"
|
37
|
-
text
|
38
|
-
end
|
39
|
-
|
40
|
-
def end_processing
|
41
|
-
puts status
|
42
|
-
end
|
43
|
-
|
44
|
-
def start_test test, env
|
45
|
-
@counts[:commands] += test[:commands].size
|
46
|
-
tests_counts = test[:commands].map{|line| line[:tests].nil? ? 0 : line[:tests].size }
|
47
|
-
@counts[:tests] += tests_counts.empty? ? 0 : tests_counts.inject(&:+)
|
48
|
-
end
|
49
|
-
|
50
|
-
def end_test test
|
51
|
-
end
|
52
|
-
|
53
|
-
def start_command line
|
54
|
-
end
|
55
|
-
|
56
|
-
def end_command line, status, env
|
57
|
-
@counts[:commands_finished] += 1
|
58
|
-
end
|
59
|
-
|
60
|
-
def command_out out
|
61
|
-
end
|
62
|
-
|
63
|
-
def command_err err
|
64
|
-
end
|
65
|
-
|
66
|
-
def test_processed test, status, msg
|
67
|
-
if status
|
68
|
-
@counts[:tests_success] += 1
|
69
|
-
else
|
70
|
-
@counts[:tests_failure] += 1
|
71
|
-
end
|
72
|
-
end
|
73
|
-
end
|
@@ -1,17 +0,0 @@
|
|
1
|
-
class DTF::StatusTest
|
2
|
-
MATCHER = /^status([!]?=)([[:digit:]]+)$/
|
3
|
-
|
4
|
-
def matches? test
|
5
|
-
test =~ DTF::StatusTest::MATCHER
|
6
|
-
end
|
7
|
-
|
8
|
-
def execute test, _stdout, _stderr, _stdboth, _status, env
|
9
|
-
test =~ DTF::StatusTest::MATCHER
|
10
|
-
sign, value = $1, $2.to_i
|
11
|
-
if ( sign == "=" ) ^ ( _status == value )
|
12
|
-
[ false, "failed: status #{sign} #{value} # was #{_status}" ]
|
13
|
-
else
|
14
|
-
[ true, "passed: status #{sign} #{value}" ]
|
15
|
-
end
|
16
|
-
end
|
17
|
-
end
|
@@ -1,52 +0,0 @@
|
|
1
|
-
class DTF::TextOutput
|
2
|
-
RED = `tput setaf 1`
|
3
|
-
GREEN = `tput setaf 2`
|
4
|
-
YELLOW = `tput setaf 3`
|
5
|
-
BLUE = `tput setaf 4`
|
6
|
-
RESET = `tput setaf 9`
|
7
|
-
|
8
|
-
def self.argument_matches? argument
|
9
|
-
[:load] if argument == "--text"
|
10
|
-
end
|
11
|
-
|
12
|
-
def initialize
|
13
|
-
end
|
14
|
-
|
15
|
-
def start_processing
|
16
|
-
end
|
17
|
-
|
18
|
-
def end_processing
|
19
|
-
end
|
20
|
-
|
21
|
-
def start_test test, env
|
22
|
-
puts "#{BLUE}##### starting test #{test[:name]}.#{RESET}"
|
23
|
-
end
|
24
|
-
|
25
|
-
def end_test test
|
26
|
-
#puts "#{BLUE}##### finished test #{test[:name]}.#{RESET}"
|
27
|
-
end
|
28
|
-
|
29
|
-
def start_command line
|
30
|
-
puts "#{YELLOW}$ #{line[:cmd]}#{RESET}"
|
31
|
-
end
|
32
|
-
|
33
|
-
def end_command line, status, env
|
34
|
-
#puts ": $?=#{status}"
|
35
|
-
end
|
36
|
-
|
37
|
-
def command_out out
|
38
|
-
puts out
|
39
|
-
end
|
40
|
-
|
41
|
-
def command_err err
|
42
|
-
puts err
|
43
|
-
end
|
44
|
-
|
45
|
-
def test_processed test, status, msg
|
46
|
-
if status
|
47
|
-
puts "#{GREEN}# #{msg}#{RESET}"
|
48
|
-
else
|
49
|
-
puts "#{RED}# #{msg}#{RESET}"
|
50
|
-
end
|
51
|
-
end
|
52
|
-
end
|