Django 验证时隙
Django validating time slot
这是我的模型,用于存储新预订时特定时间的可用性
class TimeSlot(models.Model):
day = models.ForeignKey(
Day,
on_delete=models.CASCADE,
related_name="time"
)
booking = models.ForeignKey(
Booking,
on_delete=models.CASCADE,
related_name="time"
)
start_hour = models.TimeField()
end_hour = models.TimeField()
class Meta:
unique_together = [('end_hour', 'start_hour',)]
def clean(self):
pass
目前它允许预订,即使那些在 end_hour 和 start_hour 方面被认为是重复的。我想阻止空位,这样就不会在已经预订的范围之间放置新的预订。
有谁知道如何使用范围吗?
我认为问题是允许添加属于现有时间范围内的 start_hour
和 end_hour
。当然 unique_together
约束不能处理这个,因为它只处理范围内的唯一性而不是唯一性。相反,您可以覆盖您的模型 clean
方法并在那里执行此验证:
from django.db.models import Q
from django.core.exceptions import ValidationError
class TimeSlot(models.Model):
day = models.ForeignKey(
Day,
on_delete=models.CASCADE,
related_name="time"
)
booking = models.ForeignKey(
Booking,
on_delete=models.CASCADE,
related_name="time"
)
start_hour = models.TimeField()
end_hour = models.TimeField()
class Meta:
unique_together = [('end_hour', 'start_hour',)]
def clean(self):
start_hour_in_range = Q(start_hour__lte=self.start_hour, end_hour__gte=self.start_hour)
end_hour_in_range = Q(start_hour__lte=self.end_hour, end_hour__gte=self.end_hour)
# Queryset that finds all clashing timeslots with the same day
queryset = self._meta.default_manager.filter(start_hour_in_range | end_hour_in_range, day=self.day)
if self.pk:
queryset = queryset.exclude(pk=self.pk) # Exclude this object if it is already saved to the database
if queryset.exists():
raise ValidationError('An existing timeslot clashes with the given one!')
接下来,如果您使用的是 ModelForm
,此方法将被自动调用,否则您可以调用 instance.full_clean()
,它将调用此方法和模型上的所有其他清洁方法(clean_fields
和 validate_unique
).
这是我的模型,用于存储新预订时特定时间的可用性
class TimeSlot(models.Model):
day = models.ForeignKey(
Day,
on_delete=models.CASCADE,
related_name="time"
)
booking = models.ForeignKey(
Booking,
on_delete=models.CASCADE,
related_name="time"
)
start_hour = models.TimeField()
end_hour = models.TimeField()
class Meta:
unique_together = [('end_hour', 'start_hour',)]
def clean(self):
pass
目前它允许预订,即使那些在 end_hour 和 start_hour 方面被认为是重复的。我想阻止空位,这样就不会在已经预订的范围之间放置新的预订。
有谁知道如何使用范围吗?
我认为问题是允许添加属于现有时间范围内的 start_hour
和 end_hour
。当然 unique_together
约束不能处理这个,因为它只处理范围内的唯一性而不是唯一性。相反,您可以覆盖您的模型 clean
方法并在那里执行此验证:
from django.db.models import Q
from django.core.exceptions import ValidationError
class TimeSlot(models.Model):
day = models.ForeignKey(
Day,
on_delete=models.CASCADE,
related_name="time"
)
booking = models.ForeignKey(
Booking,
on_delete=models.CASCADE,
related_name="time"
)
start_hour = models.TimeField()
end_hour = models.TimeField()
class Meta:
unique_together = [('end_hour', 'start_hour',)]
def clean(self):
start_hour_in_range = Q(start_hour__lte=self.start_hour, end_hour__gte=self.start_hour)
end_hour_in_range = Q(start_hour__lte=self.end_hour, end_hour__gte=self.end_hour)
# Queryset that finds all clashing timeslots with the same day
queryset = self._meta.default_manager.filter(start_hour_in_range | end_hour_in_range, day=self.day)
if self.pk:
queryset = queryset.exclude(pk=self.pk) # Exclude this object if it is already saved to the database
if queryset.exists():
raise ValidationError('An existing timeslot clashes with the given one!')
接下来,如果您使用的是 ModelForm
,此方法将被自动调用,否则您可以调用 instance.full_clean()
,它将调用此方法和模型上的所有其他清洁方法(clean_fields
和 validate_unique
).