class Assembly < ActiveRecord::Base
has_and_belongs_to_many :parts
end
class Part < ActiveRecord::Base
has_and_belongs_to_many :assemblies
end
In console:
part1 = Part.new
assembly1 = Assembly.new
assembly1.parts << part1
part1.delete
Parts.all
=> []
Checking assembly1.parts shows that there is still a relationship.(!)
How is this possible when the record was deleted?
Also, how to prevent deletion of parts that are associated to assemblies?
Working in Rails 3.0.7.
Everything you were doing here was done from memory (nothing was stored in the database).
the ActiveRecord
deletemethod will remove an object from the database but it doesn’t look for other objects in memory that may have already been referencing that object. I think if you didassembly1.parts.delete(part1)that would likely do what you were expecting.If you had saved the objects to the database:
Note here how even if it’s in the database
part1.deletewon’t necessarily remove it from your assembly object until you refresh the in-memory collection or delete it using the method I mentioned earlierassembly1.parts.delete(part1)UPDATE
I think you usually shouldn’t use the
delete()method. You should almost always usedestroy().delete()will just fire off a delete to the database and ignores all callbacks and I believe:dependent => :destroy-style declarations in your model. If you use thedestroy()method then you can declare abefore_destroycallback in your model:That should get your requirement of not destroying it if it is part of an assembly. You cannot stop
delete()from executing because it ignores callbacks: ActiveRecord::Relation#delete documentationMore info about model callbacks (documentation)