Hm...if I change the before_destroy hook to:

def before_destroy
  self.bars_dataset.delete
end

It seems to do the right thing. Is that the preferred way of doing it?

/lasso



On 24 mar, 14:18, Lars Olsson <[email protected]> wrote:
> Hi,
>
> Recently I've been playing around with destroy hooks in Sequel::Model.
> Everything works as expected, but the qenerated SQL seems a bit
> inefficient. Lets say I have this:
>
> ### Start code
> require 'logger'
> require 'sequel'
>
> DB_NAME = 'foobar.db'
>
> # Remove old db (if it exists)
> File.delete(DB_NAME) if File.exists?(DB_NAME)
>
> # Create new (sqlite) db
> DB = Sequel.sqlite(DB_NAME, :loggers => Logger.new($stdout))
>
> # Allow table creation from within the model
> Sequel::Model.plugin(:schema)
>
> class Foo < Sequel::Model
>   self.db = DB
>   self.set_schema do
>     primary_key :id
>     text :s1
>     text :s2
>   end
>   self.create_table unless self.table_exists?
>
>   def before_destroy
>     self.bars.each do |bar|
>       bar.destroy
>     end
>   end
> end
>
> class Bar < Sequel::Model
>   self.db = DB
>   self.set_schema do
>     primary_key :id
>     text :s1
>     integer :i1
>     foreign_key :foo_id
>   end
>   self.create_table unless self.table_exists?
> end
>
> # Associations
> Foo.associate :one_to_many, :bars, :class => Bar, :key => :foo_id
> Bar.associate :many_to_one, :foo, :class => Foo, :key => :foo_id
>
> # Create some Foos and Bars
> foo_1 = Foo.new
> foo_1.s1 = 'foo_1'
> foo_1.s2 = 'foo_1'
> foo_1.save
>
> bar_1 = Bar.new
> bar_1.s1 = 'bar_1'
> bar_1.i1 = 1
> bar_1.foo = foo_1
> bar_1.save
>
> bar_2 = Bar.new
> bar_2.s1 = 'bar_2'
> bar_2.i1 = 2
> bar_2.foo = foo_1
> bar_2.save
>
> bar_3 = Bar.new
> bar_3.s1 = 'bar_3'
> bar_3.i1 = 3
> bar_3.foo = foo_1
> bar_3.save
>
> bar_4 = Bar.new
> bar_4.s1 = 'bar_4'
> bar_4.i1 = 4
> bar_4.foo = foo_1
> bar_4.save
>
> # Print all Bars
> puts Bar.all.inspect
>
> # Destroy the Foo
> foo_1.destroy
>
> # Print all Bars
> puts Bar.all.inspect
>
> ### End code
>
> Whenever I remove a Foo I also want to remove all associated Bars. The
> generated SQL code (for the before_destroy hook) looks like this:
>
> I, [2011-03-24T14:11:20.784272 #7766]  INFO -- : (0.000056s) BEGIN
> I, [2011-03-24T14:11:20.784996 #7766]  INFO -- : (0.000303s) SELECT *
> FROM `bars` WHERE (`bars`.`foo_id` = 1)
> I, [2011-03-24T14:11:20.785629 #7766]  INFO -- : (0.000181s) DELETE
> FROM `bars` WHERE (`id` = 1)
> I, [2011-03-24T14:11:20.786088 #7766]  INFO -- : (0.000089s) DELETE
> FROM `bars` WHERE (`id` = 2)
> I, [2011-03-24T14:11:20.786528 #7766]  INFO -- : (0.000088s) DELETE
> FROM `bars` WHERE (`id` = 3)
> I, [2011-03-24T14:11:20.786966 #7766]  INFO -- : (0.000083s) DELETE
> FROM `bars` WHERE (`id` = 4)
> I, [2011-03-24T14:11:20.787305 #7766]  INFO -- : (0.000142s) DELETE
> FROM `foos` WHERE (`id` = 1)
> I, [2011-03-24T14:11:20.802552 #7766]  INFO -- : (0.015104s) COMMIT
>
> As seen in the trace, the before_destroy hook generates four SQL
> calls, but ideally it should need just one:
> DELETE FROM `bars` WHERE (`foo_id` = 1)
>
> Is there a way to accomplish this within Sequel::Model? A
> Foo.destroy_all_bars method or something?
>
> /lasso

-- 
You received this message because you are subscribed to the Google Groups 
"sequel-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/sequel-talk?hl=en.

Reply via email to