Browse files

Add in_array to ensure_exclusion_of

  • Loading branch information...
1 parent 41c763d commit 8a477a92bd62aa8d4dad24b19247c5932709c481 @grk grk committed with drapergeek Aug 19, 2012
View
34 lib/shoulda/matchers/active_model/ensure_exclusion_of_matcher.rb
@@ -5,6 +5,7 @@ module ActiveModel # :nodoc:
# Ensure that the attribute's value is not in the range specified
#
# Options:
+ # * <tt>in_array</tt> - the array of not allowed values for this attribute
# * <tt>in_range</tt> - the range of not allowed values for this attribute
# * <tt>with_message</tt> - value the test expects to find in
# <tt>errors.on(:attribute)</tt>. Regexp or string. Defaults to the
@@ -18,6 +19,10 @@ def ensure_exclusion_of(attr)
end
class EnsureExclusionOfMatcher < ValidationMatcher # :nodoc:
+ def in_array(array)
+ @array = array
+ self
+ end
def in_range(range)
@range = range
@@ -32,20 +37,30 @@ def with_message(message)
end
def description
- "ensure exclusion of #{@attribute} in #{@range.inspect}"
+ "ensure exclusion of #{@attribute} in #{inspect_message}"
end
def matches?(subject)
super(subject)
- allows_lower_value &&
- disallows_minimum_value &&
- allows_higher_value &&
- disallows_maximum_value
+ if @range
+ allows_lower_value &&
+ disallows_minimum_value &&
+ allows_higher_value &&
+ disallows_maximum_value
+ elsif @array
+ disallows_all_values_in_array?
+ end
end
private
+ def disallows_all_values_in_array?
+ @array.all? do |value|
+ disallows_value_of(value, expected_message)
+ end
+ end
+
def allows_lower_value
@minimum == 0 || allows_value_of(@minimum - 1, expected_message)
end
@@ -65,8 +80,15 @@ def disallows_maximum_value
def expected_message
@expected_message || :exclusion
end
- end
+ def inspect_message
+ if @range
+ @range.inspect
+ else
+ @array.inspect
+ end
+ end
+ end
end
end
end
View
2 lib/shoulda/matchers/active_model/ensure_inclusion_of_matcher.rb
@@ -5,7 +5,7 @@ module ActiveModel # :nodoc:
# Ensure that the attribute's value is in the range specified
#
# Options:
- # * <tt>in_array</tt> - the range of allowed values for this attribute
+ # * <tt>in_array</tt> - the array of allowed values for this attribute
# * <tt>in_range</tt> - the range of allowed values for this attribute
# * <tt>with_low_message</tt> - value the test expects to find in
# <tt>errors.on(:attribute)</tt>. Regexp or string. Defaults to the
View
24 spec/shoulda/active_model/ensure_exclusion_of_matcher_spec.rb
@@ -51,7 +51,29 @@ def custom_validation
it "should accept ensuring the correct range and messages" do
@model.should ensure_exclusion_of(:attr).in_range(2..5).with_message(/shoud be out of this range/)
end
-
end
+ context "an attribute which must be excluded in an array" do
+ before do
+ @model = define_model(:example, :attr => :string) do
+ validates_exclusion_of :attr, :in => %w(one two)
+ end.new
+ end
+
+ it "accepts with correct array" do
+ @model.should ensure_exclusion_of(:attr).in_array(%w(one two))
+ end
+
+ it "rejects when only part of array matches" do
+ @model.should_not ensure_exclusion_of(:attr).in_array(%w(one wrong_value))
+ end
+
+ it "rejects when array doesn't match at all" do
+ @model.should_not ensure_exclusion_of(:attr).in_array(%w(cat dog))
+ end
+
+ it "has correct description" do
+ ensure_exclusion_of(:attr).in_array([true, 'dog']).description.should == 'ensure exclusion of attr in [true, "dog"]'
+ end
+ end
end

0 comments on commit 8a477a9

Please sign in to comment.