Uh oh!
There was an error while loading.Please reload this page.
- Notifications
You must be signed in to change notification settings - Fork7k
Description
Checklist
- I have verified that that issue exists against the
masterbranch of Django REST framework. - I have searched for similar issues in both open and closed tickets and cannot find a duplicate.
- This is not a usage question. (Those should be directed to thediscussion group instead.)
- This cannot be dealt with as a third party library. (We prefer new functionality to bein the form of third party libraries where possible.)
- I have reduced the issue to the simplest possible case.
- I have included a failing test as a pull request. (If you are unable to do so we can still accept the issue.)
Steps to reproduce
I ran into a really nasty bug today because of how we are using DjangoFilterBackend. Here is our scenario... we have a FilterBackend as well as a parent filter backend (that is really a mixin). Our backend extends our mixin as well as the rest_framework.filters.DjangoFilterBackend.... so it looks something like this
classNewDjangoFilterBackend:deffilter_queryset(self):print("Inside django-filters")classDefaultDRFBackwardsCompat:def__new__(*args,**kwargs):returnNewDjangoFilterBackend()classOurCustomerFilterBackendParent:deffilter_queryset(self):print("Inside Our Parent Object")classOurFilterBackend(OurCustomerFilterBackendParent,DefaultDRFBackwardsCompat):passOurFilterBackend().filter_queryset()
Expected behavior
(this is in Python 3.4.6 btw)
I expect, because of Python's normal MRO thatfilter_queryset onOurCustomerFilterBackendParent will be called.
Actual behavior
Due to the__new__ inDefaultDRFBackwardsCompat thefilter_queryset inside ofdjango-filters is called instead.
It is not very clear to my why this would happen... but there has to be a way to deprecate a class without breaking Python's MRO.
In our case, the fix to our bug was to just use the DjangoFilterBackend from django-filters instead of the one in rest_framework... but this just seems like a potentially dangerous way to make something be backwards compatible.