Add support for counter_cache option in belongs_to associations

This commit is contained in:
Fabio Rehm 2013-06-19 20:52:46 -03:00 committed by Melissa Xie
parent 1b5e3abdf9
commit 3f7c440851
5 changed files with 63 additions and 0 deletions

View File

@ -1,5 +1,7 @@
# HEAD # HEAD
* Add a `counter_cache` submatcher for `belongs_to` associations
* Add a rescue_from matcher for Rails controllers which checks that the correct * Add a rescue_from matcher for Rails controllers which checks that the correct
ActiveSupport call has been made and that the handlers exist without actually ActiveSupport call has been made and that the handlers exist without actually
throwing an exception. throwing an exception.

View File

@ -1,4 +1,5 @@
require 'shoulda/matchers/active_record/association_matcher' require 'shoulda/matchers/active_record/association_matcher'
require 'shoulda/matchers/active_record/association_matchers/counter_cache_matcher'
require 'shoulda/matchers/active_record/association_matchers/order_matcher' require 'shoulda/matchers/active_record/association_matchers/order_matcher'
require 'shoulda/matchers/active_record/association_matchers/through_matcher' require 'shoulda/matchers/active_record/association_matchers/through_matcher'
require 'shoulda/matchers/active_record/association_matchers/dependent_matcher' require 'shoulda/matchers/active_record/association_matchers/dependent_matcher'

View File

@ -98,6 +98,12 @@ module Shoulda # :nodoc:
self self
end end
def counter_cache(counter_cache = true)
counter_cache_matcher = AssociationMatchers::CounterCacheMatcher.new(counter_cache, name)
add_submatcher(counter_cache_matcher)
self
end
def conditions(conditions) def conditions(conditions)
@options[:conditions] = conditions @options[:conditions] = conditions
self self

View File

@ -0,0 +1,35 @@
module Shoulda # :nodoc:
module Matchers
module ActiveRecord # :nodoc:
module AssociationMatchers
class CounterCacheMatcher
attr_accessor :missing_option
def initialize(counter_cache, name)
@counter_cache = counter_cache
@name = name
@missing_option = ''
end
def description
"counter_cache => #{counter_cache}"
end
def matches?(subject)
subject = ModelReflector.new(subject, name)
if subject.option_set_properly?(counter_cache, :counter_cache)
true
else
self.missing_option = "#{name} should have #{description}"
false
end
end
private
attr_accessor :counter_cache, :name
end
end
end
end
end

View File

@ -46,6 +46,25 @@ describe Shoulda::Matchers::ActiveRecord::AssociationMatcher do
belonging_to_parent.should_not belong_to(:parent).dependent(:destroy) belonging_to_parent.should_not belong_to(:parent).dependent(:destroy)
end end
it 'accepts an association with a valid :counter_cache option' do
belonging_to_parent(:counter_cache => :attribute_count).
should belong_to(:parent).counter_cache(:attribute_count)
end
it 'defaults :counter_cache to true' do
belonging_to_parent(:counter_cache => true).
should belong_to(:parent).counter_cache
end
it 'rejects an association with a bad :counter_cache option' do
belonging_to_parent(:counter_cache => :attribute_count).
should_not belong_to(:parent).counter_cache(true)
end
it 'rejects an association that has no :counter_cache option' do
belonging_to_parent.should_not belong_to(:parent).counter_cache
end
it 'accepts an association with a valid :conditions option' do it 'accepts an association with a valid :conditions option' do
define_model :parent, :adopter => :boolean define_model :parent, :adopter => :boolean
define_model :child, :parent_id => :integer do define_model :child, :parent_id => :integer do