]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
- [bug] Fixed bug in relationship comparisons
authorMike Bayer <mike_mp@zzzcomputing.com>
Thu, 26 Apr 2012 15:58:54 +0000 (11:58 -0400)
committerMike Bayer <mike_mp@zzzcomputing.com>
Thu, 26 Apr 2012 15:58:54 +0000 (11:58 -0400)
whereby calling unimplemented methods like
SomeClass.somerelationship.like() would
produce a recursion overflow, instead
of NotImplementedError.

CHANGES
lib/sqlalchemy/orm/properties.py
lib/sqlalchemy/sql/operators.py
test/orm/test_query.py

diff --git a/CHANGES b/CHANGES
index 7dc9e8300fdc45d417c798113b7633a0d8ca344d..354120a42098a7804b14247184925c742b1298e2 100644 (file)
--- a/CHANGES
+++ b/CHANGES
@@ -41,6 +41,12 @@ CHANGES
     OrderingList from being pickleable
     [ticket:2454].  Courtesy Jeff Dairiki
 
+  - [bug] Fixed bug in relationship comparisons
+    whereby calling unimplemented methods like
+    SomeClass.somerelationship.like() would
+    produce a recursion overflow, instead
+    of NotImplementedError.
+
 - sql
   - [bug] Removed warning when Index is created
     with no columns; while this might not be what 
index 74ccf0157f3d37ad906bb379c27fe1ad94c31f98..f2186df511aeeed7ac67d08278c3d416a020b0b6 100644 (file)
@@ -323,12 +323,6 @@ class RelationshipProperty(StrategizedProperty):
             else:
                 return elem
 
-        def operate(self, op, *other, **kwargs):
-            return op(self, *other, **kwargs)
-
-        def reverse_operate(self, op, other, **kwargs):
-            return op(self, *other, **kwargs)
-
         def of_type(self, cls):
             """Produce a construct that represents a particular 'subtype' of
             attribute for the parent class.
index 89f0aaee13e753d7faf5a3986d9a008508ec9b77..3fcbf7cf97ccda997b3f358fb43a5ef5803517d7 100644 (file)
@@ -469,13 +469,13 @@ def like_op(a, b, escape=None):
     return a.like(b, escape=escape)
 
 def notlike_op(a, b, escape=None):
-    raise NotImplementedError()
+    return ~a.like(b, escape=escape)
 
 def ilike_op(a, b, escape=None):
     return a.ilike(b, escape=escape)
 
 def notilike_op(a, b, escape=None):
-    raise NotImplementedError()
+    return ~a.ilike(b, escape=escape)
 
 def between_op(a, b, c):
     return a.between(b, c)
@@ -484,7 +484,7 @@ def in_op(a, b):
     return a.in_(b)
 
 def notin_op(a, b):
-    raise NotImplementedError()
+    return ~a.in_(b)
 
 def distinct_op(a):
     return a.distinct()
index bcc97681657382a55836512bc1b3a0ef153148b3..3f1035599dd1d81f400225f795dd22e052721cf0 100644 (file)
@@ -603,6 +603,16 @@ class OperatorTest(QueryTest, AssertsCompiledSQL):
         self._test(None == Address.user, "addresses.user_id IS NULL")
         self._test(~(None == Address.user), "addresses.user_id IS NOT NULL")
 
+    def test_relationship_unimplemented(self):
+        User, Address = self.classes.User, self.classes.Address
+        for op in [
+            User.addresses.like,
+            User.addresses.ilike,
+            User.addresses.__le__,
+            User.addresses.__gt__,
+        ]:
+            assert_raises(NotImplementedError, op, "x")
+
     def test_relationship(self):
         User, Address = self.classes.User, self.classes.Address