diff options
Diffstat (limited to 'lib/sqlalchemy')
-rw-r--r-- | lib/sqlalchemy/orm/properties.py | 23 | ||||
-rw-r--r-- | lib/sqlalchemy/orm/util.py | 2 | ||||
-rw-r--r-- | lib/sqlalchemy/sql/expression.py | 14 |
3 files changed, 31 insertions, 8 deletions
diff --git a/lib/sqlalchemy/orm/properties.py b/lib/sqlalchemy/orm/properties.py index f8288f5fb..048b4fad3 100644 --- a/lib/sqlalchemy/orm/properties.py +++ b/lib/sqlalchemy/orm/properties.py @@ -350,6 +350,8 @@ class RelationshipProperty(StrategizedProperty): """ + _of_type = None + def __init__(self, prop, mapper, of_type=None, adapter=None): """Construction of :class:`.RelationshipProperty.Comparator` is internal to the ORM's attribute mechanics. @@ -376,13 +378,30 @@ class RelationshipProperty(StrategizedProperty): def parententity(self): return self.property.parent - def __clause_element__(self): + def _source_selectable(self): elem = self.property.parent._with_polymorphic_selectable if self.adapter: return self.adapter(elem) else: return elem + def __clause_element__(self): + adapt_from = self._source_selectable() + if self._of_type: + of_type = inspect(self._of_type).mapper + else: + of_type = None + + pj, sj, source, dest, \ + secondary, target_adapter = self.property._create_joins( + source_selectable=adapt_from, + source_polymorphic=True, + of_type=of_type) + if sj is not None: + return pj & sj + else: + return pj + def of_type(self, cls): """Produce a construct that represents a particular 'subtype' of attribute for the parent class. @@ -477,7 +496,7 @@ class RelationshipProperty(StrategizedProperty): to_selectable = None if self.adapter: - source_selectable = self.__clause_element__() + source_selectable = self._source_selectable() else: source_selectable = None diff --git a/lib/sqlalchemy/orm/util.py b/lib/sqlalchemy/orm/util.py index 750c3b298..2e38e0ce3 100644 --- a/lib/sqlalchemy/orm/util.py +++ b/lib/sqlalchemy/orm/util.py @@ -796,7 +796,7 @@ class _ORMJoin(expression.Join): prop = left_mapper.get_property(onclause) elif isinstance(onclause, attributes.QueryableAttribute): if adapt_from is None: - adapt_from = onclause.__clause_element__() + adapt_from = onclause.comparator._source_selectable() prop = onclause.property elif isinstance(onclause, MapperProperty): prop = onclause diff --git a/lib/sqlalchemy/sql/expression.py b/lib/sqlalchemy/sql/expression.py index 63b1a4037..5b6e4d82d 100644 --- a/lib/sqlalchemy/sql/expression.py +++ b/lib/sqlalchemy/sql/expression.py @@ -4839,7 +4839,7 @@ class SelectBase(Executable, FromClause): return [self] -class ScalarSelect(Grouping): +class ScalarSelect(Generative, Grouping): _from_objects = [] def __init__(self, element): @@ -4853,13 +4853,17 @@ class ScalarSelect(Grouping): 'column-level expression.') c = columns + @_generative + def where(self, crit): + """Apply a WHERE clause to the SELECT statement referred to + by this :class:`.ScalarSelect`. + + """ + self.element = self.element.where(crit) + def self_group(self, **kwargs): return self - def _make_proxy(self, selectable, name=None, **kw): - return list(self.inner_columns)[0]._make_proxy( - selectable, name=name) - class CompoundSelect(SelectBase): """Forms the basis of ``UNION``, ``UNION ALL``, and other SELECT-based set operations.""" |