我在 django 和 django-filter 之间获取错误

问题描述 投票:0回答:1

我的问题是 django-filter 库无法与 django Rest 框架中的选择字段一起正常工作:

模型.py

class Incident(models.Model):
    caller = models.ForeignKey(
        'core.Caller',
        verbose_name='caller',
        on_delete=models.PROTECT,
        related_name='incidents',
        blank=True,
        null=True,
    )
    declarant = models.ForeignKey(
        'core.Declarant',
        verbose_name='declarant',
        on_delete=models.CASCADE,
        related_name='incidents',
        blank=True,
        null=True,
    )
    kind = models.ForeignKey(
        IncidentKind,
        verbose_name='kind',
        on_delete=models.SET_NULL,
        related_name='incidents',
        blank=True,
        null=True,
    )
    duplicate_of = models.ForeignKey(
        'self',
        verbose_name='duplicate',
        on_delete=models.CASCADE,
        related_name='duplicates',
        blank=True,
        null=True,
    )
    source = models.CharField(
        'source',
        max_length=255,
        default=consts.IncidentSource.APP,
        choices=consts.IncidentSource.CHOICES,
    )
    status = models.CharField(
        'status',
        max_length=255,
        choices=consts.IncidentStatus.CHOICES,
        default=consts.IncidentStatus.REQUEST_112,
    )

过滤器

class Incident(django_filters.FilterSet):
    description = django_filters.CharFilter(lookup_expr='icontains')
    declarant_phone = django_filters.CharFilter(field_name='declarant__phone', lookup_expr='icontains')
    incident_address = django_filters.CharFilter(field_name='address__full_address', lookup_expr='icontains')
    source = django_filters.ChoiceFilter(choices=consts.IncidentSource.CHOICES, lookup_expr='icontains')
    status = django_filters.ChoiceFilter(choices=consts.IncidentStatus.CHOICES, lookup_expr='icontains')
    service = django_filters.Filter(method='filter_service')
    address_caller = django_filters.CharFilter(field_name='caller__address', lookup_expr='icontains')
    victims = django_filters.BooleanFilter(method='filter_victims')
    death = django_filters.BooleanFilter(method='filter_death')
    dt_create = django_filters.Filter(method='filter_dt_create')
    incident_moment = django_filters.Filter(method='filter_incident_moment')

    class Meta:
        model = models.Incident
        fields = [
            'is_needs_reaction',
            'is_social_significant',
            'is_risk_emergency',
            'description',
            'declarant_phone',
            'status',
            'source',
            'operator',
            'incident_address',
            'kind',
            'service',
            'address_caller',
            'victims',
            'death',
            'dt_create',
        ]

来源和状态选择字段。

我遇到了错误

super()._set_choices(value)
AttributeError: 'super' object has no attribute '_set_choices'

如果我使用 CharFilter,那么过滤会起作用,但不完全符合预期

source = django_filters.CharFilter(choices=consts.IncidentSource.CHOICES, lookup_expr='icontains')
    status = django_filters.CharFilter(choices=consts.IncidentStatus.CHOICES, lookup_expr='icontains')

我的回溯:

Traceback (most recent call last):
  File "/core/tests/test_incident.py", line 60, in test_update
    response = self.client.put(self.detail_url)
  File "/venv/lib/python3.10/site-packages/rest_framework/test.py", line 304, in put
    response = super().put(
  File "/venv/lib/python3.10/site-packages/rest_framework/test.py", line 214, in put
    return self.generic('PUT', path, data, content_type, **extra)
  File "/venv/lib/python3.10/site-packages/rest_framework/test.py", line 234, in generic
    return super().generic(
  File "/venv/lib/python3.10/site-packages/django/test/client.py", line 617, in generic
    return self.request(**r)
  File "/venv/lib/python3.10/site-packages/rest_framework/test.py", line 286, in request
    return super().request(**kwargs)
  File "/venv/lib/python3.10/site-packages/rest_framework/test.py", line 238, in request
    request = super().request(**kwargs)
  File "/venv/lib/python3.10/site-packages/django/test/client.py", line 1013, in request
    self.check_exception(response)
  File "/venv/lib/python3.10/site-packages/django/test/client.py", line 743, in check_exception
    raise exc_value
  File "/venv/lib/python3.10/site-packages/django/core/handlers/exception.py", line 55, in inner
    response = get_response(request)
  File "/venv/lib/python3.10/site-packages/django/core/handlers/base.py", line 197, in _get_response
    response = wrapped_callback(request, *callback_args, **callback_kwargs)
  File "/venv/lib/python3.10/site-packages/django/views/decorators/csrf.py", line 65, in _view_wrapper
    return view_func(request, *args, **kwargs)
  File "/venv/lib/python3.10/site-packages/rest_framework/viewsets.py", line 124, in view
    return self.dispatch(request, *args, **kwargs)
  File "/venv/lib/python3.10/site-packages/rest_framework/views.py", line 509, in dispatch
    response = self.handle_exception(exc)
  File "/venv/lib/python3.10/site-packages/rest_framework/views.py", line 469, in handle_exception
    self.raise_uncaught_exception(exc)
  File "/venv/lib/python3.10/site-packages/rest_framework/views.py", line 480, in raise_uncaught_exception
    raise exc
  File "/venv/lib/python3.10/site-packages/rest_framework/views.py", line 506, in dispatch
    response = handler(request, *args, **kwargs)
  File "/venv/lib/python3.10/site-packages/rest_framework/mixins.py", line 65, in update
    instance = self.get_object()
  File "/venv/lib/python3.10/site-packages/rest_framework/generics.py", line 87, in get_object
    queryset = self.filter_queryset(self.get_queryset())
  File "/venv/lib/python3.10/site-packages/rest_framework/generics.py", line 154, in filter_queryset
    queryset = backend().filter_queryset(self.request, queryset, self)
  File "/venv/lib/python3.10/site-packages/django_filters/rest_framework/backends.py", line 94, in filter_queryset
    if not filterset.is_valid() and self.raise_exception:
  File "/lib/python3.10/site-packages/django_filters/filterset.py", line 212, in is_valid
    return self.is_bound and self.form.is_valid()
  File "/venv/lib/python3.10/site-packages/django_filters/rest_framework/filterset.py", line 24, in form
    form = super().form
  File "/venv/lib/python3.10/site-packages/django_filters/filterset.py", line 264, in form
    Form = self.get_form_class()
  File "/venv/lib/python3.10/site-packages/django_filters/filterset.py", line 254, in get_form_class
    fields = OrderedDict([
  File "/venv/lib/python3.10/site-packages/django_filters/filterset.py", line 255, in <listcomp>
    (name, filter_.field)
  File "/venv/lib/python3.10/site-packages/django_filters/filters.py", line 137, in field
    self._field = self.field_class(label=self.label, **field_kwargs)
  File "/venv/lib/python3.10/site-packages/django_filters/fields.py", line 281, in __init__
    super().__init__(*args, **kwargs)
  File "/venv/lib/python3.10/site-packages/django_filters/fields.py", line 262, in __init__
    super().__init__(*args, **kwargs)
  File "/venv/lib/python3.10/site-packages/django/forms/fields.py", line 880, in __init__
    self.choices = choices
  File "/venv/lib/python3.10/site-packages/django_filters/fields.py", line 268, in _set_choices

我也只是尝试将源和状态字段传递到字段字段,它也没有帮助。 他问了GPT问题,他说其中一个可能的问题可能是库本身的bug,所以他决定在这里问另一个问题,以防有人有类似的情况

python django django-rest-framework django-filter
1个回答
0
投票

使用选择字段时删除

lookup_expr
。默认情况下,它使用精确的查找表达式,因为它是一个选择字段。

我的 Django 应用程序中的工作过滤器示例如下所示:

DOMAIN_CHOICES = (
    ('Educations', 'Educations'),
    ('Certificates', 'Certificates'),
    ('Qualifications', 'Qualifications'),
)

class HistoryFilter(filters.FilterSet):
    domain = filters.ChoiceFilter(choices=DOMAIN_CHOICES, required=True)

    class Meta:
        model = EmployeeHistory
        fields = ['domain']
© www.soinside.com 2019 - 2024. All rights reserved.