PageRenderTime 42ms CodeModel.GetById 24ms app.highlight 15ms RepoModel.GetById 1ms app.codeStats 0ms

/spec/rails_best_practices/reviews/law_of_demeter_review_spec.rb

http://github.com/flyerhzm/rails_best_practices
Ruby | 186 lines | 168 code | 17 blank | 1 comment | 0 complexity | d9ae9668ee0fd5c453a94b9e12ec225b MD5 | raw file
  1# frozen_string_literal: true
  2
  3require 'spec_helper'
  4
  5module RailsBestPractices
  6  module Reviews
  7    describe LawOfDemeterReview do
  8      let(:runner) do
  9        Core::Runner.new(
 10          prepares: [Prepares::ModelPrepare.new, Prepares::SchemaPrepare.new], reviews: described_class.new
 11        )
 12      end
 13
 14      describe 'belongs_to' do
 15        before do
 16          content = <<-EOF
 17          class Invoice < ActiveRecord::Base
 18            belongs_to :user
 19          end
 20          EOF
 21          runner.prepare('app/models/invoice.rb', content)
 22
 23          content = <<-EOF
 24          ActiveRecord::Schema.define(version: 20110216150853) do
 25            create_table "users", force => true do |t|
 26              t.string :name
 27              t.string :address
 28              t.string :cellphone
 29            end
 30          end
 31          EOF
 32          runner.prepare('db/schema.rb', content)
 33        end
 34
 35        it 'laws of demeter with erb' do
 36          content = <<-EOF
 37          <%= @invoice.user.name %>
 38          <%= @invoice.user.address %>
 39          <%= @invoice.user.cellphone %>
 40          EOF
 41          runner.review('app/views/invoices/show.html.erb', content)
 42          expect(runner.errors.size).to eq(3)
 43          expect(runner.errors[0].to_s).to eq('app/views/invoices/show.html.erb:1 - law of demeter')
 44        end
 45
 46        it 'laws of demeter with haml' do
 47          content = <<~EOF
 48            = @invoice.user.name
 49            = @invoice.user.address
 50            = @invoice.user.cellphone
 51          EOF
 52          runner.review('app/views/invoices/show.html.haml', content)
 53          expect(runner.errors.size).to eq(3)
 54          expect(runner.errors[0].to_s).to eq('app/views/invoices/show.html.haml:1 - law of demeter')
 55        end
 56
 57        it 'laws of demeter with slim' do
 58          content = <<~EOF
 59            = @invoice.user.name
 60            = @invoice.user.address
 61            = @invoice.user.cellphone
 62          EOF
 63          runner.review('app/views/invoices/show.html.slim', content)
 64          expect(runner.errors.size).to eq(3)
 65          expect(runner.errors[0].to_s).to eq('app/views/invoices/show.html.slim:1 - law of demeter')
 66        end
 67
 68        it 'noes law of demeter' do
 69          content = <<-EOF
 70          <%= @invoice.user_name %>
 71          <%= @invoice.user_address %>
 72          <%= @invoice.user_cellphone %>
 73          EOF
 74          runner.review('app/views/invoices/show.html.erb', content)
 75          expect(runner.errors.size).to eq(0)
 76        end
 77      end
 78
 79      describe 'has_one' do
 80        before do
 81          content = <<-EOF
 82          class Invoice < ActiveRecord::Base
 83            has_one :price
 84          end
 85          EOF
 86          runner.prepare('app/models/invoice.rb', content)
 87
 88          content = <<-EOF
 89          ActiveRecord::Schema.define(version: 20110216150853) do
 90            create_table "prices", force => true do |t|
 91              t.string :currency
 92              t.integer :number
 93            end
 94          end
 95          EOF
 96          runner.prepare('db/schema.rb', content)
 97        end
 98
 99        it 'laws of demeter' do
100          content = <<-EOF
101          <%= @invoice.price.currency %>
102          <%= @invoice.price.number %>
103          EOF
104          runner.review('app/views/invoices/show.html.erb', content)
105          expect(runner.errors.size).to eq(2)
106          expect(runner.errors[0].to_s).to eq('app/views/invoices/show.html.erb:1 - law of demeter')
107        end
108      end
109
110      context 'polymorphic association' do
111        before do
112          content = <<-EOF
113          class Comment < ActiveRecord::Base
114            belongs_to :commentable, polymorphic: true
115          end
116          EOF
117          runner.prepare('app/models/comment.rb', content)
118
119          content = <<-EOF
120          class Post < ActiveRecord::Base
121            has_many :comments
122          end
123          EOF
124          runner.prepare('app/models/comment.rb', content)
125
126          content = <<-EOF
127          ActiveRecord::Schema.define(version: 20110216150853) do
128            create_table "posts", force => true do |t|
129              t.string :title
130            end
131          end
132          EOF
133          runner.prepare('db/schema.rb', content)
134        end
135
136        it 'laws of demeter' do
137          content = <<-EOF
138          <%= @comment.commentable.title %>
139          EOF
140          runner.review('app/views/comments/index.html.erb', content)
141          expect(runner.errors.size).to eq(1)
142          expect(runner.errors[0].to_s).to eq('app/views/comments/index.html.erb:1 - law of demeter')
143        end
144      end
145
146      it 'noes law of demeter with method call' do
147        content = <<-EOF
148        class Question < ActiveRecord::Base
149          has_many :answers, dependent: :destroy
150        end
151        EOF
152        runner.prepare('app/models/question.rb', content)
153        content = <<-EOF
154        class Answer < ActiveRecord::Base
155          belongs_to :question, counter_cache: true, touch: true
156        end
157        EOF
158        runner.prepare('app/models/answer.rb', content)
159        content = <<-EOF
160        class CommentsController < ApplicationController
161          def comment_url
162            question_path(@answer.question)
163          end
164        end
165        EOF
166        runner.review('app/controllers/comments_controller.rb', content)
167        expect(runner.errors.size).to eq(0)
168      end
169
170      it 'does not check ignored files' do
171        runner =
172          Core::Runner.new(
173            prepares: [Prepares::ModelPrepare.new, Prepares::SchemaPrepare.new],
174            reviews: described_class.new(ignored_files: %r{app/views/invoices})
175          )
176        content = <<-EOF
177          <%= @invoice.user.name %>
178          <%= @invoice.user.address %>
179          <%= @invoice.user.cellphone %>
180        EOF
181        runner.review('app/views/invoices/show.html.erb', content)
182        expect(runner.errors.size).to eq(0)
183      end
184    end
185  end
186end