Skip to content

Commit 0d126bc

Browse files
committed
Refactored AutoPrefetchRelated mixin
1 parent 4e30c1b commit 0d126bc

File tree

3 files changed

+20
-11
lines changed

3 files changed

+20
-11
lines changed

example/tests/test_performance.py

+1-1
Original file line numberDiff line numberDiff line change
@@ -53,7 +53,7 @@ def test_query_count_include_author(self):
5353
4. Author types prefetched
5454
5. Entries prefetched
5555
"""
56-
with self.assertNumQueries(5):
56+
with self.assertNumQueries(4):
5757
response = self.client.get('/comments?include=author&page[size]=25')
5858
self.assertEqual(len(response.data['results']), 25)
5959

example/views.py

+2-2
Original file line numberDiff line numberDiff line change
@@ -12,7 +12,7 @@
1212
from rest_framework_json_api.filters import OrderingFilter, QueryParameterValidationFilter
1313
from rest_framework_json_api.pagination import JsonApiPageNumberPagination
1414
from rest_framework_json_api.utils import format_drf_errors
15-
from rest_framework_json_api.views import ModelViewSet, RelationshipView
15+
from rest_framework_json_api.views import ModelViewSet, RelationshipView, PreloadIncludesMixin
1616

1717
from example.models import Author, Blog, Comment, Company, Entry, Project, ProjectType
1818
from example.serializers import (
@@ -200,7 +200,7 @@ def get_queryset(self, *args, **kwargs):
200200
return super(CommentViewSet, self).get_queryset()
201201

202202

203-
class CompanyViewset(ModelViewSet):
203+
class CompanyViewset(PreloadIncludesMixin, viewsets.ModelViewSet):
204204
queryset = Company.objects.all()
205205
serializer_class = CompanySerializer
206206
prefetch_for_includes = {

rest_framework_json_api/views.py

+17-8
Original file line numberDiff line numberDiff line change
@@ -35,7 +35,7 @@ class PrefetchForIncludesHelperMixin(object):
3535

3636
def __init__(self, *args, **kwargs):
3737
warnings.warn("PrefetchForIncludesHelperMixin is deprecated. "
38-
"Use AutoPreloadMixin instead",
38+
"Use PreloadIncludesMixin instead",
3939
DeprecationWarning)
4040
super(PrefetchForIncludesHelperMixin, self).__init__(*args, **kwargs)
4141

@@ -70,7 +70,7 @@ class MyViewSet(viewsets.ModelViewSet):
7070
return qs
7171

7272

73-
class AutoPreloadMixin(object):
73+
class PreloadIncludesMixin(object):
7474
"""
7575
This mixin provides a helper attributes to select or prefetch related models
7676
based on the include specified in the URL.
@@ -99,22 +99,30 @@ def get_prefetch_related(self, include):
9999
return getattr(self, 'prefetch_for_includes', {}).get(include, None)
100100

101101
def get_queryset(self, *args, **kwargs):
102-
""" This mixin adds automatic prefetching for OneToOne and ManyToMany fields. """
103-
qs = super(AutoPreloadMixin, self).get_queryset(*args, **kwargs)
104-
included_resources = get_included_resources(self.request)
102+
qs = super(PreloadIncludesMixin, self).get_queryset(*args, **kwargs)
105103

104+
included_resources = get_included_resources(self.request)
106105
for included in included_resources + ['__all__']:
107-
# Custom defined "select_related" and "prefetch_related" is a priority
106+
108107
select_related = self.get_select_related(included)
109108
if select_related is not None:
110109
qs = qs.select_related(*select_related)
111-
continue
112110

113111
prefetch_related = self.get_prefetch_related(included)
114112
if prefetch_related is not None:
115113
qs = qs.prefetch_related(*prefetch_related)
116-
continue
117114

115+
return qs
116+
117+
118+
class AutoPreloadMixin(object):
119+
120+
def get_queryset(self, *args, **kwargs):
121+
""" This mixin adds automatic prefetching for OneToOne and ManyToMany fields. """
122+
qs = super(AutoPreloadMixin, self).get_queryset(*args, **kwargs)
123+
included_resources = get_included_resources(self.request)
124+
125+
for included in included_resources + ['__all__']:
118126
# If include was not defined, trying to resolve it automatically
119127
included_model = None
120128
levels = included.split('.')
@@ -252,6 +260,7 @@ def get_related_instance(self):
252260

253261

254262
class ModelViewSet(AutoPreloadMixin,
263+
PreloadIncludesMixin,
255264
RelatedMixin,
256265
viewsets.ModelViewSet):
257266
pass

0 commit comments

Comments
 (0)