How does the :save hook relate to the :update hook in DataMapper?
-
10-02-2021 - |
Question
If I define the following model...
class Foo
include DataMapper::Resource
property :name, String, :key => true
before :save, do
puts 'save'
end
before :update, do
puts 'update'
end
end
Why does the 2nd save also trigger the 'update' hook?
ruby :001 > f = Foo.new
=> #<Foo @name=nil>
ruby :002 > f.name = 'Bob'
=> "Bob"
ruby :003 > f.save
save
=> true
ruby :004 > f.name = 'Joe'
=> "Joe"
ruby :005 > f.save
save
update
=> true
Of course I could dive into the source and answer the question of what code drives this behavior. More importantly, I want to understand the right way to use each of these hooks in practice.
Solution
require 'rubygems'
require 'data_mapper'
class Foo
include DataMapper::Resource
property :name, String, :key => true
before :create, do
puts 'Create: Only happens when saving a new object.'
end
before :update, do
puts 'Update: Only happens when saving an existing object.'
end
before :save, do
puts 'Save: Happens when either creating or updating an object.'
end
before :destroy, do
puts 'Destroy: Only happens when destroying an existing object.'
end
end
DataMapper.setup :default, 'sqlite::memory:'
DataMapper.finalize
DataMapper.auto_migrate!
puts "New Foo:"
f = Foo.new :name => "Fighter"
f.save
puts "\nUpdate Foo:"
f.name = "Bar"
f.save
puts "\nUpdate Foo again:"
f.update :name => "Baz"
puts "\nDestroy Foo:"
f.destroy
Which returns:
New Foo:
Save: Happens when either creating or updating an object.
Create: Only happens when saving a new object.
Update Foo:
Save: Happens when either creating or updating an object.
Update: Only happens when saving an existing object.
Update Foo again:
Save: Happens when either creating or updating an object.
Update: Only happens when saving an existing object.
Destroy Foo:
Destroy: Only happens when destroying an existing object.
So as you can see you'd want to use :save
hooks whenever something should happen after either a create or an update, and :create
and/or :update
when you want a finer level of control.
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow