Reputation: 43153
So, I have two models, Collection and Folder.
Within each Collection there is one root folder. Folders all belong to a Collection, but can also be nested within each other.
Following this question, I wrote my models like shown below. I also added a callback, because I always want a Collection to start out with a root folder.
class Folder < ActiveRecord::Base
has_one :master_collection, :class_name => 'Collection', :foreign_key => :root_folder_id
belongs_to :collection
belongs_to :parent, :class_name => 'Folder'
has_many :subfolders, :class_name => 'Folder', :foreign_key => :parent_id
...
end
class Collection < ActiveRecord::Base
belongs_to :root_folder, :class_name => 'Folder'
has_many :folders
after_create :setup_root_folder
private
def setup_root_folder
self.root_folder = Folder.create(:name => 'Collection Root', :collection => self )
end
end
In Folders I have the columns: parent_id, folder_id In Collections I have the column: root_folder_id
This seems like it should work, but I get this strange behavior in the console:
ruby-1.9.2-p0 :001 > c = Collection.create(:name=>"Example")
=> #<Collection id: 6, name: "Example", ...timestamps..., root_folder_id: 8>
ruby-1.9.2-p0 :003 > f = c.root_folder
=> #<Folder id: 8, parent_id: nil, name: "Collection Root", ...timestamps..., collection_id: 6>
ruby-1.9.2-p0 :004 > f.master_collection
=> nil
So, clearly the association works on the collection side, but the root folder is not able to find the collection it is the root of, even though the foreign key is available and ActiveRecord isn't raising any errors on using the association...
Any ideas?
Upvotes: 2
Views: 3136
Reputation: 14619
I suspect that this is what's happening:
C.after_create
root_folder_id
is set to F's id
F.master_collection
coleections.root_folder_id = folders.id
root_folder_id
hasn't been saved, F doesn't find anythingIf you want to test this, call c.save
in your example code before you call f.master_collection
- and you should get the collection, like you expect (you might need a f.reload
too).
That said, I've never liked double belongs_to
s (Folder belongs_to Collection + Collection belongs_to root_folder). Instead, I'd recommend:
class Collection < ActiveRecord::Base
has_one :root_folder, :class_name => 'Folder', :conditions => {:parent_id => nil}
# ...other stuff...
end
Hope that helps!
PS: Your definition of Folder.master_collection
will only give you back a collection if you call it from a root folder - all other folders will just return nil, since no collections have root_folder_id
s that point to them. Is that what you intended?
Upvotes: 2