Once I added this HABTM, one of my 'through' relationships, on a non-habtm model, seems to have brok

I’m a rails newb and have been Googling about this, but I’m still
stumped.

Not showing everything here, but basically it should be a pretty common
setup so I’m sure others know what I’m doing wrong.

  • A meter can belong to many meter_groups
  • A meter_group can have many meters.
  • A user can ‘subscribe’ to viewing a meter_group (Subscription) so he
    should be able to see the meters that are in that meter_group of the
    subscription (think subscribing to a topic in a forum.)

Initially I was only allowing a single meter to belong to only one
meter_group and the following test and relationship of a Subscription
worked
fine:

class Subscription < ActiveRecord::Base
belongs_to :user, :foreign_key => “user_id”
belongs_to :meter_group, :foreign_key => “meter_group_id”
has_many :meters, :through => :meter_group
end

test “group1 and group2 belong to rachel” do
user = User.find_by_login(“rachel”)
subscriptions = Subscription.find_all_by_user_id(user.id)
subscriptions.each do |s|
meters = s.meters
meters.each do |m|
puts “meter = #{p m}”
end
end
end

However now things are not working since I created some HABTM
relationships
for meter_group and meters. I end up with the following error:

ActiveRecord::HasManyThroughSourceAssociationMacroError: Invalid source
reflection macro :has_and_belongs_to_many for has_many :meters, :through
=>
:meter_group. Use :source to specify the source reflection.

Here are some of the other relevant tables and migrations (stripped of a
few
non-related fields):

class MeterGroup < ActiveRecord::Base
belongs_to :user, :foreign_key => “user_id”
has_and_belongs_to_many :meters
end

class Meter < ActiveRecord::Base
has_and_belongs_to_many :meter_groups
belongs_to :user, :foreign_key => “user_id”
end

#Migrations (removed some cols and drop section)

class CreateMeterGroups < ActiveRecord::Migration
def self.up
create_table :meter_groups do |t|
t.string :name
t.string :description
t.integer :user_id

  t.timestamps
end

end
end

class CreateMeters < ActiveRecord::Migration
def self.up
create_table :meters do |t|
t.integer :meter_type_id
t.integer :scale_id
t.integer :user_id
t.string :name
t.string :description

  t.timestamps
end

end
end

class CreateMetersMeterGroups < ActiveRecord::Migration
def self.up
create_table :meter_groups_meters, :id => false do |t|
t.integer :meter_id
t.integer :meter_group_id

  t.timestamps
end

end
end

class CreateSubscriptions < ActiveRecord::Migration
def self.up
create_table :subscriptions do |t|
t.integer :user_id
t.integer :meter_group_id

  t.timestamps
end

end
end

On Wed, Aug 18, 2010 at 3:04 PM, Rick R [email protected] wrote:

test “group1 and group2 belong to rachel” do

As a side note, there isn’t an issue if I try to get meters directly
from
the meter_group. For example in the above test it works if changed to:

test “group1 and group2 belong to rachel” do
user = User.find_by_login(“rachel”)
subscriptions = Subscription.find_all_by_user_id(user.id)
subscriptions.each do |s|
meter_group = s.meter_group
meters = meter_group.meters

meters.each do |m|
puts “meter = #{p m}”
end
end
end

class MeterGroup < ActiveRecord::Base

end
t.timestamps
t.timestamps
t.timestamps
end
end
end


Rick R

I would start by getting rid of the :foreign_key specifications
unless you are doing something non standard.

oh you need to add the has_many for the join table

has_many :meter_goup
has_many :meters, :through => :meter_group

On Wed, Aug 18, 2010 at 3:30 PM, Me [email protected] wrote:

I would start by getting rid of the :foreign_key specifications
unless you are doing something non standard.

Ok, thanks. I removed them. (Didn’t fix the issue but does look a lot
cleaner.)

  • A user can ‘subscribe’ to viewing a meter_group (Subscription) so he
    belongs_to :meter_group, :foreign_key => “meter_group_id”
    end
    *meter_group = s.meter_group

a

end
t.timestamps
t.string :name
t.integer :meter_id
t.integer :user_id

You received this message because you are subscribed to the Google G.
“Ruby on Rails: Talk” group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to
[email protected][email protected]
.
For more options, visit this group at
http://groups.google.com/group/rubyonrails-talk?hl=en.


Rick R

sorry I misread your tables. The has_many :through is looking for a
join table with ids for both sides which is the cause of the error,
same kind of table as a HABTM join table.

class Author < ActiveRecord::Base
has_many :authorships
has_many :books, :through => :authorships
end

class Authorship < ActiveRecord::Base
belongs_to :author
belongs_to :book
end

On Wed, Aug 18, 2010 at 4:00 PM, Me [email protected] wrote:

oh you need to add the has_many for the join table

has_many :meter_goup
has_many :meters, :through => :meter_group

I take it you mean on the Subscription table? which currently looks
like:

class Subscription < ActiveRecord::Base
belongs_to :user
belongs_to :meter_group
has_many :meters, :through => :meter_group
end

But a Subscription doesn’t have many mete groups, a subscription can
only be
tied to a single meterGroup and has a fk to the meter_group table.

Or are you saying for the other join table “meter_groups_meters” I need
to
make a MeterGroupsMeter model object and add the relationships you
described?

For reference The other relevant tables are:

class Meter < ActiveRecord::Base
has_and_belongs_to_many :meter_groups
belongs_to :user
end

class MeterGroup < ActiveRecord::Base
belongs_to :user
has_and_belongs_to_many :meters
end