rails_best_practices 0.6.6 → 0.6.7

Sign up to get free protection for your applications and to get access to all the features.
Files changed (79) hide show
  1. data/Gemfile +0 -1
  2. data/README.md +28 -24
  3. data/Rakefile +0 -8
  4. data/install_supported_rubies.sh +2 -3
  5. data/lib/rails_best_practices.rb +8 -7
  6. data/lib/rails_best_practices/core.rb +1 -0
  7. data/lib/rails_best_practices/core/check.rb +68 -0
  8. data/lib/rails_best_practices/core/checking_visitor.rb +18 -15
  9. data/lib/rails_best_practices/core/runner.rb +22 -12
  10. data/lib/rails_best_practices/core/visitable_sexp.rb +6 -2
  11. data/lib/rails_best_practices/prepares.rb +11 -0
  12. data/lib/rails_best_practices/prepares/mailer_prepare.rb +33 -0
  13. data/lib/rails_best_practices/prepares/model_prepare.rb +60 -0
  14. data/lib/rails_best_practices/reviews.rb +23 -0
  15. data/lib/rails_best_practices/{checks/add_model_virtual_attribute_check.rb → reviews/add_model_virtual_attribute_review.rb} +6 -9
  16. data/lib/rails_best_practices/{checks/always_add_db_index_check.rb → reviews/always_add_db_index_review.rb} +9 -12
  17. data/lib/rails_best_practices/{checks/dry_bundler_in_capistrano_check.rb → reviews/dry_bundler_in_capistrano_review.rb} +8 -11
  18. data/lib/rails_best_practices/{checks/isolate_seed_data_check.rb → reviews/isolate_seed_data_review.rb} +11 -14
  19. data/lib/rails_best_practices/{checks/keep_finders_on_their_own_model_check.rb → reviews/keep_finders_on_their_own_model_review.rb} +7 -10
  20. data/lib/rails_best_practices/{checks/law_of_demeter_check.rb → reviews/law_of_demeter_review.rb} +10 -14
  21. data/lib/rails_best_practices/{checks/move_code_into_controller_check.rb → reviews/move_code_into_controller_review.rb} +8 -11
  22. data/lib/rails_best_practices/{checks/move_code_into_helper_check.rb → reviews/move_code_into_helper_review.rb} +7 -10
  23. data/lib/rails_best_practices/{checks/move_code_into_model_check.rb → reviews/move_code_into_model_review.rb} +7 -10
  24. data/lib/rails_best_practices/{checks/move_finder_to_named_scope_check.rb → reviews/move_finder_to_named_scope_review.rb} +7 -10
  25. data/lib/rails_best_practices/{checks/move_model_logic_into_model_check.rb → reviews/move_model_logic_into_model_review.rb} +8 -11
  26. data/lib/rails_best_practices/{checks/needless_deep_nesting_check.rb → reviews/needless_deep_nesting_review.rb} +8 -11
  27. data/lib/rails_best_practices/{checks/not_use_default_route_check.rb → reviews/not_use_default_route_review.rb} +7 -10
  28. data/lib/rails_best_practices/{checks/overuse_route_customizations_check.rb → reviews/overuse_route_customizations_review.rb} +10 -13
  29. data/lib/rails_best_practices/{checks/replace_complex_creation_with_factory_method_check.rb → reviews/replace_complex_creation_with_factory_method_review.rb} +8 -11
  30. data/lib/rails_best_practices/{checks/replace_instance_variable_with_local_variable_check.rb → reviews/replace_instance_variable_with_local_variable_review.rb} +7 -10
  31. data/lib/rails_best_practices/reviews/review.rb +92 -0
  32. data/lib/rails_best_practices/{checks/use_before_filter_check.rb → reviews/use_before_filter_review.rb} +8 -11
  33. data/lib/rails_best_practices/{checks/use_model_association_check.rb → reviews/use_model_association_review.rb} +8 -11
  34. data/lib/rails_best_practices/{checks/use_observer_check.rb → reviews/use_observer_review.rb} +14 -41
  35. data/lib/rails_best_practices/{checks/use_query_attribute_check.rb → reviews/use_query_attribute_review.rb} +20 -16
  36. data/lib/rails_best_practices/{checks/use_say_with_time_in_migrations_check.rb → reviews/use_say_with_time_in_migrations_review.rb} +8 -11
  37. data/lib/rails_best_practices/{checks/use_scope_access_check.rb → reviews/use_scope_access_review.rb} +8 -11
  38. data/lib/rails_best_practices/version.rb +1 -1
  39. data/rails_best_practices.gemspec +3 -2
  40. data/rails_best_practices.yml +22 -22
  41. data/rake_rubies.sh +3 -2
  42. data/spec/rails_best_practices/core/check_spec.rb +41 -0
  43. data/spec/rails_best_practices/core/checking_visitor_spec.rb +78 -0
  44. data/spec/rails_best_practices/core/visitable_sexp_spec.rb +39 -36
  45. data/spec/rails_best_practices/prepares/mailer_prepare_spec.rb +14 -0
  46. data/spec/rails_best_practices/prepares/model_prepare_spec.rb +22 -0
  47. data/spec/rails_best_practices/{checks/add_model_virtual_attribute_check_spec.rb → reviews/add_model_virtual_attribute_review_spec.rb} +17 -25
  48. data/spec/rails_best_practices/{checks/always_add_db_index_check_spec.rb → reviews/always_add_db_index_review_spec.rb} +28 -41
  49. data/spec/rails_best_practices/{checks/dry_bundler_in_capistrano_check_spec.rb → reviews/dry_bundler_in_capistrano_review_spec.rb} +7 -11
  50. data/spec/rails_best_practices/{checks/isolate_seed_data_check_spec.rb → reviews/isolate_seed_data_review_spec.rb} +13 -20
  51. data/spec/rails_best_practices/{checks/keep_finders_on_their_own_model_check_spec.rb → reviews/keep_finders_on_their_own_model_review_spec.rb} +16 -24
  52. data/spec/rails_best_practices/{checks/law_of_demeter_check_spec.rb → reviews/law_of_demeter_review_spec.rb} +24 -26
  53. data/spec/rails_best_practices/reviews/move_code_into_controller_review_spec.rb +29 -0
  54. data/spec/rails_best_practices/reviews/move_code_into_helper_review_spec.rb +24 -0
  55. data/spec/rails_best_practices/{checks/move_code_into_model_check_spec.rb → reviews/move_code_into_model_review_spec.rb} +12 -18
  56. data/spec/rails_best_practices/{checks/move_finder_to_named_scope_check_spec.rb → reviews/move_finder_to_named_scope_review_spec.rb} +12 -16
  57. data/spec/rails_best_practices/{checks/move_model_logic_into_model_check_spec.rb → reviews/move_model_logic_into_model_review_spec.rb} +7 -11
  58. data/spec/rails_best_practices/{checks/needless_deep_nesting_check_spec.rb → reviews/needless_deep_nesting_review_spec.rb} +26 -37
  59. data/spec/rails_best_practices/{checks/not_use_default_route_check_spec.rb → reviews/not_use_default_route_review_spec.rb} +13 -19
  60. data/spec/rails_best_practices/{checks/overuse_route_customizations_check_spec.rb → reviews/overuse_route_customizations_review_spec.rb} +27 -39
  61. data/spec/rails_best_practices/{checks/replace_complex_creation_with_factory_method_check_spec.rb → reviews/replace_complex_creation_with_factory_method_review_spec.rb} +10 -15
  62. data/spec/rails_best_practices/reviews/replace_instance_variable_with_local_variable_review_spec.rb +31 -0
  63. data/spec/rails_best_practices/reviews/review_spec.rb +11 -0
  64. data/spec/rails_best_practices/{checks/use_before_filter_check_spec.rb → reviews/use_before_filter_review_spec.rb} +11 -17
  65. data/spec/rails_best_practices/{checks/use_model_association_check_spec.rb → reviews/use_model_association_review_spec.rb} +12 -18
  66. data/spec/rails_best_practices/{checks/use_observer_check_spec.rb → reviews/use_observer_review_spec.rb} +28 -29
  67. data/spec/rails_best_practices/reviews/use_query_attribute_review_spec.rb +190 -0
  68. data/spec/rails_best_practices/{checks/use_say_with_time_in_migrations_check_spec.rb → reviews/use_say_with_time_in_migrations_review_spec.rb} +14 -23
  69. data/spec/rails_best_practices/{checks/use_scope_access_check_spec.rb → reviews/use_scope_access_review_spec.rb} +28 -37
  70. data/spec/rails_best_practices_spec.rb +4 -4
  71. data/spec/spec_helper.rb +1 -0
  72. metadata +128 -102
  73. data/lib/rails_best_practices/checks.rb +0 -23
  74. data/lib/rails_best_practices/checks/check.rb +0 -203
  75. data/spec/rails_best_practices/checks/check_spec.rb +0 -57
  76. data/spec/rails_best_practices/checks/move_code_into_controller_check_spec.rb +0 -33
  77. data/spec/rails_best_practices/checks/move_code_into_helper_check_spec.rb +0 -28
  78. data/spec/rails_best_practices/checks/replace_instance_variable_with_local_variable_check_spec.rb +0 -36
  79. data/spec/rails_best_practices/checks/use_query_attribute_check_spec.rb +0 -192
@@ -1,9 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
- describe RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodCheck do
4
- before(:each) do
5
- @runner = RailsBestPractices::Core::Runner.new(RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodCheck.new)
6
- end
3
+ describe RailsBestPractices::Reviews::ReplaceComplexCreationWithFactoryMethodReview do
4
+ let(:runner) { RailsBestPractices::Core::Runner.new(:reviews => RailsBestPractices::Reviews::ReplaceComplexCreationWithFactoryMethodReview.new) }
7
5
 
8
6
  it "should replace complex creation with factory method" do
9
7
  content = <<-EOF
@@ -25,10 +23,9 @@ describe RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodChec
25
23
  end
26
24
  end
27
25
  EOF
28
- @runner.review('app/controllers/invoices_controller.rb', content)
29
- errors = @runner.errors
30
- errors.should_not be_empty
31
- errors[0].to_s.should == "app/controllers/invoices_controller.rb:3 - replace complex creation with factory method (@invoice attribute_assignment_count > 2)"
26
+ runner.review('app/controllers/invoices_controller.rb', content)
27
+ runner.should have(1).errors
28
+ runner.errors[0].to_s.should == "app/controllers/invoices_controller.rb:3 - replace complex creation with factory method (@invoice attribute_assignment_count > 2)"
32
29
  end
33
30
 
34
31
  it "should not replace complex creation with factory method with simple creation" do
@@ -43,9 +40,8 @@ describe RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodChec
43
40
  end
44
41
  end
45
42
  EOF
46
- @runner.review('app/controllers/invoices_controller.rb', content)
47
- errors = @runner.errors
48
- errors.should be_empty
43
+ runner.review('app/controllers/invoices_controller.rb', content)
44
+ runner.should have(0).errors
49
45
  end
50
46
 
51
47
  it "should not replace complex creation with factory method when attrasgn_count is 5" do
@@ -68,9 +64,8 @@ describe RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodChec
68
64
  end
69
65
  end
70
66
  EOF
71
- @runner = RailsBestPractices::Core::Runner.new(RailsBestPractices::Checks::ReplaceComplexCreationWithFactoryMethodCheck.new('attribute_assignment_count' => 5))
72
- @runner.review('app/controllers/invoices_controller.rb', content)
73
- errors = @runner.errors
74
- errors.should be_empty
67
+ runner = RailsBestPractices::Core::Runner.new(:reviews => RailsBestPractices::Reviews::ReplaceComplexCreationWithFactoryMethodReview.new('attribute_assignment_count' => 5))
68
+ runner.review('app/controllers/invoices_controller.rb', content)
69
+ runner.should have(0).errors
75
70
  end
76
71
  end
@@ -0,0 +1,31 @@
1
+ require 'spec_helper'
2
+
3
+ describe RailsBestPractices::Reviews::ReplaceInstanceVariableWithLocalVariableReview do
4
+ let(:runner) { RailsBestPractices::Core::Runner.new(:reviews => RailsBestPractices::Reviews::ReplaceInstanceVariableWithLocalVariableReview.new) }
5
+
6
+ it "should replace instance variable with local varialbe" do
7
+ content = <<-EOF
8
+ <%= @post.title %>
9
+ EOF
10
+ runner.review('app/views/posts/_post.html.erb', content)
11
+ runner.should have(1).errors
12
+ runner.errors[0].to_s.should == "app/views/posts/_post.html.erb:1 - replace instance variable with local variable"
13
+ end
14
+
15
+ it "should replace instance variable with local varialbe in haml file" do
16
+ content = <<-EOF
17
+ = @post.title
18
+ EOF
19
+ runner.review('app/views/posts/_post.html.haml', content)
20
+ runner.should have(1).errors
21
+ runner.errors[0].to_s.should == "app/views/posts/_post.html.haml:1 - replace instance variable with local variable"
22
+ end
23
+
24
+ it "should not replace instance variable with local varialbe" do
25
+ content = <<-EOF
26
+ <%= post.title %>
27
+ EOF
28
+ runner.review('app/views/posts/_post.html.erb', content)
29
+ runner.should have(0).errors
30
+ end
31
+ end
@@ -0,0 +1,11 @@
1
+ require 'spec_helper'
2
+
3
+ describe RailsBestPractices::Reviews::Review do
4
+ let(:check) { RailsBestPractices::Reviews::Review.new }
5
+
6
+ context "equal?" do
7
+ it "should be true when compare symbol string with symbol" do
8
+ check.equal?(":test", :test).should be_true
9
+ end
10
+ end
11
+ end
@@ -1,9 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
- describe RailsBestPractices::Checks::UseBeforeFilterCheck do
4
- before(:each) do
5
- @runner = RailsBestPractices::Core::Runner.new(RailsBestPractices::Checks::UseBeforeFilterCheck.new)
6
- end
3
+ describe RailsBestPractices::Reviews::UseBeforeFilterReview do
4
+ let(:runner) { RailsBestPractices::Core::Runner.new(:reviews => RailsBestPractices::Reviews::UseBeforeFilterReview.new) }
7
5
 
8
6
  it "should use before_filter" do
9
7
  content = <<-EOF
@@ -29,10 +27,9 @@ describe RailsBestPractices::Checks::UseBeforeFilterCheck do
29
27
 
30
28
  end
31
29
  EOF
32
- @runner.review('app/controllers/posts_controller.rb', content)
33
- errors = @runner.errors
34
- errors.should_not be_empty
35
- errors[0].to_s.should == "app/controllers/posts_controller.rb:3,7,11,16 - use before_filter for show,edit,update,destroy"
30
+ runner.review('app/controllers/posts_controller.rb', content)
31
+ runner.should have(1).errors
32
+ runner.errors[0].to_s.should == "app/controllers/posts_controller.rb:3,7,11,16 - use before_filter for show,edit,update,destroy"
36
33
  end
37
34
 
38
35
  it "should not use before_filter" do
@@ -55,9 +52,8 @@ describe RailsBestPractices::Checks::UseBeforeFilterCheck do
55
52
  end
56
53
  end
57
54
  EOF
58
- @runner.review('app/controllers/posts_controller.rb', content)
59
- errors = @runner.errors
60
- errors.should be_empty
55
+ runner.review('app/controllers/posts_controller.rb', content)
56
+ runner.should have(0).errors
61
57
  end
62
58
 
63
59
  it "should not use before_filter by nil" do
@@ -78,9 +74,8 @@ describe RailsBestPractices::Checks::UseBeforeFilterCheck do
78
74
 
79
75
  end
80
76
  EOF
81
- @runner.review('app/controllers/posts_controller.rb', content)
82
- errors = @runner.errors
83
- errors.should be_empty
77
+ runner.review('app/controllers/posts_controller.rb', content)
78
+ runner.should have(0).errors
84
79
  end
85
80
 
86
81
  it "should not use before_filter for protected/private methods" do
@@ -98,8 +93,7 @@ describe RailsBestPractices::Checks::UseBeforeFilterCheck do
98
93
  end
99
94
  end
100
95
  EOF
101
- @runner.review('app/controllers/posts_controller.rb', content)
102
- errors = @runner.errors
103
- errors.should be_empty
96
+ runner.review('app/controllers/posts_controller.rb', content)
97
+ runner.should have(0).errors
104
98
  end
105
99
  end
@@ -1,9 +1,7 @@
1
1
  require 'spec_helper'
2
2
 
3
- describe RailsBestPractices::Checks::UseModelAssociationCheck do
4
- before(:each) do
5
- @runner = RailsBestPractices::Core::Runner.new(RailsBestPractices::Checks::UseModelAssociationCheck.new)
6
- end
3
+ describe RailsBestPractices::Reviews::UseModelAssociationReview do
4
+ let(:runner) { RailsBestPractices::Core::Runner.new(:reviews => RailsBestPractices::Reviews::UseModelAssociationReview.new) }
7
5
 
8
6
  it "should use model association for instance variable" do
9
7
  content = <<-EOF
@@ -16,10 +14,9 @@ describe RailsBestPractices::Checks::UseModelAssociationCheck do
16
14
  end
17
15
  end
18
16
  EOF
19
- @runner.review('app/controllers/posts_controller.rb', content)
20
- errors = @runner.errors
21
- errors.should_not be_empty
22
- errors[0].to_s.should == "app/controllers/posts_controller.rb:3 - use model association (for @post)"
17
+ runner.review('app/controllers/posts_controller.rb', content)
18
+ runner.should have(1).errors
19
+ runner.errors[0].to_s.should == "app/controllers/posts_controller.rb:3 - use model association (for @post)"
23
20
  end
24
21
 
25
22
  it "should not use model association without association assign" do
@@ -32,9 +29,8 @@ describe RailsBestPractices::Checks::UseModelAssociationCheck do
32
29
  end
33
30
  end
34
31
  EOF
35
- @runner.review('app/controllers/posts_controller.rb', content)
36
- errors = @runner.errors
37
- errors.should be_empty
32
+ runner.review('app/controllers/posts_controller.rb', content)
33
+ runner.should have(0).errors
38
34
  end
39
35
 
40
36
  it "should use model association for local variable" do
@@ -48,10 +44,9 @@ describe RailsBestPractices::Checks::UseModelAssociationCheck do
48
44
  end
49
45
  end
50
46
  EOF
51
- @runner.review('app/controllers/posts_controller.rb', content)
52
- errors = @runner.errors
53
- errors.should_not be_empty
54
- errors[0].to_s.should == "app/controllers/posts_controller.rb:3 - use model association (for post)"
47
+ runner.review('app/controllers/posts_controller.rb', content)
48
+ runner.should have(1).errors
49
+ runner.errors[0].to_s.should == "app/controllers/posts_controller.rb:3 - use model association (for post)"
55
50
  end
56
51
 
57
52
  it "should not use model association" do
@@ -64,8 +59,7 @@ describe RailsBestPractices::Checks::UseModelAssociationCheck do
64
59
  end
65
60
  end
66
61
  EOF
67
- @runner.review('app/controllers/posts_controller.rb', content)
68
- errors = @runner.errors
69
- errors.should be_empty
62
+ runner.review('app/controllers/posts_controller.rb', content)
63
+ runner.should have(0).errors
70
64
  end
71
65
  end
@@ -1,14 +1,19 @@
1
1
  require 'spec_helper'
2
2
 
3
- describe RailsBestPractices::Checks::UseObserverCheck do
4
- before(:each) do
5
- @runner = RailsBestPractices::Core::Runner.new(RailsBestPractices::Checks::UseObserverCheck.new)
6
-
3
+ describe RailsBestPractices::Reviews::UseObserverReview do
4
+ let(:runner) {
5
+ RailsBestPractices::Core::Runner.new(
6
+ :prepares => RailsBestPractices::Prepares::MailerPrepare.new,
7
+ :reviews => RailsBestPractices::Reviews::UseObserverReview.new
8
+ )
9
+ }
10
+
11
+ before :each do
7
12
  content =<<-EOF
8
13
  class ProjectMailer < ActionMailer::Base
9
14
  end
10
15
  EOF
11
- @runner.prepare('app/models/project_mailer.rb', content)
16
+ runner.prepare('app/models/project_mailer.rb', content)
12
17
  end
13
18
 
14
19
  describe "rails2" do
@@ -26,10 +31,9 @@ describe RailsBestPractices::Checks::UseObserverCheck do
26
31
  end
27
32
  end
28
33
  EOF
29
- @runner.review('app/models/project.rb', content)
30
- errors = @runner.errors
31
- errors.should_not be_empty
32
- errors[0].to_s.should == "app/models/project.rb:6 - use observer"
34
+ runner.review('app/models/project.rb', content)
35
+ runner.should have(1).errors
36
+ runner.errors[0].to_s.should == "app/models/project.rb:6 - use observer"
33
37
  end
34
38
 
35
39
  it "should not use observer without callback" do
@@ -44,9 +48,8 @@ describe RailsBestPractices::Checks::UseObserverCheck do
44
48
  end
45
49
  end
46
50
  EOF
47
- @runner.review('app/models/project.rb', content)
48
- errors = @runner.errors
49
- errors.should be_empty
51
+ runner.review('app/models/project.rb', content)
52
+ runner.should have(0).errors
50
53
  end
51
54
 
52
55
  it "should use observer with two after_create" do
@@ -66,10 +69,9 @@ describe RailsBestPractices::Checks::UseObserverCheck do
66
69
  end
67
70
  end
68
71
  EOF
69
- @runner.review('app/models/project.rb', content)
70
- errors = @runner.errors
71
- errors.should_not be_empty
72
- errors[0].to_s.should == "app/models/project.rb:6 - use observer"
72
+ runner.review('app/models/project.rb', content)
73
+ runner.should have(1).errors
74
+ runner.errors[0].to_s.should == "app/models/project.rb:6 - use observer"
73
75
  end
74
76
 
75
77
  it "should not raise when initiate an object in callback" do
@@ -78,7 +80,7 @@ describe RailsBestPractices::Checks::UseObserverCheck do
78
80
  after_create ProjectMailer.new
79
81
  end
80
82
  EOF
81
- lambda { @runner.review('app/models/project.rb', content) }.should_not raise_error
83
+ lambda { runner.review('app/models/project.rb', content) }.should_not raise_error
82
84
  end
83
85
  end
84
86
 
@@ -97,10 +99,9 @@ describe RailsBestPractices::Checks::UseObserverCheck do
97
99
  end
98
100
  end
99
101
  EOF
100
- @runner.review('app/models/project.rb', content)
101
- errors = @runner.errors
102
- errors.should_not be_empty
103
- errors[0].to_s.should == "app/models/project.rb:6 - use observer"
102
+ runner.review('app/models/project.rb', content)
103
+ runner.should have(1).errors
104
+ runner.errors[0].to_s.should == "app/models/project.rb:6 - use observer"
104
105
  end
105
106
 
106
107
  it "should not use observer without callback" do
@@ -115,9 +116,8 @@ describe RailsBestPractices::Checks::UseObserverCheck do
115
116
  end
116
117
  end
117
118
  EOF
118
- @runner.review('app/models/project.rb', content)
119
- errors = @runner.errors
120
- errors.should be_empty
119
+ runner.review('app/models/project.rb', content)
120
+ runner.should have(0).errors
121
121
  end
122
122
 
123
123
  it "should use observer with two after_create" do
@@ -137,10 +137,9 @@ describe RailsBestPractices::Checks::UseObserverCheck do
137
137
  end
138
138
  end
139
139
  EOF
140
- @runner.review('app/models/project.rb', content)
141
- errors = @runner.errors
142
- errors.should_not be_empty
143
- errors[0].to_s.should == "app/models/project.rb:6 - use observer"
140
+ runner.review('app/models/project.rb', content)
141
+ runner.should have(1).errors
142
+ runner.errors[0].to_s.should == "app/models/project.rb:6 - use observer"
144
143
  end
145
144
 
146
145
  it "should not raise when initiate an object in callback" do
@@ -149,7 +148,7 @@ describe RailsBestPractices::Checks::UseObserverCheck do
149
148
  after_create ProjectMailer.new
150
149
  end
151
150
  EOF
152
- lambda { @runner.review('app/models/project.rb', content) }.should_not raise_error
151
+ lambda { runner.review('app/models/project.rb', content) }.should_not raise_error
153
152
  end
154
153
  end
155
154
  end
@@ -0,0 +1,190 @@
1
+ require 'spec_helper'
2
+
3
+ describe RailsBestPractices::Reviews::UseQueryAttributeReview do
4
+ let(:runner) {
5
+ RailsBestPractices::Core::Runner.new(
6
+ :prepares => RailsBestPractices::Prepares::ModelPrepare.new,
7
+ :reviews => RailsBestPractices::Reviews::UseQueryAttributeReview.new
8
+ )
9
+ }
10
+
11
+ before :each do
12
+ content = <<-EOF
13
+ class User < ActiveRecord::Base
14
+ has_many :projects
15
+ belongs_to :location
16
+ has_one :phone
17
+
18
+ belongs_to :category, :class_name => 'IssueCategory', :foreign_key => 'category_id'
19
+ end
20
+ EOF
21
+ runner.prepare('app/models/user.rb', content)
22
+ end
23
+
24
+ it "should use query attribute by blank call" do
25
+ content = <<-EOF
26
+ <% if @user.login.blank? %>
27
+ <%= link_to 'login', new_session_path %>
28
+ <% end %>
29
+ EOF
30
+ runner.review('app/views/users/show.html.erb', content)
31
+ runner.should have(1).errors
32
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
33
+ end
34
+
35
+ it "should use query attribute by comparing empty string" do
36
+ content = <<-EOF
37
+ <% if @user.login == "" %>
38
+ <%= link_to 'login', new_session_path %>
39
+ <% end %>
40
+ EOF
41
+ runner.review('app/views/users/show.html.erb', content)
42
+ runner.should have(1).errors
43
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
44
+ end
45
+
46
+ it "should use query attribute by nil call" do
47
+ content = <<-EOF
48
+ <% if @user.login.nil? %>
49
+ <%= link_to 'login', new_session_path %>
50
+ <% end %>
51
+ EOF
52
+ runner.review('app/views/users/show.html.erb', content)
53
+ runner.should have(1).errors
54
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
55
+ end
56
+
57
+ it "should use query attribute by present call" do
58
+ content = <<-EOF
59
+ <% if @user.login.present? %>
60
+ <%= @user.login %>
61
+ <% end %>
62
+ EOF
63
+ runner.review('app/views/users/show.html.erb', content)
64
+ runner.should have(1).errors
65
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
66
+ end
67
+
68
+ it "should use query attribute within and conditions" do
69
+ content = <<-EOF
70
+ <% if @user.active? and @user.login.present? %>
71
+ <%= @user.login %>
72
+ <% end %>
73
+ EOF
74
+ runner.review('app/views/users/show.html.erb', content)
75
+ runner.should have(1).errors
76
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
77
+ end
78
+
79
+ it "should use query attribute within or conditions" do
80
+ content = <<-EOF
81
+ <% if @user.active? or @user.login != "" %>
82
+ <%= @user.login %>
83
+ <% end %>
84
+ EOF
85
+ runner.review('app/views/users/show.html.erb', content)
86
+ runner.should have(1).errors
87
+ runner.errors[0].to_s.should == "app/views/users/show.html.erb:1 - use query attribute (@user.login?)"
88
+ end
89
+
90
+ it "should not use query attribute" do
91
+ content = <<-EOF
92
+ <% if @user.login? %>
93
+ <%= @user.login %>
94
+ <% end %>
95
+ EOF
96
+ runner.review('app/views/users/show.html.erb', content)
97
+ runner.should have(0).errors
98
+ end
99
+
100
+ it "should not review for pluralize attribute" do
101
+ content = <<-EOF
102
+ <% if @user.roles.blank? %>
103
+ <%= @user.login %>
104
+ <% end %>
105
+ EOF
106
+ runner.review('app/views/users/show.html.erb', content)
107
+ runner.should have(0).errors
108
+ end
109
+
110
+ it "should not review non model class" do
111
+ content = <<-EOF
112
+ <% if @person.login.present? %>
113
+ <%= @person.login %>
114
+ <% end %>
115
+ EOF
116
+ runner.review('app/views/users/show.html.erb', content)
117
+ runner.should have(0).errors
118
+ end
119
+
120
+ context "association" do
121
+ it "should not review belongs_to association" do
122
+ content = <<-EOF
123
+ <% if @user.location.present? %>
124
+ <%= @user.location.name %>
125
+ <% end %>
126
+ EOF
127
+ runner.review('app/views/users/show.html.erb', content)
128
+ runner.should have(0).errors
129
+ end
130
+
131
+ it "should not review belongs_to category" do
132
+ content = <<-EOF
133
+ <% if @user.category.present? %>
134
+ <%= @user.category.name %>
135
+ <% end %>
136
+ EOF
137
+ runner.review('app/views/users/show.html.erb', content)
138
+ runner.should have(0).errors
139
+ end
140
+
141
+ it "should not review has_one association" do
142
+ content = <<-EOF
143
+ <% if @user.phone.present? %>
144
+ <%= @user.phone.number %>
145
+ <% end %>
146
+ EOF
147
+ runner.review('app/views/users/show.html.erb', content)
148
+ runner.should have(0).errors
149
+ end
150
+
151
+ it "should not review has_many association" do
152
+ content = <<-EOF
153
+ <% if @user.projects.present? %>
154
+ <%= @user.projects.first.name %>
155
+ <% end %>
156
+ EOF
157
+ runner.review('app/views/users/show.html.erb', content)
158
+ runner.should have(0).errors
159
+ end
160
+ end
161
+
162
+ it "should not review for class method" do
163
+ content = <<-EOF
164
+ <% if User.name.present? %>
165
+ <%= User.name %>
166
+ <% end %>
167
+ EOF
168
+ runner.review('app/views/users/show.html.erb', content)
169
+ runner.should have(0).errors
170
+ end
171
+
172
+ it "should not review for non attribute call" do
173
+ content = <<-EOF
174
+ if @user.login(false).nil?
175
+ puts @user.login(false)
176
+ end
177
+ EOF
178
+ runner.review('app/models/users_controller.rb', content)
179
+ runner.should have(0).errors
180
+ end
181
+
182
+ it "should not raise error for common conditional statement" do
183
+ content = <<-EOF
184
+ if voteable.is_a? Answer
185
+ puts voteable.title
186
+ end
187
+ EOF
188
+ lambda { runner.review('app/models/users_controller.rb', content) }.should_not raise_error
189
+ end
190
+ end