Целостность данных при обновлении / увеличении значений в Rails - PullRequest
2 голосов
/ 04 марта 2010

Я работаю над приложением, в котором один модуль обращается к журналу (модель ActiveRecord), чтобы увеличивать различные значения в нескольких точках выполнения. Проблема в том, что выполнение сценария может занять несколько секунд, а другие экземпляры этого же сценария могут выполняться в одно и то же время.

Что я вижу, так это то, что, хотя скрипт завершился правильно и все данные учтены, значения никогда не бывают правильными. Вероятно, это связано с тем, что к тому времени, когда сценарий достигает точки, в которой он обновляет значение, значение чтения для столбца (которое увеличивается) уже устарело.

Значения верны, если я заставлю его иметь только один экземпляр модуля за раз, но по соображениям производительности я не могу продолжать это делать.

В настоящее время я пытался решить эту проблему, запрашивая базу данных для записи перед каждым оператором приращения в транзакции, например, где column является символом столбца, а value равно 1 или выше:

Log.transaction do
  log = Log.find(@log_id)
  log.update_attribute(column, log.send(column) + value)
end

Однако, это все равно не даст мне точных цифр. Я думаю, что кеширование вовлечено, и я полагаю, что могу попробовать что-то вроде:

Log.transaction do
  uncached do
    log = Log.find(@log_id)
    log.update_attribute(column, log.send(column) + value)
  end
end

Но, конечно, я не могу быть первым, кто столкнулся с этой проблемой, поэтому мне интересно, есть ли лучшая реализация / решение для моей проблемы?

1 Ответ

3 голосов
/ 04 марта 2010

ActiveRecord предоставляет метод update_counters . Вы можете изменить свой код следующим образом:

Log.update_counters @log_id, column.to_sym => value
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...