On Wednesday, August 16, 2017 at 2:27:11 PM UTC+3, Josh Smeaton wrote:
>
> It won't affect experienced users. They'll read the release notes, see
>> that this change has been implemented, and either go and delete a bunch of
>> prefetch_related() calls, grumble a bit and turn auto-prefetch off globally
>> or just file it away as another fact they know about the Django ORM.
>>
>
> This is, for me, the biggest point in favour of having it opt out. It'll
> barely affect anyone who is really experienced, but can provide such a
> large upside for others.
>
There is huge potential for this feature going very bad for performance.
For example, this common anti-pattern would immediately cause interesting
issues:
if qs:
qs[0].do_something()
then if do_something() does access a couple of relations, you'll load data
for the whole queryset where you only need it for the first one. So, at
least make this opt-in instead of opt-out.
Doing this for "select_related" cases on opt-in basis seems like a
plausible idea. Doing this for reverse foreign key or m2m cases where you
need to use prefetch_related seems complex to implement, and just for that
reason I'd avoid the prefetch related case at least initially.
Note that it should be possible to implement this fully as 3rd party
project if we add an easy way to customise how related object fetching is
done. I'm not sure if we can add an easy way for that.
By the way, a very efficient test for N+1 queries issue is to do something
like this:
def test_nplusone_queries(self):
self.create_object()
with self.count_queries() as cnt:
self.client.get('object_listing/')
self.create_object()
with self.assertNumQueries(cnt):
self.client.get('object_listing/')
that is, you test the same list view with one and two objects. If there was
an easy way to write tests like this, that would make n+1 queries problems
a lot easier to detect. Maybe something to make this kind of test trivial
to write could be in Django? Something like
self.assertListViewScales(object_creator, 'view_name')?
- Anssi
--
You received this message because you are subscribed to the Google Groups
"Django developers (Contributions to Django itself)" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
To post to this group, send email to [email protected].
Visit this group at https://groups.google.com/group/django-developers.
To view this discussion on the web visit
https://groups.google.com/d/msgid/django-developers/1dcd8559-5f99-4635-b1d1-959bea066192%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.