Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

#56, #62 combined #63

Merged
merged 6 commits into from
May 25, 2015
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
55 changes: 39 additions & 16 deletions djangotoolbox/db/basecompiler.py
Original file line number Diff line number Diff line change
Expand Up @@ -43,7 +43,6 @@ def get_selected_fields(query):
else:
return query.model._meta.fields


EMULATED_OPS = {
'exact': lambda x, y: y in x if isinstance(x, (list, tuple)) else x == y,
'iexact': lambda x, y: x.lower() == y.lower(),
Expand Down Expand Up @@ -90,7 +89,7 @@ def __init__(self, compiler, fields):
self.compiler = compiler
self.connection = compiler.connection
self.ops = compiler.connection.ops
self.query = compiler.query # sql.Query
self.query = compiler.query # sql.Query
self.fields = fields
self._negated = False

Expand Down Expand Up @@ -189,12 +188,33 @@ def _decode_child(self, child):
leaf (a tuple).
"""

# TODO: Call get_db_prep_lookup directly, constraint.process
# doesn't do much more.
constraint, lookup_type, annotation, value = child
packed, value = constraint.process(lookup_type, value, self.connection)
alias, column, db_type = packed
field = constraint.field
if django.VERSION < (1, 7):
# TODO: Call get_db_prep_lookup directly, constraint.process
# doesn't do much more.
constraint, lookup_type, annotation, value = child
packed, value = constraint.process(lookup_type, value, self.connection)
alias, column, db_type = packed
field = constraint.field
else:
rhs, rhs_params = child.process_rhs(self.compiler, self.connection)

lookup_type = child.lookup_name

# Since NoSql databases generally don't support aggregation or
# annotation we simply pass true in this case unless the query has a
# get_aggregation method defined. It's a little troubling however that
# the _nomalize_lookup_value method seems to only use this value in the case
# that the value is an iterable and the lookup_type equals isnull.
if hasattr(self, 'get_aggregation'):
annotation = self.get_aggregation(using=self.connection)[None]
else:
annotation = True

value = rhs_params

packed = child.lhs.get_group_by_cols()[0]
alias, column = packed
field = child.lhs.output_field

opts = self.query.model._meta
if alias and alias != opts.db_table:
Expand Down Expand Up @@ -261,8 +281,7 @@ def _get_children(self, children):
result = []
for child in children:

if SubqueryConstraint is not None \
and isinstance(child, SubqueryConstraint):
if SubqueryConstraint is not None and isinstance(child, SubqueryConstraint):
raise DatabaseError("Subqueries are not supported.")

if isinstance(child, tuple):
Expand Down Expand Up @@ -338,7 +357,13 @@ def _matches_filters(self, entity, filters):
def _order_in_memory(self, lhs, rhs):
for field, ascending in self.compiler._get_ordering():
column = field.column
result = cmp(lhs.get(column), rhs.get(column))

# TOOD: cmp is removed in python 3. Rewrite this logic to leverage
# the __eq__() special function.
a = lhs.get(column)
b = rhs.get(column)

result = (a > b) - (a < b)
if result != 0:
return result if ascending else -result
return 0
Expand Down Expand Up @@ -396,8 +421,7 @@ def execute_sql(self, result_type=MULTI):
aggregate = aggregates[0]
assert isinstance(aggregate, sqlaggregates.Count)
opts = self.query.get_meta()
if aggregate.col != '*' and \
aggregate.col != (opts.db_table, opts.pk.column):
if aggregate.col != '*' and aggregate.col != (opts.db_table, opts.pk.column):
raise DatabaseError("This database backend only supports "
"count() queries on the primary key.")

Expand Down Expand Up @@ -449,9 +473,8 @@ def check_query(self):
"""
if hasattr(self.query, 'is_empty') and self.query.is_empty():
raise EmptyResultSet()
if (len([a for a in self.query.alias_map if
self.query.alias_refcount[a]]) > 1 or
self.query.distinct or self.query.extra or self.query.having):
if (len([a for a in self.query.alias_map if self.query.alias_refcount[a]]) > 1
or self.query.distinct or self.query.extra or self.query.having):
raise DatabaseError("This query is not supported by the database.")

def get_count(self, check_exists=False):
Expand Down