Reputation: 403
EDIT: This may help get to the point of my question...
Is there a way to do "cascading" through: associations? For example, if we go with the bones song: "The foot bone is connected to the ankle bone, the ankle bone's connected to the leg bone, the leg bone's connected to the hip bone..." I don't want to say that the foot has_many hipbones, because that's not entirely accurate. Nor do I want to say the foot has_many hipbones through the legbone (because it also needs to pass through the ankle). No instead, the foot has_many hips through the ankle which is through the leg. The foot is connected to an ankle, and that foot_ankle assembly is then connected to a leg, and then that entire foot_ankle_leg assembly is finally attached to a hip. So a foot can have many hips, but the foot doesn't belong to a hip in isolation, the association exists only as part of a particular foot_ankle_leg assembly.
To represent something like this, am I correct in setting up those inbetween through tables to "carry" the foot/ankle/leg connections up to the hip? (ie The a_b_c_d_e table represents something akin to a "final" foot_ankle_leg_hip assembly)
ORIGINAL QUESTION: Have several models that come together with various intervening many-to-many :through tables. HABTM is not used since these through tables contain additional attributes.
Here's an image of how it fits together, green boxes are the many-to-many join tables. For brevity's sake, renamed to letters
Here's how the structure is coded
class A < ApplicationRecord
has_many :a_bs
has_many :bs, through: :a_b
...
end
class B < ApplicationRecord
has_many :a_bs,
has_many :as, through: :a_b
...
end
class AB < ApplicationRecord
belongs_to :a
belongs_to :b
has_many :a_b_c_ds
has_many :c_ds, through: :a_b_c_d
...
end
class C < ApplicationRecord
has_many :c_ds
has_many :ds, through: :c_d
...
end
class D < ApplicationRecord
has_many :c_ds
has_many :cs, through: :c_d
...
end
class CD < ApplicationRecord
belongs_to :c
belongs_to :d
has_many :a_b_c_ds
has_many :a_bs, through: :a_b_c_d
...
end
class ABCD < ApplicationRecord
belongs_to :a_b
belongs_to :c_d
has_many :a_b_c_d_es
has_many :es, through: :a_b_c_d_e
...
end
class E < ApplicationRecord
has_many :a_b_c_d_es
has_many :a_b_c_ds, through: :a_b_c_d_e
...
end
class ABCDE < ApplicationRecord
belongs_to :a_b_c_d
belongs_to :e
...
end
Whenever I try to access nested children from the parent object in the console, something like A.first.a_b_c_ds
, it returns
#<ABCD::ActiveRecord_Associations_CollectionProxy:0x26ca578>
.
Is this what I should be seeing? Do I need to interact with that CollectionProxy directly rather than see the "usual" records output? If so, that's a new thing I'll need to learn about :)
In the read-out, I also notice that it's attempting to find the parent's id in the through table rather than the "child" id that's associated.
ABCD Load (0.3ms) SELECT "a_b_c_ds".* FROM "a_b_c_d" WHERE "a_b_c_d"."a_id" = ? [["a_id", 1]]
Now, obviously, the a_id
won't be in table ABCD. But ab_id
is in there, which is associated with a_id
. And if I'm reading the rails-guide correctly, rails should be smart enough to make that distinction if I set it up properly.
Any idea where I'm taking a wrong turn?
The class names aren't necessarily alphabetical. For example, Wrapping, Package, Object, WrappingPackage, WrappingPacakgeObject. But since I'm using named many-to-many through: tables, it's my understanding the table names shouldn't matter. That it only comes into play when using has_many_and_belongs_to join tables. But is that where I'm off?
Thanks for your help! Let me know if you need more snippets!
Upvotes: 0
Views: 96
Reputation: 3267
Each belongs_to or has_many call creates an association method in all instances of the class.
So when you do:
class A
has_many bs
end
class B
has_many cs
end
then you basically added method bs
to all A's instances. There is no method cs
in A and there is no other magic involved.
Upvotes: 1