我有一个名为' session_start'的DateTimeField。在一个模型中。我正在尝试过滤日期范围内的session_start字段。
Model.py
class TimeCard(models.Model):
profile = models.ForeignKey(settings.AUTH_USER_MODEL)
session_start = models.DateTimeField()
过滤器需要遵循以下条件:
start_date =从今天起30天后。
end_date =今天。
我写了以下代码来过滤" session_start"在" start_date"之间的范围内的字段和" end_date"。现在我停留在检查start_date大于end_date的条件。我该怎么做才能进行验证?
filter.py
class TimeCardFilter(filters.FilterSet):
start_date = django_filters.DateTimeFilter(name="session_start", lookup_type='gte')
end_date = django_filters.DateTimeFilter(name="session_start", lookup_type='lte')
class Meta:
model = TimeCard
fields = ['profile', 'start_date', 'end_date']
答案 0 :(得分:3)
您实际上可以在django-filters
过滤器中使用django forms,因此您可以使用表单clean()
方法管理验证。您的filter.py看起来像这样:
import django_filters
from app.models import TimeCard
from django import forms
class TimeCardFilter(django_filters.FilterSet):
start_date = django_filters.DateTimeFilter(
name="session_start",
lookup_type="gte")
end_date = django_filters.DateTimeFilter(
name="session_start",
lookup_type="lte")
class Meta:
model = TimeCard
form = TimeCardForm
class TimeCardForm(forms.Form):
def clean(self):
cleaned_data = super(TimeCardForm, self).clean()
start_date = cleaned_data.get("start_date")
end_date = cleaned_data.get("end_date")
if start_date < end_date:
self._errors['start_date'] = self._errors.get('start_date', [])
self._errors['start_date'].append("Start date must be before end date.")
return cleaned_data
答案 1 :(得分:1)
Based on the source code,您的选择可能有限。您最好的选择是覆盖qs
属性。
class TimeCardFilter(filters.FilterSet):
start_date = django_filters.DateTimeFilter(name="session_start", lookup_type='gte')
end_date = django_filters.DateTimeFilter(name="session_start", lookup_type='lte')
@property
def qs(self):
# Parent class defines a property _qs which represents the updated queryset
if hasattr(self, '_qs'):
return self._qs
# qs property is the place that FilterSet generates a query string.
# it finds the values in the self.form.cleaned_data or self.form[name].value()
orig_start = self.form.cleaned_data['session_start']
orig_end = self.form.cleaned_data['session_end']
# Your conditional logic would go here.
if orig_start > orig_end:
# You'll need real values here, these clearly are fake.
self.form.cleaned_data['session_start'] = now()-30 * 24 * 3600
self.form.cleaned_data['session_end'] = now()
# Be sure to return FilterSet's actual QS.
return super(TimeCardFilter, self).qs()
class Meta:
model = TimeCard
fields = ['profile', 'start_date', 'end_date']