Search code examples
djangodjango-filter

AttributeError: type object has no attribute '_meta'


I'm trying to follow the docs on using django-filter at https://django-rest-framework-datatables.readthedocs.io/en/latest/django-filters.html#django-filter-quickstart

When I add the ExpertGlobalFilter to my ExpertViewset like so

class GlobalCharFilter(GlobalFilter, filters.CharFilter):
    pass    

class ExpertGlobalFilter(GlobalFilter):
    name = GlobalCharFilter(lookup_expr='icontains')
    objectives = GlobalCharFilter(field_name='meetings__objective', lookup_expr='icontains')

    class Meta:
        model = Expert
        fields = '__all__'

class ExpertViewSet(viewsets.ModelViewSet):
    queryset = Expert.objects.all().order_by("id")
    serializer_class = ExpertSerializer
    filter_backends = (DatatablesFilterBackend,)
    filterset_class = ExpertGlobalFilter

I get the following error

Environment:


Request Method: GET
Request URL: http://localhost:8000/api/experts/?format=datatables&draw=1&columns%5B0%5D%5Bdata%5D=id&columns%5B0%5D%5Bname%5D=&columns%5B0%5D%5Bsearchable%5D=true&columns%5B0%5D%5Borderable%5D=true&columns%5B0%5D%5Bsearch%5D%5Bvalue%5D=&columns%5B0%5D%5Bsearch%5D%5Bregex%5D=false&columns%5B1%5D%5Bdata%5D=name&columns%5B1%5D%5Bname%5D=&columns%5B1%5D%5Bsearchable%5D=true&columns%5B1%5D%5Borderable%5D=true&columns%5B1%5D%5Bsearch%5D%5Bvalue%5D=&columns%5B1%5D%5Bsearch%5D%5Bregex%5D=false&columns%5B2%5D%5Bdata%5D=objectives&columns%5B2%5D%5Bname%5D=objectives&columns%5B2%5D%5Bsearchable%5D=true&columns%5B2%5D%5Borderable%5D=true&columns%5B2%5D%5Bsearch%5D%5Bvalue%5D=&columns%5B2%5D%5Bsearch%5D%5Bregex%5D=false&order%5B0%5D%5Bcolumn%5D=0&order%5B0%5D%5Bdir%5D=asc&start=0&length=10&search%5Bvalue%5D=&search%5Bregex%5D=false&_=1614377397193

Traceback (most recent call last):
  File "/usr/local/lib/python3.9/site-packages/django/core/handlers/exception.py", line 47, in inner
    response = get_response(request)
  File "/usr/local/lib/python3.9/site-packages/django/core/handlers/base.py", line 181, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)
  File "/usr/local/lib/python3.9/site-packages/django/views/decorators/csrf.py", line 54, in wrapped_view
    return view_func(*args, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/rest_framework/viewsets.py", line 125, in view
    return self.dispatch(request, *args, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/rest_framework/views.py", line 509, in dispatch
    response = self.handle_exception(exc)
  File "/usr/local/lib/python3.9/site-packages/rest_framework/views.py", line 469, in handle_exception
    self.raise_uncaught_exception(exc)
  File "/usr/local/lib/python3.9/site-packages/rest_framework/views.py", line 480, in raise_uncaught_exception
    raise exc
  File "/usr/local/lib/python3.9/site-packages/rest_framework/views.py", line 506, in dispatch
    response = handler(request, *args, **kwargs)
  File "/usr/local/lib/python3.9/site-packages/rest_framework/mixins.py", line 38, in list
    queryset = self.filter_queryset(self.get_queryset())
  File "/usr/local/lib/python3.9/site-packages/rest_framework/generics.py", line 150, in filter_queryset
    queryset = backend().filter_queryset(self.request, queryset, self)
  File "/usr/local/lib/python3.9/site-packages/rest_framework_datatables/django_filters/backends.py", line 28, in filter_queryset
    filterset = self.get_filterset(request, queryset, view)
  File "/usr/local/lib/python3.9/site-packages/django_filters/rest_framework/backends.py", line 31, in get_filterset
    filterset_class = self.get_filterset_class(view, queryset)
  File "/usr/local/lib/python3.9/site-packages/django_filters/rest_framework/backends.py", line 60, in get_filterset_class
    filterset_model = filterset_class._meta.model

Exception Type: AttributeError at /api/experts/
Exception Value: type object 'ExpertGlobalFilter' has no attribute '_meta'

A fully runnable example resides at https://github.com/morenoh149/django-rest-datatables-relations-example

error _meta


Solution

  • ExpertGlobalSet needs to be a DatatablesFilterSet, not GlobalFilter

    from django_filters import filters
    from rest_framework import viewsets
    from rest_framework_datatables.django_filters.backends import DatatablesFilterBackend
    from rest_framework_datatables.django_filters.filterset import DatatablesFilterSet
    from rest_framework_datatables.django_filters.filters import GlobalFilter
    
    
    class GlobalCharFilter(GlobalFilter, filters.CharFilter):
        pass
    
    class ExpertGlobalFilterSet(DatatablesFilterSet):
        name = GlobalCharFilter(lookup_expr='icontains')
        objectives = GlobalCharFilter(field_name='meeting__objective', lookup_expr='icontains')
    
        class Meta:
            model = Expert
            fields = '__all__'
    
    class ExpertViewSet(viewsets.ModelViewSet):
        queryset = Expert.objects.all().order_by("id")
        serializer_class = ExpertSerializer
        filter_backends = (DatatablesFilterBackend,)
        filterset_class = ExpertGlobalFilterSet