Fix a performance issue with datagrids using chained select_related calls.

Review Request #8877 - Created April 5, 2017 and submitted

Christian Hammond

Datagrids allow columns to augment the queryset, pulling in additional
fields if needed. While we've generally gotten away with this, it
doesn't really work well in practice on Django 1.6, because calls to
select_related() do not chain. They've fixed this on newer versions of
Django, but we can't depend on those for this.

The good news is that they can be made to be chainable by merging the
select_related dictionaries on querysets. This format is standard on all
versions of Django 1.6 and higher.

This change introduces a chainable_select_related_queryset function that
takes in a QuerySet and returns a version supporting chaining. On Django
1.6, this returns a special subclass that handles merging. On newer
versions, this simply returns the provided QuerySet.

Datagrids make use of this to ensure that all select_related() calls
from queryset augmentation will stay performant and won't
unintentionally drop select_related() fields.

Unit tests pass.

Manually verified that different select_related() calls were being
factored in for the datagrid.

Barret Rennie
David Trowbridge
Christian Hammond
Review request changed

Status: Closed (submitted)

Change Summary:

Pushed to release-0.9.x (08976bd)