diff options
author | Jon Leighton <j@jonathanleighton.com> | 2010-10-19 14:14:06 +0100 |
---|---|---|
committer | Jon Leighton <j@jonathanleighton.com> | 2010-10-19 14:14:06 +0100 |
commit | 01838636c6136d9a649ace71db61bb7990f9bd82 (patch) | |
tree | 2f307e4dd6843588ab19f7d41615a04465560fff /activerecord | |
parent | 596cc3b2329a9cc4a30c95c157ce36b2d08975df (diff) | |
download | rails-01838636c6136d9a649ace71db61bb7990f9bd82.tar.gz rails-01838636c6136d9a649ace71db61bb7990f9bd82.tar.bz2 rails-01838636c6136d9a649ace71db61bb7990f9bd82.zip |
Support for :primary_key option on the source reflection of a through association, where the source is a has_one or has_many
Diffstat (limited to 'activerecord')
-rw-r--r-- | activerecord/lib/active_record/associations.rb | 10 | ||||
-rw-r--r-- | activerecord/lib/active_record/associations/through_association_scope.rb | 4 | ||||
-rw-r--r-- | activerecord/lib/active_record/reflection.rb | 8 | ||||
-rw-r--r-- | activerecord/test/cases/associations/has_many_through_associations_test.rb | 12 | ||||
-rw-r--r-- | activerecord/test/cases/associations/has_one_through_associations_test.rb | 12 | ||||
-rw-r--r-- | activerecord/test/fixtures/essays.yml | 2 | ||||
-rw-r--r-- | activerecord/test/fixtures/owners.yml | 1 | ||||
-rw-r--r-- | activerecord/test/models/author.rb | 2 | ||||
-rw-r--r-- | activerecord/test/models/essay.rb | 3 | ||||
-rw-r--r-- | activerecord/test/schema/schema.rb | 5 |
10 files changed, 41 insertions, 18 deletions
diff --git a/activerecord/lib/active_record/associations.rb b/activerecord/lib/active_record/associations.rb index 75e5eb8ee4..29f1c7b81d 100644 --- a/activerecord/lib/active_record/associations.rb +++ b/activerecord/lib/active_record/associations.rb @@ -2173,13 +2173,11 @@ module ActiveRecord if reflection.source_reflection.nil? case reflection.macro when :belongs_to - key = reflection.options[:primary_key] || - reflection.klass.primary_key + key = reflection.association_primary_key foreign_key = reflection.primary_key_name when :has_many, :has_one key = reflection.primary_key_name - foreign_key = reflection.options[:primary_key] || - reflection.active_record.primary_key + foreign_key = reflection.active_record_primary_key conditions << polymorphic_conditions(reflection, table) when :has_and_belongs_to_many @@ -2209,13 +2207,13 @@ module ActiveRecord else case reflection.source_reflection.macro when :belongs_to - key = reflection.klass.primary_key + key = reflection.source_reflection.association_primary_key foreign_key = reflection.source_reflection.primary_key_name conditions << source_type_conditions(reflection, foreign_table) when :has_many, :has_one key = reflection.source_reflection.primary_key_name - foreign_key = reflection.source_reflection.klass.primary_key + foreign_key = reflection.source_reflection.active_record_primary_key when :has_and_belongs_to_many table, join_table = table diff --git a/activerecord/lib/active_record/associations/through_association_scope.rb b/activerecord/lib/active_record/associations/through_association_scope.rb index 86ceb1a204..2b2229f01f 100644 --- a/activerecord/lib/active_record/associations/through_association_scope.rb +++ b/activerecord/lib/active_record/associations/through_association_scope.rb @@ -108,7 +108,7 @@ module ActiveRecord when :belongs_to joins << inner_join_sql( right_table_and_alias, - table_aliases[left], left.klass.primary_key, + table_aliases[left], left.source_reflection.association_primary_key, table_aliases[right], left.source_reflection.primary_key_name, source_type_conditions(left), reflection_conditions(right_index) @@ -124,7 +124,7 @@ module ActiveRecord joins << inner_join_sql( right_table_and_alias, table_aliases[left], left.source_reflection.primary_key_name, - right_table, right.klass.primary_key, + right_table, left.source_reflection.active_record_primary_key, polymorphic_conditions(left, left.source_reflection), reflection_conditions(right_index) ) diff --git a/activerecord/lib/active_record/reflection.rb b/activerecord/lib/active_record/reflection.rb index d8bd6c9873..a46597e497 100644 --- a/activerecord/lib/active_record/reflection.rb +++ b/activerecord/lib/active_record/reflection.rb @@ -217,6 +217,14 @@ module ActiveRecord def association_foreign_key @association_foreign_key ||= @options[:association_foreign_key] || class_name.foreign_key end + + def association_primary_key + @association_primary_key ||= @options[:primary_key] || klass.primary_key + end + + def active_record_primary_key + @active_record_primary_key ||= @options[:primary_key] || active_record.primary_key + end def counter_cache_column if options[:counter_cache] == true diff --git a/activerecord/test/cases/associations/has_many_through_associations_test.rb b/activerecord/test/cases/associations/has_many_through_associations_test.rb index 5a2e6b26aa..713c492f5e 100644 --- a/activerecord/test/cases/associations/has_many_through_associations_test.rb +++ b/activerecord/test/cases/associations/has_many_through_associations_test.rb @@ -19,12 +19,13 @@ require 'models/book' require 'models/subscription' require 'models/essay' require 'models/category' +require 'models/owner' class HasManyThroughAssociationsTest < ActiveRecord::TestCase fixtures :posts, :readers, :people, :comments, :authors, :owners, :pets, :toys, :jobs, :references, :companies, :subscribers, :books, :subscriptions, :developers, - :essays, :categories + :essays, :categories, :owners # Dummies to force column loads so query counts are clean. def setup @@ -453,14 +454,19 @@ class HasManyThroughAssociationsTest < ActiveRecord::TestCase assert author.comments.include?(comment) end - def test_has_many_through_polymorphic_with_primary_key_option_on_through_reflection + def test_has_many_through_polymorphic_with_primary_key_option assert_equal [categories(:general)], authors(:david).essay_categories authors = Author.joins(:essay_categories).where('categories.id' => categories(:general).id) assert_equal authors(:david), authors.first + + assert_equal [owners(:blackbeard)], authors(:david).essay_owners + + authors = Author.joins(:essay_owners).where("owners.name = 'blackbeard'") + assert_equal authors(:david), authors.first end - def test_has_many_through_with_primary_key_option_on_through_reflection + def test_has_many_through_with_primary_key_option assert_equal [categories(:general)], authors(:david).essay_categories_2 authors = Author.joins(:essay_categories_2).where('categories.id' => categories(:general).id) diff --git a/activerecord/test/cases/associations/has_one_through_associations_test.rb b/activerecord/test/cases/associations/has_one_through_associations_test.rb index 8805968869..39e14b4bfd 100644 --- a/activerecord/test/cases/associations/has_one_through_associations_test.rb +++ b/activerecord/test/cases/associations/has_one_through_associations_test.rb @@ -12,10 +12,11 @@ require 'models/speedometer' require 'models/category' require 'models/author' require 'models/essay' +require 'models/owner' class HasOneThroughAssociationsTest < ActiveRecord::TestCase fixtures :member_types, :members, :clubs, :memberships, :sponsors, :organizations, :minivans, - :dashboards, :speedometers, :categories, :authors, :essays + :dashboards, :speedometers, :categories, :authors, :essays, :owners def setup @member = members(:groucho) @@ -217,14 +218,19 @@ class HasOneThroughAssociationsTest < ActiveRecord::TestCase end end - def test_has_one_through_polymorphic_with_primary_key_option_on_through_reflection + def test_has_one_through_polymorphic_with_primary_key_option assert_equal categories(:general), authors(:david).essay_category authors = Author.joins(:essay_category).where('categories.id' => categories(:general).id) assert_equal authors(:david), authors.first + + assert_equal owners(:blackbeard), authors(:david).essay_owner + + authors = Author.joins(:essay_owner).where("owners.name = 'blackbeard'") + assert_equal authors(:david), authors.first end - def test_has_one_through_with_primary_key_option_on_through_reflection + def test_has_one_through_with_primary_key_option assert_equal categories(:general), authors(:david).essay_category_2 authors = Author.joins(:essay_category_2).where('categories.id' => categories(:general).id) diff --git a/activerecord/test/fixtures/essays.yml b/activerecord/test/fixtures/essays.yml index 8c96a469e6..9d15d82359 100644 --- a/activerecord/test/fixtures/essays.yml +++ b/activerecord/test/fixtures/essays.yml @@ -2,5 +2,5 @@ david_modest_proposal: name: A Modest Proposal writer_type: Author writer_id: David - category_id: 1 + category_id: General author_id: David diff --git a/activerecord/test/fixtures/owners.yml b/activerecord/test/fixtures/owners.yml index d5493a84b7..2d21ce433c 100644 --- a/activerecord/test/fixtures/owners.yml +++ b/activerecord/test/fixtures/owners.yml @@ -1,6 +1,7 @@ blackbeard: owner_id: 1 name: blackbeard + essay_id: A Modest Proposal ashley: owner_id: 2 diff --git a/activerecord/test/models/author.rb b/activerecord/test/models/author.rb index 1ba01d6b6b..53b3b80950 100644 --- a/activerecord/test/models/author.rb +++ b/activerecord/test/models/author.rb @@ -98,12 +98,14 @@ class Author < ActiveRecord::Base has_one :essay, :primary_key => :name, :as => :writer has_one :essay_category, :through => :essay, :source => :category + has_one :essay_owner, :through => :essay, :source => :owner has_one :essay_2, :primary_key => :name, :class_name => 'Essay', :foreign_key => :author_id has_one :essay_category_2, :through => :essay_2, :source => :category has_many :essays, :primary_key => :name, :as => :writer has_many :essay_categories, :through => :essays, :source => :category + has_many :essay_owners, :through => :essays, :source => :owner has_many :essays_2, :primary_key => :name, :class_name => 'Essay', :foreign_key => :author_id has_many :essay_categories_2, :through => :essays_2, :source => :category diff --git a/activerecord/test/models/essay.rb b/activerecord/test/models/essay.rb index 6a62042863..ec4b982b5b 100644 --- a/activerecord/test/models/essay.rb +++ b/activerecord/test/models/essay.rb @@ -1,4 +1,5 @@ class Essay < ActiveRecord::Base belongs_to :writer, :primary_key => :name, :polymorphic => true - belongs_to :category + belongs_to :category, :primary_key => :name + has_one :owner, :primary_key => :name end diff --git a/activerecord/test/schema/schema.rb b/activerecord/test/schema/schema.rb index b5bf9a7349..de3baaf4ab 100644 --- a/activerecord/test/schema/schema.rb +++ b/activerecord/test/schema/schema.rb @@ -214,8 +214,8 @@ ActiveRecord::Schema.define do t.string :name t.string :writer_id t.string :writer_type - t.integer :category_id - t.integer :author_id + t.string :category_id + t.string :author_id end create_table :events, :force => true do |t| @@ -369,6 +369,7 @@ ActiveRecord::Schema.define do t.string :name t.column :updated_at, :datetime t.column :happy_at, :datetime + t.string :essay_id end |