many to many :through problem

Hi all,

This should be a simple one, but I just don't see my mistake.

Migration1:
class CreateCompanyUsers < ActiveRecord::Migration
  def self.up
    create_table :employments, :id => false do |t|
      t.boolean :admin_role
      t.integer :company_id, :user_id
      t.timestamps
    end
  end

  def self.down
    drop_table :employments
  end
end

Migration2:
class CreateCompanies < ActiveRecord::Migration
  def self.up
    create_table :companies do |t|
      t.string :name, :subdomain
      t.boolean :admin_company
      t.timestamps
    end
    add_index :companies, :subdomain, :unique => true
    Company.create :name => "Default", :subdomain =>
"default", :admin_company => true
  end

  def self.down
    drop_table :companies
  end
end

Migration3:
class CreateUsers < ActiveRecord::Migration
  def self.up
    create_table "users", :force => true do |t|
      t.column :login, :string, :limit => 40
      t.column :name, :string, :limit =>
100, :default => '', :null => true
      t.column :email, :string, :limit => 100
      t.column :crypted_password, :string, :limit => 40
      t.column :salt, :string, :limit => 40
      t.column :created_at, :datetime
      t.column :updated_at, :datetime
      t.column :remember_token, :string, :limit => 40
      t.column :remember_token_expires_at, :datetime

    end
    add_index :users, :login, :unique => true
    User.create :login => "admin", :name => "Administrator
God", :email => 'admin@example.com', :password =>
'password', :password_confirmation => 'password'
  end

  def self.down
    drop_table "users"
  end
end

And my models:
class Employment < ActiveRecord::Base
  belongs_to :company
  belongs_to :user
end

class Company < ActiveRecord::Base
  has_many :employments
  has_many :users, :through => :employments
end

class User < ActiveRecord::Base
  # cut out restful_auth stuff
  has_many :employments
  has_many :companies, :through => :employments

When testing in script/console:
Loading development environment (Rails 2.1.0)

user=User.find :first

=> #<User id: 1, login: "admin", name: "Administrator God", email:
"admin@example.com", crypted_password:
"a5d460ff8566a5e0e11b6e591f1d8921a5726ea6", salt:
"872d3a4ebb1d9b2ef6be18938d36aea3bafe2646", created_at: "2008-08-24
15:53:40", updated_at: "2008-08-24 15:53:40", remember_token: nil,
remember_token_expires_at: nil>

company=Company.find :first

=> #<Company id: 1, name: "Default", subdomain: "default",
admin_company: true, created_at: "2008-08-24 15:53:40", updated_at:
"2008-08-24 15:53:40">

company.users << user

NameError: uninitialized constant Company::Employment
  from /Library/Ruby/Gems/1.8/gems/activesupport-2.1.0/lib/
active_support/dependencies.rb:492:in `const_missing'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
base.rb:1909:in `compute_type'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:129:in `send'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:129:in `klass'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:189:in `source_reflection'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:189:in `collect'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:189:in `source_reflection'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
reflection.rb:198:in `check_validity!'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
associations/has_many_through_association.rb:5:in `initialize'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
associations.rb:1128:in `new'
  from /Library/Ruby/Gems/1.8/gems/activerecord-2.1.0/lib/active_record/
associations.rb:1128:in `users'
  from (irb):3

So what did I do wrong, or what did I miss?

Kind regards,
Wijnand

Hi all,

This should be a simple one, but I just don't see my mistake.

Migration1:
class CreateCompanyUsers < ActiveRecord::Migration
def self.up
   create_table :employments, :id => false do |t|
     t.boolean :admin_role
     t.integer :company_id, :user_id
     t.timestamps
   end
end

With has many through, the join table is a model in its own right so
you must not skip :id like you are doing here.

def self.down
   drop_table :employments
end
end

And my models:
class Employment < ActiveRecord::Base
belongs_to :company
belongs_to :user
end

class Company < ActiveRecord::Base
has_many :employments
has_many :users, :through => :employments
end

class User < ActiveRecord::Base
# cut out restful_auth stuff
has_many :employments
has_many :companies, :through => :employments

When testing in script/console:
Loading development environment (Rails 2.1.0)

user=User.find :first

=> #<User id: 1, login: "admin", name: "Administrator God", email:
"admin@example.com", crypted_password:
"a5d460ff8566a5e0e11b6e591f1d8921a5726ea6", salt:
"872d3a4ebb1d9b2ef6be18938d36aea3bafe2646", created_at: "2008-08-24
15:53:40", updated_at: "2008-08-24 15:53:40", remember_token: nil,
remember_token_expires_at: nil>

company=Company.find :first

=> #<Company id: 1, name: "Default", subdomain: "default",
admin_company: true, created_at: "2008-08-24 15:53:40", updated_at:
"2008-08-24 15:53:40">

company.users << user

NameError: uninitialized constant Company::Employment

That's odd, it couldn't find your Employment class. Is it in
employment.rb ?

Fred