Permalink
Browse files

Allow a predicate from ComparableKeyPathExpression to be negated.

  • Loading branch information...
1 parent a537489 commit b31da1aa0ed3d4233e54a7b59bce1ddb897c8db5 @alloy committed Aug 11, 2012
Showing with 24 additions and 40 deletions.
  1. +10 −6 app/predicate.rb
  2. +14 −34 spec/predicate_spec.rb
View
@@ -26,13 +26,16 @@ def value(keyPath)
end
end
- attr_reader :expression, :comparisonOptions
+ attr_reader :expression, :comparisonOptions, :negate
def initialize(keyPath)
@expression = NSExpression.expressionForKeyPath(keyPath.to_s)
@comparisonOptions = 0
+ @negate = false
end
+ def not; @negate = true; self; end
+
def caseInsensitive; @comparisonOptions |= NSCaseInsensitivePredicateOption; self; end
def diacriticInsensitive; @comparisonOptions |= NSDiacriticInsensitivePredicateOption; self; end
def localeSensitive; @comparisonOptions |= NSLocaleSensitivePredicateOption; self; end
@@ -53,11 +56,12 @@ def endsWith?(string); comparisonWith(string, type:NSEndsWithPredicateOper
private
def comparisonWith(value, type:comparisonType)
- NSComparisonPredicate.predicateWithLeftExpression(@expression,
- rightExpression:NSExpression.expressionForConstantValue(value),
- modifier:NSDirectPredicateModifier,
- type:comparisonType,
- options:@comparisonOptions)
+ predicate = NSComparisonPredicate.predicateWithLeftExpression(@expression,
+ rightExpression:NSExpression.expressionForConstantValue(value),
+ modifier:NSDirectPredicateModifier,
+ type:comparisonType,
+ options:@comparisonOptions)
+ @negate ? NSCompoundPredicate.notPredicateWithSubpredicate(predicate) : predicate
end
end
end
@@ -1,11 +1,11 @@
module MotionData
- describe ComparablevaluePathExpression do
- extend ComparablevaluePathExpression::Mixin
+ describe ComparableKeyPathExpression do
+ extend ComparableKeyPathExpression::Mixin
it "returns a expression for the left-hand side of a comparison" do
- value(:property).expression.valuePath.should == 'property'
- valuePath('property.subproperty').expression.valuePath.should == 'property.subproperty'
+ value(:property).expression.keyPath.should == 'property'
+ value('property.subproperty').expression.keyPath.should == 'property.subproperty'
end
it "returns comparison predicates" do
@@ -16,39 +16,19 @@ module MotionData
(value(:amount) >= 42) => 'amount >= 42',
(value(:amount) != 42) => 'amount != 42',
(value(:amount) == 42) => 'amount == 42',
+
+ value(:amount).between?(21, 42) => 'amount BETWEEN {21, 42}',
+ value(:amount).in?([21, 42]) => 'amount IN {21, 42}',
+ value(:amount).include?(42) => 'amount CONTAINS 42',
+ value(:name).beginsWith?('bob') => 'name BEGINSWITH "bob"',
+ value(:name).endsWith?('bob') => 'name ENDSWITH "bob"',
}.each do |predicate, format|
predicate.predicateFormat.should == format
end
end
- it "returns a `between` predicate" do
- predicate = value(:amount).between?(21, 42)
- predicate.predicateFormat.should == 'amount BETWEEN {21, 42}'
- end
-
- it "returns a `in` predicate" do
- predicate = value(:amount).in?([21, 42])
- predicate.predicateFormat.should == 'amount IN {21, 42}'
- end
-
- it "returns a `contains` predicate" do
- predicate = value(:amount).include?(42)
- predicate.predicateFormat.should == 'amount CONTAINS 42'
- end
-
- it "returns a `in collection` predicate" do
- predicate = value(:amount).in?([21, 42])
- predicate.predicateFormat.should == 'amount IN {21, 42}'
- end
-
- it "returns a `begin's with` predicate" do
- predicate = value(:name).beginsWith?('bob')
- predicate.predicateFormat.should == 'name BEGINSWITH "bob"'
- end
-
- it "returns a `end's with` predicate" do
- predicate = value(:name).endsWith?('bob')
- predicate.predicateFormat.should == 'name ENDSWITH "bob"'
+ it "negates the comparison predicate" do
+ value(:name).not.beginsWith?('bob').predicateFormat.should == 'NOT name BEGINSWITH "bob"'
end
it "by default returns that no comparison options should be used" do
@@ -86,8 +66,8 @@ module MotionData
end
end
- describe Predicate do
- extend ComparablevaluePathExpression::Mixin
+ describe NSPredicate do
+ extend ComparableKeyPathExpression::Mixin
it "returns a compound `AND` predicate" do
predicate = ( value(:amount) < 42 ).and( value(:amount) > 42 ).and( value(:amount) != 21 )

0 comments on commit b31da1a

Please sign in to comment.