Forum: Ruby on Rails Joining three objects uniquely using :has_many

Announcement (2017-05-07): www.ruby-forum.com is now read-only since I unfortunately do not have the time to support and maintain the forum any more. Please see rubyonrails.org/community and ruby-lang.org/en/community for other Rails- und Ruby-related community platforms.
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-22 01:20
(Received via mailing list)
I've confused myself.

I have three objects: level, product, part. Together they classify a
repair type.

- Replacing a part in a product has a level of difficulty associated
with it.
- The same part replaced in a different product has a different level
of difficulty.

How can I model an association among these?

I have created a join model, "Repair class," and connected all three
using :has_many through. However, this does not prevent multiple
records where the part and product stay the same, but the level
changes. In other words, I end up with multiple levels assigned to the
same part/product combination which does not happen in the real world.

What's the best way to proceed?

Evan
81b61875e41eaa58887543635d556fca?d=identicon&s=25 Frederick Cheung (Guest)
on 2009-02-22 01:27
(Received via mailing list)
On 22 Feb 2009, at 00:20, Evan wrote:

>
> How can I model an association among these?
>
> I have created a join model, "Repair class," and connected all three
> using :has_many through. However, this does not prevent multiple
> records where the part and product stay the same, but the level
> changes. In other words, I end up with multiple levels assigned to the
> same part/product combination which does not happen in the real world.
>

You might want to describe exactly what join model you have created

Personally my instinct would be to have a unique index on the join
table enforcing that there is only one entry for each part/product pair

Fred
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-22 01:32
(Received via mailing list)
My join model is "Repair class." Its attributes are:

- id (PK)
- level_id (FK)
- product_id (FK)
- part_id (FK)
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-22 01:42
(Received via mailing list)
So I could create a unique index consisting of product_id, part_id. Is
it possible to then create a unique index consisting of level_id and
the other index? I am using MySQL currently.
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-22 02:26
(Received via mailing list)
I just tried this code and was still able to create records with
different levels for the same part/product combination.

class RepairClass < ActiveRecord::Base
  belongs_to :level
  belongs_to :product
  belongs_to :part

  validates_presence_of :level_id, :product_id, :part_id
  validates_uniqueness_of :level_id, :scope =>
[ :product_id, :part_id ]
end
6fabb84e727dee98d1277df56458cbac?d=identicon&s=25 Andrew Bloom (Guest)
on 2009-02-22 05:33
(Received via mailing list)
I'm not sure I'm 100% clear, but it sounds like you are saying that a
Repair may only have one combination of Part/Product, and it just so
happens that this combination implies a Level. To me the validation
would be:

class Repair < ActiveRecord::Base
  belongs_to :level
  belongs_to :product
  belongs_to :part

  validates_presence_of :level_id, :product_id, :part_id
  validates_uniqueness_of :part_id, :scope => [:product_id]
end

Assuming I understand the problem, I think your confusion stems from
the fact that the level isn't part of what defines a Repair, its
simply an attribute of the Repair. It is really the Part and the
Product that you should be concerned with.
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-24 01:09
(Received via mailing list)
Andrew,

Your last paragraph helps clarify it a little bit. I think you are
correct in that I am chasing the wrong thing. I think that stems from
not fully understanding the scope option of validates_uniqueness_of.
The documentation for it is not clear.

Evan
C608d449f87ba87dd4a3f653afb304c1?d=identicon&s=25 Evan (Guest)
on 2009-02-25 19:25
(Received via mailing list)
Andrew,

Changing the scope of validates_uniqueness_of to product_id solved my
problem. Thank you.

Evan
This topic is locked and can not be replied to.