Refs #28459 -- Improved performance of SQLCompiler.results_iter().

This commit is contained in:
Sergey Fedoseev 2017-08-08 02:06:15 +05:00 committed by Tim Graham
parent 50a97edc1a
commit ca46f4688c
3 changed files with 18 additions and 16 deletions

View File

@ -1227,9 +1227,9 @@ class RawQuerySet:
converters = compiler.get_converters([ converters = compiler.get_converters([
f.get_col(f.model._meta.db_table) if f else None for f in fields f.get_col(f.model._meta.db_table) if f else None for f in fields
]) ])
if converters:
query = compiler.apply_converters(query, converters)
for values in query: for values in query:
if converters:
values = compiler.apply_converters(values, converters)
# Associate fields to values # Associate fields to values
model_init_values = [values[pos] for pos in model_init_pos] model_init_values = [values[pos] for pos in model_init_pos]
instance = model_cls.from_db(db, model_init_names, model_init_values) instance = model_cls.from_db(db, model_init_names, model_init_values)

View File

@ -938,14 +938,17 @@ class SQLCompiler:
converters[i] = (convs, expression) converters[i] = (convs, expression)
return converters return converters
def apply_converters(self, row, converters): def apply_converters(self, rows, converters):
row = list(row) connection = self.connection
for pos, (convs, expression) in converters.items(): converters = list(converters.items())
value = row[pos] for row in rows:
for converter in convs: row = list(row)
value = converter(value, expression, self.connection) for pos, (convs, expression) in converters:
row[pos] = value value = row[pos]
return tuple(row) for converter in convs:
value = converter(value, expression, connection)
row[pos] = value
yield tuple(row)
def results_iter(self, results=None): def results_iter(self, results=None):
"""Return an iterator over the results from executing this query.""" """Return an iterator over the results from executing this query."""
@ -953,11 +956,10 @@ class SQLCompiler:
results = self.execute_sql(MULTI) results = self.execute_sql(MULTI)
fields = [s[0] for s in self.select[0:self.col_count]] fields = [s[0] for s in self.select[0:self.col_count]]
converters = self.get_converters(fields) converters = self.get_converters(fields)
for rows in results: rows = chain.from_iterable(results)
for row in rows: if converters:
if converters: rows = self.apply_converters(rows, converters)
row = self.apply_converters(row, converters) return rows
yield row
def has_results(self): def has_results(self):
""" """

View File

@ -464,7 +464,7 @@ class Query:
result = [None for q in outer_query.annotation_select.items()] result = [None for q in outer_query.annotation_select.items()]
converters = compiler.get_converters(outer_query.annotation_select.values()) converters = compiler.get_converters(outer_query.annotation_select.values())
result = compiler.apply_converters(result, converters) result = next(compiler.apply_converters((result,), converters))
return { return {
alias: val alias: val