summaryrefslogtreecommitdiff
path: root/lib/sqlalchemy/ext
diff options
context:
space:
mode:
authorMike Bayer <mike_mp@zzzcomputing.com>2018-02-25 19:54:37 -0500
committerMike Bayer <mike_mp@zzzcomputing.com>2018-05-16 15:54:41 -0400
commit21d8a82c7b0dc450a14957fa34b81250119ad6a7 (patch)
tree443b5f066eed43443b8b6a1e4aa48404ccb08d73 /lib/sqlalchemy/ext
parentb2c4333d5b158f73bb3afaf979e0e379f828b3b5 (diff)
downloadsqlalchemy-21d8a82c7b0dc450a14957fa34b81250119ad6a7.tar.gz
Merge existing query params in baked lazy load
Corrected backport, was supposed to be in 1.2.5 however never got backported. Fixed a long-standing regression that occurred in version 1.0, which prevented the use of a custom :class:`.MapperOption` that alters the _params of a :class:`.Query` object for a lazy load, since the lazy loader itself would overwrite those parameters. This applies to the "temporal range" example on the wiki. Note however that the :meth:`.Query.populate_existing` method is now required in order to rewrite the mapper options associated with an object already loaded in the identity map. As part of this change, a custom defined :class:`.MapperOption` will now cause lazy loaders related to the target object to use a non-baked query by default unless the :meth:`.MapperOption._generate_cache_key` method is implemented. In particular, this repairs one regression which occured when using the dogpile.cache "advanced" example, which was not returning cached results and instead emitting SQL due to an incompatibility with the baked query loader; with the change, the ``RelationshipCache`` option included for many releases in the dogpile example will disable the "baked" query altogether. Note that the dogpile example is also modernized to avoid both of these issues as part of issue :ticket:`4258`. This is a cherry-pick / squash from: 4a31c30fa5ebd6af0e72937b21b2e5ee79e12631 2e46f73f35b9036287f5f567c09a8cb786fe5fd3 b9f428a589a1718efa20e5555be45ae3f767e89e Change-Id: I899808734458e25a023142c2c5bb37cbed869479 Fixes: #4128
Diffstat (limited to 'lib/sqlalchemy/ext')
-rw-r--r--lib/sqlalchemy/ext/baked.py11
1 files changed, 8 insertions, 3 deletions
diff --git a/lib/sqlalchemy/ext/baked.py b/lib/sqlalchemy/ext/baked.py
index 13ad4cf7c..f4d71f410 100644
--- a/lib/sqlalchemy/ext/baked.py
+++ b/lib/sqlalchemy/ext/baked.py
@@ -240,7 +240,8 @@ class BakedQuery(object):
baked_queries.append((k, bk._cache_key, v))
del context.attributes[k]
- def _unbake_subquery_loaders(self, session, context, params):
+ def _unbake_subquery_loaders(
+ self, session, context, params, post_criteria):
"""Retrieve subquery eager loaders stored by _bake_subquery_loaders
and turn them back into Result objects that will iterate just
like a Query object.
@@ -250,7 +251,10 @@ class BakedQuery(object):
bk = BakedQuery(self._bakery,
lambda sess, q=query: q.with_session(sess))
bk._cache_key = cache_key
- context.attributes[k] = bk.for_session(session).params(**params)
+ q = bk.for_session(session)
+ for fn in post_criteria:
+ q = fn(q)
+ context.attributes[k] = q.params(**params)
class Result(object):
@@ -329,7 +333,8 @@ class Result(object):
context.session = self.session
context.attributes = context.attributes.copy()
- bq._unbake_subquery_loaders(self.session, context, self._params)
+ bq._unbake_subquery_loaders(
+ self.session, context, self._params, self._post_criteria)
context.statement.use_labels = True
if context.autoflush and not context.populate_existing: