]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
- Anonymous labeling is applied to a :attr:`.func` construct that is
authorMike Bayer <mike_mp@zzzcomputing.com>
Fri, 26 Feb 2016 05:20:39 +0000 (00:20 -0500)
committerMike Bayer <mike_mp@zzzcomputing.com>
Fri, 26 Feb 2016 05:20:39 +0000 (00:20 -0500)
passed to :func:`.column_property`, so that if the same attribute
is referred to as a column expression twice the names are de-duped,
thus avoiding "ambiguous column" errors.   Previously, the
``.label(None)`` would need to be applied in order for the name
to be de-anonymized.
fixes #3663

doc/build/changelog/changelog_10.rst
lib/sqlalchemy/sql/elements.py
test/orm/test_query.py

index 36152c2360cc882dd8a3fbc85109dc01c603908f..209f13bdc9383ebf1c2aef198f19baba41c59eaf 100644 (file)
 .. changelog::
     :version: 1.0.13
 
+    .. change::
+        :tags: bug, orm
+        :tickets: 3663
+
+        Anonymous labeling is applied to a :attr:`.func` construct that is
+        passed to :func:`.column_property`, so that if the same attribute
+        is referred to as a column expression twice the names are de-duped,
+        thus avoiding "ambiguous column" errors.   Previously, the
+        ``.label(None)`` would need to be applied in order for the name
+        to be de-anonymized.
+
     .. change::
         :tags: bug, py3k
         :tickets: 3660
index ca822d3104827120176d374cc1e35a16169685c4..67a442b0c2aa0bfb4f576013c4429d2143df2d59 100644 (file)
@@ -4006,7 +4006,7 @@ def _cloned_difference(a, b):
 
 
 def _labeled(element):
-    if not hasattr(element, 'name'):
+    if not hasattr(element, 'name') or not getattr(element, '_label', None):
         return element.label(None)
     else:
         return element
index c4c62c319a33f5a1f9ba77c3ce7c48b51a9ed763..cdc4ac2c2feefc5be8e0856e7066968f9d490d03 100644 (file)
@@ -484,7 +484,7 @@ class RawSelectTest(QueryTest, AssertsCompiledSQL):
         self.assert_compile(
             select([Foo]).where(Foo.foob == 'somename').order_by(Foo.foob),
             "SELECT users.id, users.name FROM users "
-            "WHERE coalesce(users.name) = :coalesce_1 "
+            "WHERE coalesce(users.name) = :param_1 "
             "ORDER BY coalesce(users.name)"
         )
 
@@ -1593,6 +1593,63 @@ class ColumnPropertyTest(_fixtures.FixtureTest, AssertsCompiledSQL):
         }, with_polymorphic="*" if polymorphic else None)
         mapper(Address, addresses)
 
+    def _func_fixture(self, label=False):
+        User = self.classes.User
+        users = self.tables.users
+
+        if label:
+            mapper(User, users, properties={
+                "foobar": column_property(
+                    func.foob(users.c.name).label(None)
+                )
+            })
+        else:
+            mapper(User, users, properties={
+                "foobar": column_property(
+                    func.foob(users.c.name)
+                )
+            })
+
+    def test_anon_label_function_auto(self):
+        self._func_fixture()
+        User = self.classes.User
+
+        s = Session()
+
+        u1 = aliased(User)
+        self.assert_compile(
+            s.query(User.foobar, u1.foobar),
+            "SELECT foob(users.name) AS foob_1, foob(users_1.name) AS foob_2 "
+            "FROM users, users AS users_1"
+        )
+
+    def test_anon_label_function_manual(self):
+        self._func_fixture(label=True)
+        User = self.classes.User
+
+        s = Session()
+
+        u1 = aliased(User)
+        self.assert_compile(
+            s.query(User.foobar, u1.foobar),
+            "SELECT foob(users.name) AS foob_1, foob(users_1.name) AS foob_2 "
+            "FROM users, users AS users_1"
+        )
+
+    def test_anon_label_ad_hoc_labeling(self):
+        self._func_fixture()
+        User = self.classes.User
+
+        s = Session()
+
+        u1 = aliased(User)
+        self.assert_compile(
+            s.query(User.foobar.label('x'), u1.foobar.label('y')),
+            "SELECT foob(users.name) AS x, foob(users_1.name) AS y "
+            "FROM users, users AS users_1"
+        )
+
+
     def test_order_by_column_prop_string(self):
         User, Address = self.classes("User", "Address")
         self._fixture(label=True)