excellent 1.5.4
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 +69 -0
- data/README.rdoc +72 -0
- data/VERSION.yml +4 -0
- data/bin/excellent +34 -0
- data/lib/simplabs/excellent.rb +16 -0
- data/lib/simplabs/excellent/checks.rb +33 -0
- data/lib/simplabs/excellent/checks/abc_metric_method_check.rb +43 -0
- data/lib/simplabs/excellent/checks/assignment_in_conditional_check.rb +39 -0
- data/lib/simplabs/excellent/checks/base.rb +62 -0
- data/lib/simplabs/excellent/checks/case_missing_else_check.rb +34 -0
- data/lib/simplabs/excellent/checks/class_line_count_check.rb +36 -0
- data/lib/simplabs/excellent/checks/class_name_check.rb +38 -0
- data/lib/simplabs/excellent/checks/control_coupling_check.rb +35 -0
- data/lib/simplabs/excellent/checks/cyclomatic_complexity_block_check.rb +48 -0
- data/lib/simplabs/excellent/checks/cyclomatic_complexity_check.rb +23 -0
- data/lib/simplabs/excellent/checks/cyclomatic_complexity_method_check.rb +48 -0
- data/lib/simplabs/excellent/checks/empty_rescue_body_check.rb +31 -0
- data/lib/simplabs/excellent/checks/flog_block_check.rb +40 -0
- data/lib/simplabs/excellent/checks/flog_check.rb +27 -0
- data/lib/simplabs/excellent/checks/flog_class_check.rb +40 -0
- data/lib/simplabs/excellent/checks/flog_method_check.rb +40 -0
- data/lib/simplabs/excellent/checks/for_loop_check.rb +42 -0
- data/lib/simplabs/excellent/checks/global_variable_check.rb +33 -0
- data/lib/simplabs/excellent/checks/line_count_check.rb +27 -0
- data/lib/simplabs/excellent/checks/method_line_count_check.rb +36 -0
- data/lib/simplabs/excellent/checks/method_name_check.rb +38 -0
- data/lib/simplabs/excellent/checks/module_line_count_check.rb +36 -0
- data/lib/simplabs/excellent/checks/module_name_check.rb +38 -0
- data/lib/simplabs/excellent/checks/name_check.rb +27 -0
- data/lib/simplabs/excellent/checks/nested_iterators_check.rb +34 -0
- data/lib/simplabs/excellent/checks/parameter_number_check.rb +38 -0
- data/lib/simplabs/excellent/checks/rails.rb +22 -0
- data/lib/simplabs/excellent/checks/rails/attr_accessible_check.rb +38 -0
- data/lib/simplabs/excellent/checks/rails/attr_protected_check.rb +39 -0
- data/lib/simplabs/excellent/checks/rails/custom_initialize_method_check.rb +37 -0
- data/lib/simplabs/excellent/checks/rails/instance_var_in_partial_check.rb +37 -0
- data/lib/simplabs/excellent/checks/rails/params_hash_in_view_check.rb +38 -0
- data/lib/simplabs/excellent/checks/rails/session_hash_in_view_check.rb +38 -0
- data/lib/simplabs/excellent/checks/rails/validations_check.rb +36 -0
- data/lib/simplabs/excellent/checks/singleton_variable_check.rb +33 -0
- data/lib/simplabs/excellent/command_line_runner.rb +37 -0
- data/lib/simplabs/excellent/extensions/sexp.rb +21 -0
- data/lib/simplabs/excellent/extensions/string.rb +28 -0
- data/lib/simplabs/excellent/formatters.rb +13 -0
- data/lib/simplabs/excellent/formatters/base.rb +49 -0
- data/lib/simplabs/excellent/formatters/html.rb +153 -0
- data/lib/simplabs/excellent/formatters/text.rb +40 -0
- data/lib/simplabs/excellent/parsing.rb +10 -0
- data/lib/simplabs/excellent/parsing/abc_measure.rb +52 -0
- data/lib/simplabs/excellent/parsing/block_context.rb +43 -0
- data/lib/simplabs/excellent/parsing/call_context.rb +52 -0
- data/lib/simplabs/excellent/parsing/case_context.rb +31 -0
- data/lib/simplabs/excellent/parsing/class_context.rb +99 -0
- data/lib/simplabs/excellent/parsing/code_processor.rb +165 -0
- data/lib/simplabs/excellent/parsing/conditional_context.rb +25 -0
- data/lib/simplabs/excellent/parsing/cvar_context.rb +28 -0
- data/lib/simplabs/excellent/parsing/cyclomatic_complexity_measure.rb +73 -0
- data/lib/simplabs/excellent/parsing/flog_measure.rb +192 -0
- data/lib/simplabs/excellent/parsing/for_loop_context.rb +15 -0
- data/lib/simplabs/excellent/parsing/gvar_context.rb +21 -0
- data/lib/simplabs/excellent/parsing/if_context.rb +38 -0
- data/lib/simplabs/excellent/parsing/ivar_context.rb +32 -0
- data/lib/simplabs/excellent/parsing/method_context.rb +50 -0
- data/lib/simplabs/excellent/parsing/module_context.rb +29 -0
- data/lib/simplabs/excellent/parsing/parser.rb +35 -0
- data/lib/simplabs/excellent/parsing/resbody_context.rb +39 -0
- data/lib/simplabs/excellent/parsing/scopeable.rb +34 -0
- data/lib/simplabs/excellent/parsing/sexp_context.rb +125 -0
- data/lib/simplabs/excellent/parsing/singleton_method_context.rb +55 -0
- data/lib/simplabs/excellent/parsing/until_context.rb +24 -0
- data/lib/simplabs/excellent/parsing/while_context.rb +24 -0
- data/lib/simplabs/excellent/rake.rb +1 -0
- data/lib/simplabs/excellent/rake/excellent_task.rb +61 -0
- data/lib/simplabs/excellent/runner.rb +143 -0
- data/lib/simplabs/excellent/warning.rb +53 -0
- data/spec/checks/abc_metric_method_check_spec.rb +122 -0
- data/spec/checks/assignment_in_conditional_check_spec.rb +90 -0
- data/spec/checks/case_missing_else_check_spec.rb +42 -0
- data/spec/checks/class_line_count_check_spec.rb +62 -0
- data/spec/checks/class_name_check_spec.rb +48 -0
- data/spec/checks/control_coupling_check_spec.rb +103 -0
- data/spec/checks/cyclomatic_complexity_block_check_spec.rb +47 -0
- data/spec/checks/cyclomatic_complexity_method_check_spec.rb +210 -0
- data/spec/checks/empty_rescue_body_check_spec.rb +170 -0
- data/spec/checks/flog_block_check_spec.rb +28 -0
- data/spec/checks/flog_class_check_spec.rb +28 -0
- data/spec/checks/flog_method_check_spec.rb +46 -0
- data/spec/checks/for_loop_check_spec.rb +52 -0
- data/spec/checks/global_variable_check_spec.rb +66 -0
- data/spec/checks/method_line_count_check_spec.rb +49 -0
- data/spec/checks/method_name_check_spec.rb +112 -0
- data/spec/checks/module_line_count_check_spec.rb +48 -0
- data/spec/checks/module_name_check_spec.rb +61 -0
- data/spec/checks/nested_iterators_check_spec.rb +44 -0
- data/spec/checks/parameter_number_check_spec.rb +97 -0
- data/spec/checks/rails/attr_accessible_check_spec.rb +79 -0
- data/spec/checks/rails/attr_protected_check_spec.rb +77 -0
- data/spec/checks/rails/custom_initialize_method_check_spec.rb +58 -0
- data/spec/checks/rails/instance_var_in_partial_check_spec.rb +40 -0
- data/spec/checks/rails/params_hash_in_view_check_spec.rb +40 -0
- data/spec/checks/rails/session_hash_in_view_check_spec.rb +40 -0
- data/spec/checks/rails/validations_check_spec.rb +81 -0
- data/spec/checks/singleton_variable_check_spec.rb +66 -0
- data/spec/extensions/string_spec.rb +13 -0
- data/spec/spec_helper.rb +13 -0
- metadata +189 -0
@@ -0,0 +1,53 @@
|
|
1
|
+
require 'simplabs/excellent/extensions/string'
|
2
|
+
|
3
|
+
module Simplabs
|
4
|
+
|
5
|
+
module Excellent
|
6
|
+
|
7
|
+
# The warnings returned by Excellent provide information about the +file+ the *possibly* problematic code was found in as well as the +line+ of the
|
8
|
+
# occurence, a warning message and a Hash with specific information about the warning.
|
9
|
+
#
|
10
|
+
# Warnings also provide the message template that was used to generate the message. The message template contains tokens like <tt>{{token}}</tt> that
|
11
|
+
# correspond to the valeus in the +info+ hash, e.g.:
|
12
|
+
#
|
13
|
+
# '{{method}} has abc score of {{score}}.'
|
14
|
+
# { :method => 'User#full_name', :score => 10 }
|
15
|
+
class Warning
|
16
|
+
|
17
|
+
# The check that produced the warning
|
18
|
+
attr_reader :check
|
19
|
+
|
20
|
+
# The name of the file the check found the problematic code in
|
21
|
+
attr_reader :filename
|
22
|
+
|
23
|
+
# The file number where the check found the problematic code
|
24
|
+
attr_reader :line_number
|
25
|
+
|
26
|
+
# The warning message
|
27
|
+
attr_reader :message
|
28
|
+
|
29
|
+
# Additional info for the warning (see above)
|
30
|
+
attr_reader :info
|
31
|
+
|
32
|
+
# The template used to produce the warning (see above)
|
33
|
+
attr_reader :message_template
|
34
|
+
|
35
|
+
def initialize(check, message, filename, line_number, info) #:nodoc:
|
36
|
+
@check = check.to_s.underscore.to_sym
|
37
|
+
@info = info
|
38
|
+
@filename = filename
|
39
|
+
@line_number = line_number.to_i
|
40
|
+
|
41
|
+
@message = ''
|
42
|
+
if !message.nil?
|
43
|
+
@message_template = message
|
44
|
+
@info.each { |key, value| message.gsub!(/\{\{#{key}\}\}/, value.to_s) }
|
45
|
+
@message = message
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
end
|
50
|
+
|
51
|
+
end
|
52
|
+
|
53
|
+
end
|
@@ -0,0 +1,122 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::AbcMetricMethodCheck do
|
4
|
+
|
5
|
+
before do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::AbcMetricMethodCheck.new({ :threshold => 0 }))
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
describe 'when processing assignments' do
|
12
|
+
|
13
|
+
it "should find =" do
|
14
|
+
code = <<-END
|
15
|
+
def method_name
|
16
|
+
foo = 1
|
17
|
+
end
|
18
|
+
END
|
19
|
+
|
20
|
+
verify_code_score(code, 1, 0, 0)
|
21
|
+
end
|
22
|
+
|
23
|
+
['*=', '/=', '%=', '+=', '<<=', '>>=', '&=', '|=', '^=', '-=', '**='].each do |assignment|
|
24
|
+
|
25
|
+
it "should find #{assignment}" do
|
26
|
+
code = <<-END
|
27
|
+
def method_name
|
28
|
+
foo #{assignment} 1
|
29
|
+
end
|
30
|
+
END
|
31
|
+
|
32
|
+
# these special assignments have score 2 since before the value is assigned, a method is called on the old value
|
33
|
+
verify_code_score(code, 1, 0, 1)
|
34
|
+
end
|
35
|
+
|
36
|
+
end
|
37
|
+
|
38
|
+
end
|
39
|
+
|
40
|
+
describe 'when processing branches' do
|
41
|
+
|
42
|
+
it 'should find a virtual method call' do
|
43
|
+
code = <<-END
|
44
|
+
def method_name
|
45
|
+
call_foo
|
46
|
+
end
|
47
|
+
END
|
48
|
+
|
49
|
+
verify_code_score(code, 0, 1, 0)
|
50
|
+
end
|
51
|
+
|
52
|
+
it 'should find an explicit method call' do
|
53
|
+
code = <<-END
|
54
|
+
def method_name
|
55
|
+
@object.call_foo
|
56
|
+
end
|
57
|
+
END
|
58
|
+
|
59
|
+
verify_code_score(code, 0, 1, 0)
|
60
|
+
end
|
61
|
+
|
62
|
+
it 'should exclude a condition' do
|
63
|
+
code = <<-END
|
64
|
+
def method_name
|
65
|
+
@object.call_foo < 10
|
66
|
+
end
|
67
|
+
END
|
68
|
+
|
69
|
+
verify_code_score(code, 0, 1, 1)
|
70
|
+
end
|
71
|
+
|
72
|
+
end
|
73
|
+
|
74
|
+
describe 'when processing conditions' do
|
75
|
+
|
76
|
+
['==', '!=', '<=', '>=', '<', '>', '<=>', '=~'].each do |conditional|
|
77
|
+
|
78
|
+
it "should find #{conditional}" do
|
79
|
+
code = <<-END
|
80
|
+
def method_name
|
81
|
+
@foo #{conditional} @bar
|
82
|
+
end
|
83
|
+
END
|
84
|
+
|
85
|
+
verify_code_score(code, 0, 0, 1)
|
86
|
+
end
|
87
|
+
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
91
|
+
|
92
|
+
it 'should also work on singleton methods' do
|
93
|
+
code = <<-END
|
94
|
+
class Class
|
95
|
+
def self.method_name
|
96
|
+
foo = 1
|
97
|
+
end
|
98
|
+
end
|
99
|
+
END
|
100
|
+
@excellent.check_code(code)
|
101
|
+
warnings = @excellent.warnings
|
102
|
+
|
103
|
+
warnings.should_not be_empty
|
104
|
+
warnings[0].info.should == { :method => 'Class.method_name', :score => 1.0 }
|
105
|
+
warnings[0].line_number.should == 2
|
106
|
+
warnings[0].message.should == 'Class.method_name has abc score of 1.0.'
|
107
|
+
end
|
108
|
+
|
109
|
+
end
|
110
|
+
|
111
|
+
def verify_code_score(code, a, b, c)
|
112
|
+
score = Math.sqrt(a*a + b*b + c*c)
|
113
|
+
@excellent.check_code(code)
|
114
|
+
warnings = @excellent.warnings
|
115
|
+
|
116
|
+
warnings.should_not be_empty
|
117
|
+
warnings[0].info.should == { :method => 'method_name', :score => score }
|
118
|
+
warnings[0].line_number.should == 1
|
119
|
+
warnings[0].message.should == "method_name has abc score of #{score}."
|
120
|
+
end
|
121
|
+
|
122
|
+
end
|
@@ -0,0 +1,90 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::AssignmentInConditionalCheck do
|
4
|
+
|
5
|
+
before do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::AssignmentInConditionalCheck.new)
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
it 'should accept an assignment before an if clause' do
|
12
|
+
code = <<-END
|
13
|
+
count = count += 1 if @some_condition
|
14
|
+
END
|
15
|
+
@excellent.check_code(code)
|
16
|
+
|
17
|
+
@excellent.warnings.should be_empty
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'should accept block parameters in an if clause' do
|
21
|
+
code = <<-END
|
22
|
+
return true if exp.children.any? { |child| contains_statements?(child) }
|
23
|
+
END
|
24
|
+
@excellent.check_code(code)
|
25
|
+
|
26
|
+
@excellent.warnings.should be_empty
|
27
|
+
end
|
28
|
+
|
29
|
+
it 'should reject assignments of results of blocks in an if clause' do
|
30
|
+
code = <<-END
|
31
|
+
return true if value = exp.children.find { |child| contains_statements?(child) }
|
32
|
+
END
|
33
|
+
|
34
|
+
verify_warning_found(code)
|
35
|
+
end
|
36
|
+
|
37
|
+
it 'should reject an assignment inside an if clause' do
|
38
|
+
code = <<-END
|
39
|
+
call_foo if bar = bam
|
40
|
+
END
|
41
|
+
|
42
|
+
verify_warning_found(code)
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'should reject an assignment inside an unless clause' do
|
46
|
+
code = <<-END
|
47
|
+
call_foo unless bar = bam
|
48
|
+
END
|
49
|
+
|
50
|
+
verify_warning_found(code)
|
51
|
+
end
|
52
|
+
|
53
|
+
it 'should reject an assignment inside a while clause' do
|
54
|
+
code = <<-END
|
55
|
+
call_foo while bar = bam
|
56
|
+
END
|
57
|
+
|
58
|
+
verify_warning_found(code)
|
59
|
+
end
|
60
|
+
|
61
|
+
it 'should reject an assignment inside an until clause' do
|
62
|
+
code = <<-END
|
63
|
+
call_foo until bar = bam
|
64
|
+
END
|
65
|
+
|
66
|
+
verify_warning_found(code)
|
67
|
+
end
|
68
|
+
|
69
|
+
it 'should reject an assignment inside a ternary operator check clause' do
|
70
|
+
code = <<-END
|
71
|
+
call_foo (bar = bam) ? baz : bad
|
72
|
+
END
|
73
|
+
|
74
|
+
#RubyParser sets line number 2 here
|
75
|
+
verify_warning_found(code, 2)
|
76
|
+
end
|
77
|
+
|
78
|
+
end
|
79
|
+
|
80
|
+
def verify_warning_found(code, line_number = nil)
|
81
|
+
@excellent.check_code(code)
|
82
|
+
warnings = @excellent.warnings
|
83
|
+
|
84
|
+
warnings.should_not be_empty
|
85
|
+
warnings[0].info.should == {}
|
86
|
+
warnings[0].line_number.should == (line_number || 1)
|
87
|
+
warnings[0].message.should == 'Assignment in condition.'
|
88
|
+
end
|
89
|
+
|
90
|
+
end
|
@@ -0,0 +1,42 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::CaseMissingElseCheck do
|
4
|
+
|
5
|
+
before do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::CaseMissingElseCheck.new)
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
it 'should accept case statements that do have an else clause' do
|
12
|
+
code = <<-END
|
13
|
+
case foo
|
14
|
+
when "bar": "ok"
|
15
|
+
else "good"
|
16
|
+
end
|
17
|
+
END
|
18
|
+
@excellent.check_code(code)
|
19
|
+
warnings = @excellent.warnings
|
20
|
+
|
21
|
+
warnings.should be_empty
|
22
|
+
end
|
23
|
+
|
24
|
+
it 'should reject case statements that do not have an else clause' do
|
25
|
+
code = <<-END
|
26
|
+
case foo
|
27
|
+
when "bar": "ok"
|
28
|
+
when "bar": "bad"
|
29
|
+
end
|
30
|
+
END
|
31
|
+
@excellent.check_code(code)
|
32
|
+
warnings = @excellent.warnings
|
33
|
+
|
34
|
+
warnings.should_not be_empty
|
35
|
+
warnings[0].info.should == {}
|
36
|
+
warnings[0].line_number.should == 2
|
37
|
+
warnings[0].message.should == 'Case statement is missing else clause.'
|
38
|
+
end
|
39
|
+
|
40
|
+
end
|
41
|
+
|
42
|
+
end
|
@@ -0,0 +1,62 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::ClassLineCountCheck do
|
4
|
+
|
5
|
+
before do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::ClassLineCountCheck.new({ :threshold => 3 }))
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
it 'should accept classes with less lines than the threshold' do
|
12
|
+
code = <<-END
|
13
|
+
class OneLineClass; end
|
14
|
+
END
|
15
|
+
@excellent.check_code(code)
|
16
|
+
|
17
|
+
@excellent.warnings.should be_empty
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'should accept classes with the same number of lines as the threshold' do
|
21
|
+
code = <<-END
|
22
|
+
class ThreeLineClass
|
23
|
+
@foo = 1
|
24
|
+
end
|
25
|
+
END
|
26
|
+
@excellent.check_code(code)
|
27
|
+
|
28
|
+
@excellent.warnings.should be_empty
|
29
|
+
end
|
30
|
+
|
31
|
+
it 'should not count blank lines' do
|
32
|
+
code = <<-END
|
33
|
+
class ThreeLineClass
|
34
|
+
|
35
|
+
@foo = 1
|
36
|
+
|
37
|
+
end
|
38
|
+
END
|
39
|
+
@excellent.check_code(code)
|
40
|
+
|
41
|
+
@excellent.warnings.should be_empty
|
42
|
+
end
|
43
|
+
|
44
|
+
it 'should reject classes with more lines than the threshold' do
|
45
|
+
code = <<-END
|
46
|
+
class FourLineClass
|
47
|
+
@foo = 1
|
48
|
+
@bar = 2
|
49
|
+
end
|
50
|
+
END
|
51
|
+
@excellent.check_code(code)
|
52
|
+
warnings = @excellent.warnings
|
53
|
+
|
54
|
+
warnings.should_not be_empty
|
55
|
+
warnings[0].info.should == { :class => 'FourLineClass', :count => 4 }
|
56
|
+
warnings[0].line_number.should == 1
|
57
|
+
warnings[0].message.should == 'FourLineClass has 4 lines.'
|
58
|
+
end
|
59
|
+
|
60
|
+
end
|
61
|
+
|
62
|
+
end
|
@@ -0,0 +1,48 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::ClassNameCheck do
|
4
|
+
|
5
|
+
before(:each) do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::ClassNameCheck.new)
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
it 'should accept camel case class names starting in capitals' do
|
12
|
+
code = <<-END
|
13
|
+
class GoodClassName; end
|
14
|
+
END
|
15
|
+
@excellent.check_code(code)
|
16
|
+
|
17
|
+
@excellent.warnings.should be_empty
|
18
|
+
end
|
19
|
+
|
20
|
+
it 'should be able to parse scoped class names' do
|
21
|
+
code = <<-END
|
22
|
+
class Outer::Inner::GoodClassName
|
23
|
+
def method
|
24
|
+
end
|
25
|
+
end
|
26
|
+
END
|
27
|
+
@excellent.check_code(code)
|
28
|
+
s
|
29
|
+
@excellent.warnings.should be_empty
|
30
|
+
end
|
31
|
+
|
32
|
+
it 'should reject class names with underscores' do
|
33
|
+
code = <<-END
|
34
|
+
class Bad_ClassName
|
35
|
+
end
|
36
|
+
END
|
37
|
+
@excellent.check_code(code)
|
38
|
+
warnings = @excellent.warnings
|
39
|
+
|
40
|
+
warnings.should_not be_empty
|
41
|
+
warnings[0].info.should == { :class => 'Bad_ClassName' }
|
42
|
+
warnings[0].line_number.should == 1
|
43
|
+
warnings[0].message.should == 'Bad class name Bad_ClassName.'
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
|
48
|
+
end
|
@@ -0,0 +1,103 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
2
|
+
|
3
|
+
describe Simplabs::Excellent::Checks::ControlCouplingCheck do
|
4
|
+
|
5
|
+
before(:each) do
|
6
|
+
@excellent = Simplabs::Excellent::Runner.new(Simplabs::Excellent::Checks::ControlCouplingCheck.new)
|
7
|
+
end
|
8
|
+
|
9
|
+
describe '#evaluate' do
|
10
|
+
|
11
|
+
it 'should accept methods that just print out the parameter' do
|
12
|
+
code = <<-END
|
13
|
+
def write(quoted)
|
14
|
+
pp quoted
|
15
|
+
end
|
16
|
+
END
|
17
|
+
@excellent.check_code(code)
|
18
|
+
warnings = @excellent.warnings
|
19
|
+
|
20
|
+
warnings.should be_empty
|
21
|
+
end
|
22
|
+
|
23
|
+
it 'should accept methods with ternary operators using an instance variable' do
|
24
|
+
code = <<-END
|
25
|
+
def write(quoted)
|
26
|
+
@quoted ? write_quoted('1') : write_quoted('2')
|
27
|
+
end
|
28
|
+
END
|
29
|
+
|
30
|
+
@excellent.check_code(code)
|
31
|
+
warnings = @excellent.warnings
|
32
|
+
|
33
|
+
warnings.should be_empty
|
34
|
+
end
|
35
|
+
|
36
|
+
it 'should accept methods with ternary operators using a local variable' do
|
37
|
+
code = <<-END
|
38
|
+
def write(quoted)
|
39
|
+
test = false
|
40
|
+
test ? write_quoted('1') : write_quoted('2')
|
41
|
+
end
|
42
|
+
END
|
43
|
+
|
44
|
+
@excellent.check_code(code)
|
45
|
+
warnings = @excellent.warnings
|
46
|
+
|
47
|
+
warnings.should be_empty
|
48
|
+
end
|
49
|
+
|
50
|
+
%w(if unless).each do |conditional|
|
51
|
+
|
52
|
+
it "should reject methods with #{conditional} checks using a parameter" do
|
53
|
+
code = <<-END
|
54
|
+
def write(quoted)
|
55
|
+
#{conditional} quoted
|
56
|
+
write_quoted('test')
|
57
|
+
end
|
58
|
+
end
|
59
|
+
END
|
60
|
+
|
61
|
+
verify_warning_found(code)
|
62
|
+
end
|
63
|
+
|
64
|
+
end
|
65
|
+
|
66
|
+
it 'should reject methods with ternary operators using a parameter' do
|
67
|
+
code = <<-END
|
68
|
+
def write(quoted)
|
69
|
+
quoted ? write_quoted('1') : write_quoted('2')
|
70
|
+
end
|
71
|
+
END
|
72
|
+
|
73
|
+
verify_warning_found(code)
|
74
|
+
end
|
75
|
+
|
76
|
+
it "should reject methods with case statements using a parameter" do
|
77
|
+
code = <<-END
|
78
|
+
def write(quoted)
|
79
|
+
case quoted
|
80
|
+
when 1
|
81
|
+
write_quoted('1')
|
82
|
+
when 2
|
83
|
+
write_quoted('2')
|
84
|
+
end
|
85
|
+
end
|
86
|
+
END
|
87
|
+
|
88
|
+
verify_warning_found(code)
|
89
|
+
end
|
90
|
+
|
91
|
+
end
|
92
|
+
|
93
|
+
def verify_warning_found(code)
|
94
|
+
@excellent.check_code(code)
|
95
|
+
warnings = @excellent.warnings
|
96
|
+
|
97
|
+
warnings.should_not be_empty
|
98
|
+
warnings[0].info.should == { :method => 'write', :argument => 'quoted' }
|
99
|
+
warnings[0].line_number.should == 1
|
100
|
+
warnings[0].message.should == 'write is coupled to quoted.'
|
101
|
+
end
|
102
|
+
|
103
|
+
end
|