модуль ActiveRecord::Locking::Optimistic
Что такое Оптимистическая блокировка
Оптимистическая блокировка позволяет нескольким пользователям получать доступ к одной и той же записи для редактирования и предполагает минимум конфликтов с данными. Она делает это, проверяя, не внес ли другой процесс изменения в запись с момента её открытия; если это произошло, выбрасывается исключение ActiveRecord::StaleObjectError, и обновление игнорируется.
Посмотрите ActiveRecord::Locking::Pessimistic для альтернативного подхода.
Использование
Active Record поддерживает оптимистическую блокировку, если поле lock_version присутствует. Каждое обновление записи увеличивает значение столбца lock_version, а механизмы блокировки гарантируют, что записи, инициализированные дважды, позволят последней сохранённой записи вызвать исключение StaleObjectError, если первая также была обновлена. Пример:
p1 = Person.find(1) p2 = Person.find(1) p1.first_name = "Michael" p1.save p2.first_name = "should fail" p2.save # Raises an ActiveRecord::StaleObjectError
Оптимистическая блокировка также проверяет наличие устаревших данных при удалении объектов. Пример:
p1 = Person.find(1) p2 = Person.find(1) p1.first_name = "Michael" p1.save p2.destroy # Raises an ActiveRecord::StaleObjectError
Затем вы несёте ответственность за решение конфликта путём перехвата исключения и либо отката, либо слияния, или иным образом применения бизнес-логики, необходимой для разрешения конфликта.
Этот механизм блокировки будет работать внутри одного процесса Ruby. Чтобы заставить его работать через все веб-запросы, рекомендуется добавить lock_version в качестве скрытого поля в вашу форму.
Это поведение можно отключить, установив ActiveRecord::Base.lock_optimistically = false. Чтобы переопределить имя столбца lock_version, задайте атрибут класса locking_column:
class Person < ActiveRecord::Base self.locking_column = :lock_person end
© 2004–2018 David Heinemeier Hansson
Licensed under the MIT License.