On Aug 19, 2010, at 1:31 PM, Michael Pavling wrote:
> On 19 August 2010 21:18, Philip Hallstrom <[email protected]> wrote:
>> Don't use increment. It won't do what you want since it's only incrementing
>> the value of the object and then saving it. Not updating the value in the
>> database.
>
> What is "saving" if not updating in the database?
Let's say we have User u with id 123. u.foo = 1.
u.increment(:foo) will execute this: update users set foo = 2 where id = 123
If I have multiple copies of User 123 lying around (different mongrels perhaps)
there is a race condition. The longer I hold onto a copy of User 123 the
better chance I have of losing the true value of foo since increment() will
*overwrite* the value in the database, not add to it.
If however I do this...
User.increment_counter(:foo, 123) that will execute this: update users set foo
= foo + 1 where id = 123
It doesn't matter how many times or where I call it, the *database* will
contain the correct value of foo.
It's very possible that my local copy "u" won't until I reload it however.
>
>> You want to use increment_counter which calls update_counters which does
>> this in the database:
>
> What is the result of your "u" "u1" console experiment when you use
> increment_counter rather than increment?
> As far as I can see it will be the same - you've got two copies of an
> object loaded, and you update one, without reloading the other; of
> course that can lead to race conditions and stale data.
No. increment_counter doesn't operate on an instance of the class....
>> u = User.find(2)
>> u.login_count
=> 8
>> User.increment_counter(:login_count, 2)
User Update (3.0ms) UPDATE "users" SET "login_count" =
COALESCE("login_count", 0) + 1 WHERE ("id" = 2)
=> 1
>> u.login_count
=> 8
>> u.reload
User Load (1.7ms) SELECT * FROM "users" WHERE ("users"."id" = 2)
>> u.login_count
=> 9
--
You received this message because you are subscribed to the Google Groups "Ruby
on Rails: Talk" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected].
For more options, visit this group at
http://groups.google.com/group/rubyonrails-talk?hl=en.