Обновление в Django для UniqueConstraint
Я пытаюсь работать с UniqueConstraint, но столкнулся с некоторыми проблемами, пытаясь обновить его так, как мне нужно.
У меня есть следующая модель
class QueryModel(models.Model):
id = models.AutoField(_("query id"), primary_key=True)
user = models.ForeignKey(UserModel, on_delete=models.CASCADE)
name = models.CharField(_("query name"), max_length=150)
status = models.CharField(
_("query status"),
choices=QueryStatus.choices,
default=QueryStatus.ACTIVE,
)
is_favorite = models.BooleanField(_("favorite"), default=False)
date_created = models.DateTimeField(_("date created"), auto_now_add=True)
class Meta(object):
app_label = "app"
db_table = "query"
constraints = [
models.UniqueConstraint(
fields=("user",),
condition=Q(is_favorite=True),
name="unique_favorite_per_user",
)
]
В моей системе пользователи могут создавать запросы и устанавливать их в качестве избранных, но у каждого пользователя может быть только 1 избранный запрос, поэтому я создал UniqueConstraint, чтобы обеспечить соблюдение этого бизнес-правила.
Тогда у меня будет конечная точка для установки запроса как избранного, но есть ли способ обновить это поле без необходимости проверять все поля is_favorite у каждого пользователя и вручную устанавливать их в False?
Я нашел это сообщение StackOverflow 2-летней давности, в котором предлагается решение, но это решение не работает для меня, я был бы очень признателен за помощь
Если вы хотите установить QueryModel
с my_pk
в качестве первичного ключа как избранный, вы обновляете с помощью:
from django.db.models import BooleanField, ExpressionWrapper, Q QueryModel.objects.filter(user=my_user).update( is_favorite=ExpressionWrapper(Q(pk=my_pk), BooleanField()) )
Это автоматически отключит избранное, если оно уже есть, и установит его на то, у которого my_pk
первичный ключ.
Альтернативно, мы можем работать с двумя обновлениями, одно из которых устанавливает все строки в False
, а другое - в True
:
QueryModel.objects.filter(user=my_user).update(is_favorite=False) QueryModel.objects.filter(user=my_user, pk=my_pk).update(is_favorite=True)