Удалите строку, как только столбец достигает определенного значения

#python #postgresql #concurrency #sqlalchemy #locking

#python #postgresql #параллелизм #sqlalchemy #блокировка

Вопрос:

Если это моя модель:

 class Entity(Base):
    id = Column(Integer, primary_key=True)
    count = Column(Integer, default=0)
 

Я хочу удалить все строки, которые достигают count значения 3 (или любого числа).
Как я могу это сделать?
должен ли я реализовать такое удаление в контроллере моего веб-приложения и каждый раз count при увеличении проверять, равно ли его значение 3 или нет? Как я должен заботиться о параллельных запросах, которые меняют значение? Каково наилучшее решение?

Ответ №1:

После некоторого размышления и консультаций с экспертами я понял, что решением этого вопроса является либо реализация блокировки в базе данных, либо использование redis. Поскольку блокировка может вызвать проблемы с производительностью при множестве запросов, лучше сохранить значение count в базе данных redis и попытаться обновлять count значение в объектно-реляционной базе данных в определенные периоды времени.

Ответ №2:

Должен ли я реализовать удаление в контроллере моего веб-приложения?

ДА. Вы должны реализовать это в своем контроллере. Просто убедитесь, что у вас есть представление, которое сможет получить доступ к вашей delete функции в контроллере.

Кто [как] я могу это сделать?

Просто. В вашем контроллере создайте функцию, которая будет обрабатывать удаление. Тело функции удаления должно выглядеть следующим образом:

 limit = 3 # The value of this variable is arbitrary.
Entity.query.filter(Entity.count == limit).delete()
# The two statements above can be simplified to
# Entity.query.filter(Entity.count == 3).delete()

db.session.commit()
 

Еще лучше, добавьте параметр функции, который будет принимать значение, которое будет максимальным значением столбца в строке. Это может выглядеть так:

 def delete_entity(limit=3): # I set `limit` to 3 since that is what you have stated earlier in the question
    Entity.query.filter(Entity.count == limit).delete()
    db.session.commit()
 

Каждый раз, когда количество увеличивается, я проверяю, равно ли значение 3 или нет? Каково наилучшее решение?

Это зависит от того, что вы хотите, чтобы ваше приложение выполняло.

Комментарии:

1. Я боюсь, что ваш ответ не учитывает риск одновременных запросов, влияющих на count значение

2. Что произойдет, если около 1000 повторных обращений пытаются увеличить количество?

3. @AminEtesamian Когда я ответил на ваш вопрос, вы еще не добавили параллельные запросы.

4. @Sean, WTF. Рассмотрим, что ВСЕ запросы в веб-приложении являются ПАРАЛЛЕЛЬНЫМИ.

5. @pylover Спасибо за исправление. Мой плохой. Я забыл отметить, что все запросы должны считаться параллельными. Спасибо!