diff options
| author | Malcolm Tredinnick <malcolm.tredinnick@gmail.com> | 2009-04-04 03:21:31 +0000 |
|---|---|---|
| committer | Malcolm Tredinnick <malcolm.tredinnick@gmail.com> | 2009-04-04 03:21:31 +0000 |
| commit | dded5f52cc1dbe0e58b64a3217e12e72da7bed23 (patch) | |
| tree | 1c3cc230ff7713ab4bbd7d9da39aaa620e0302c1 /django/db/models/query.py | |
| parent | 19d14509299c641ee44ab0755a6e0f3026e48341 (diff) | |
Fixed #10695 -- Fixed implementation of deferred attribute retrieval.
The original implementation had a few silly bugs in it that meant that data was
not being used only on the instance of the class that it was appropriate for
(one of the traps when using class-level things). No more!
Thanks to Justin Bronn and Alex Gaynor for the patch.
git-svn-id: http://code.djangoproject.com/svn/django/trunk@10382 bcc190cf-cafb-0310-a4f2-bffc1f526a37
Diffstat (limited to 'django/db/models/query.py')
| -rw-r--r-- | django/db/models/query.py | 35 |
1 files changed, 17 insertions, 18 deletions
diff --git a/django/db/models/query.py b/django/db/models/query.py index ea7129b693..9dcc031a39 100644 --- a/django/db/models/query.py +++ b/django/db/models/query.py @@ -190,6 +190,20 @@ class QuerySet(object): index_start = len(extra_select) aggregate_start = index_start + len(self.model._meta.fields) + load_fields = only_load.get(self.model) + skip = None + if load_fields and not fill_cache: + # Some fields have been deferred, so we have to initialise + # via keyword arguments. + skip = set() + init_list = [] + for field in fields: + if field.name not in load_fields: + skip.add(field.attname) + else: + init_list.append(field.attname) + model_cls = deferred_class_factory(self.model, skip) + for row in self.query.results_iter(): if fill_cache: obj, _ = get_cached_row(self.model, row, @@ -197,25 +211,10 @@ class QuerySet(object): requested=requested, offset=len(aggregate_select), only_load=only_load) else: - load_fields = only_load.get(self.model) - if load_fields: - # Some fields have been deferred, so we have to initialise - # via keyword arguments. + if skip: row_data = row[index_start:aggregate_start] pk_val = row_data[pk_idx] - skip = set() - init_list = [] - for field in fields: - if field.name not in load_fields: - skip.add(field.attname) - else: - init_list.append(field.attname) - if skip: - model_cls = deferred_class_factory(self.model, pk_val, - skip) - obj = model_cls(**dict(zip(init_list, row_data))) - else: - obj = self.model(*row[index_start:aggregate_start]) + obj = model_cls(**dict(zip(init_list, row_data))) else: # Omit aggregates in object creation. obj = self.model(*row[index_start:aggregate_start]) @@ -927,7 +926,7 @@ def get_cached_row(klass, row, index_start, max_depth=0, cur_depth=0, else: init_list.append(field.attname) if skip: - klass = deferred_class_factory(klass, pk_val, skip) + klass = deferred_class_factory(klass, skip) obj = klass(**dict(zip(init_list, fields))) else: obj = klass(*fields) |
