Само по себе два одновременных обновления не приведет к взаимоблокировке, а только к временной блокировке. Давайте назовем их Bid A
и Bid B
.
Хотя мы рассматриваем их одновременно, сначала нужно получить блокировку. Мы скажем, что A
добирается туда на 1 мс быстрее.
A
получает блокировку для рассматриваемой строки. B
отправляет запрос на блокировку в очередь и должен дождаться снятия блокировки, принадлежащей A
. Как только блокировка A
снята, B
получает блокировку.
В вашем коде может быть что-то еще, кроме вашего вопроса, и, как я уже описал, сценария тупиковой ситуации не существует. Для взаимоблокировки A
должен ожидать, пока B
снимет блокировку с другого ресурса, но B
не снимет блокировку, пока не получит блокировку ресурса A
.
Если вам нужно проверить ставку в режиме реального времени, вы можете:
A. Используйте соответствующий уровень изоляции транзакции (повторяемое чтение, вероятно, по умолчанию в InnoDB) и выполняйте выбор и обновление в явной транзакции.
BEGIN TRAN
SELECT ... FOR UPDATE
IF ...
UPDATE ...
COMMIT
B. Выполните свою логику проверки в самом операторе Update. Другими словами, создайте запрос UPDATE, чтобы он влиял на строки только тогда, когда текущая ставка меньше новой ставки. Если записи не были затронуты, ставка была слишком низкой. Это возможный подход и сокращает работу с БД, но имеет свои соображения.
UPDATE ...
WHERE currentBid < newBid
Лично я бы выбрал А, потому что я не знаю, насколько сложна ваша логика.
A repeatable read
уровень изоляции гарантирует, что при каждом прочтении данной записи в транзакции значение гарантированно будет одинаковым. Он делает это, удерживая блокировку строки, которая не позволяет другим обновлять данную строку до тех пор, пока ваша транзакция не выполнит фиксацию или откат. Одно соединение не может обновить вашу таблицу, пока последняя не завершит свою транзакцию.
Суть в том, что ваш выбор / обновление будет атомарным в вашей БД, поэтому вам не придется беспокоиться о потерянных обновлениях.
Что касается параллелизма, ключ в том, чтобы ваши транзакции были максимально короткими. Садись, уходи. По умолчанию вы не можете прочитать обновляемую запись, потому что она находится в неопределенном состоянии. Эти обновления и чтения должны занимать небольшие доли секунды.