diff options
author | Aaron Patterson <aaron.patterson@gmail.com> | 2011-12-30 10:02:19 -0800 |
---|---|---|
committer | Aaron Patterson <aaron.patterson@gmail.com> | 2011-12-30 10:02:19 -0800 |
commit | 116b9edf95ccaa59feb6afe67b126ad3da526b92 (patch) | |
tree | 8c9bcdadd3e2a6315e165bf2a1582afa5898236c /activerecord | |
parent | 4b99732552f997c846b186f9e2d3439ff75baff0 (diff) | |
parent | b52d9d0ff585f3131e26317542df2971a667d319 (diff) | |
download | rails-116b9edf95ccaa59feb6afe67b126ad3da526b92.tar.gz rails-116b9edf95ccaa59feb6afe67b126ad3da526b92.tar.bz2 rails-116b9edf95ccaa59feb6afe67b126ad3da526b92.zip |
Merge pull request #4224 from alexeymuranov/my-fix-for-fixture-tables
Fix #2572 and define fixture table name in the associated model
Diffstat (limited to 'activerecord')
-rw-r--r-- | activerecord/lib/active_record/fixtures.rb | 69 | ||||
-rw-r--r-- | activerecord/test/cases/fixtures_test.rb | 33 | ||||
-rw-r--r-- | activerecord/test/fixtures/admin/randomly_named_a9.yml | 7 | ||||
-rw-r--r-- | activerecord/test/fixtures/admin/randomly_named_b0.yml | 7 | ||||
-rw-r--r-- | activerecord/test/fixtures/randomly_named_a9.yml | 7 | ||||
-rw-r--r-- | activerecord/test/models/admin/randomly_named_c1.rb | 3 | ||||
-rw-r--r-- | activerecord/test/models/randomly_named_c1.rb | 3 | ||||
-rw-r--r-- | activerecord/test/schema/schema.rb | 5 |
8 files changed, 109 insertions, 25 deletions
diff --git a/activerecord/lib/active_record/fixtures.rb b/activerecord/lib/active_record/fixtures.rb index deffc7cec5..c59c00f424 100644 --- a/activerecord/lib/active_record/fixtures.rb +++ b/activerecord/lib/active_record/fixtures.rb @@ -388,10 +388,15 @@ module ActiveRecord @@all_cached_fixtures = Hash.new { |h,k| h[k] = {} } - def self.find_table_name(table_name) # :nodoc: + def self.default_fixture_model_name(fixture_name) # :nodoc: ActiveRecord::Base.pluralize_table_names ? - table_name.to_s.singularize.camelize : - table_name.to_s.camelize + fixture_name.singularize.camelize : + fixture_name.camelize + end + + def self.default_fixture_table_name(fixture_name) # :nodoc: + "#{ActiveRecord::Base.table_name_prefix}"\ + "#{fixture_name.tr('/', '_')}#{ActiveRecord::Base.table_name_suffix}".to_sym end def self.reset_cache @@ -441,9 +446,6 @@ module ActiveRecord def self.create_fixtures(fixtures_directory, table_names, class_names = {}) table_names = [table_names].flatten.map { |n| n.to_s } - table_names.each { |n| - class_names[n.tr('/', '_').to_sym] = n.classify if n.include?('/') - } # FIXME: Apparently JK uses this. connection = block_given? ? yield : ActiveRecord::Base.connection @@ -457,12 +459,12 @@ module ActiveRecord fixtures_map = {} fixture_files = files_to_read.map do |path| - table_name = path.tr '/', '_' + fixture_name = path - fixtures_map[path] = ActiveRecord::Fixtures.new( + fixtures_map[fixture_name] = new( # ActiveRecord::Fixtures.new connection, - table_name, - class_names[table_name.to_sym] || table_name.classify, + fixture_name, + class_names[fixture_name] || default_fixture_model_name(fixture_name), ::File.join(fixtures_directory, path)) end @@ -506,25 +508,27 @@ module ActiveRecord attr_reader :table_name, :name, :fixtures, :model_class - def initialize(connection, table_name, class_name, fixture_path) + def initialize(connection, fixture_name, class_name, fixture_path) @connection = connection - @table_name = table_name @fixture_path = fixture_path - @name = table_name # preserve fixture base name + @name = fixture_name @class_name = class_name @fixtures = ActiveSupport::OrderedHash.new - @table_name = "#{ActiveRecord::Base.table_name_prefix}#{@table_name}#{ActiveRecord::Base.table_name_suffix}" # Should be an AR::Base type class if class_name.is_a?(Class) - @table_name = class_name.table_name - @connection = class_name.connection - @model_class = class_name + @model_class = class_name else - @model_class = class_name.constantize rescue nil + @model_class = class_name.constantize rescue nil end + @connection = model_class.connection if model_class && model_class.respond_to?(:connection) + + @table_name = ( model_class.respond_to?(:table_name) ? + model_class.table_name : + self.class.default_fixture_table_name(fixture_name) ) + read_fixture_files end @@ -723,14 +727,29 @@ module ActiveRecord self.use_instantiated_fixtures = false self.pre_loaded_fixtures = false - self.fixture_class_names = Hash.new do |h, table_name| - h[table_name] = ActiveRecord::Fixtures.find_table_name(table_name) + self.fixture_class_names = Hash.new do |h, fixture_name| + h[fixture_name] = ActiveRecord::Fixtures.default_fixture_model_name(fixture_name) end end module ClassMethods + # Sets the model class for a fixture when the class name cannot be inferred from the fixture name. + # + # Examples: + # + # set_fixture_class :some_fixture => SomeModel, + # 'namespaced/fixture' => Another::Model + # + # The keys must be the fixture names, that coincide with the short paths to the fixture files. + #-- + # It is also possible to pass the class name instead of the class: + # set_fixture_class 'some_fixture' => 'SomeModel' + # I think this option is redundant, i propose to deprecate it. + # Isn't it easier to always pass the class itself? + # (2011-12-20 alexeymuranov) + #++ def set_fixture_class(class_names = {}) - self.fixture_class_names = self.fixture_class_names.merge(class_names) + self.fixture_class_names = self.fixture_class_names.merge(class_names.stringify_keys) end def fixtures(*fixture_names) @@ -770,9 +789,9 @@ module ActiveRecord fixture_names = Array.wrap(fixture_names || fixture_table_names) methods = Module.new do fixture_names.each do |fixture_name| - fixture_name = fixture_name.to_s.tr('./', '_') + accessor_name = fixture_name.tr('/', '_').to_sym - define_method(fixture_name) do |*fixtures| + define_method(accessor_name) do |*fixtures| force_reload = fixtures.pop if fixtures.last == true || fixtures.last == :reload @fixture_cache[fixture_name] ||= {} @@ -785,13 +804,13 @@ module ActiveRecord @fixture_cache[fixture_name][fixture] ||= @loaded_fixtures[fixture_name][fixture.to_s].find end else - raise StandardError, "No fixture with name '#{fixture}' found for table '#{fixture_name}'" + raise StandardError, "No entry named '#{fixture}' found for fixture collection '#{fixture_name}'" end end instances.size == 1 ? instances.first : instances end - private fixture_name + private accessor_name end end include methods diff --git a/activerecord/test/cases/fixtures_test.rb b/activerecord/test/cases/fixtures_test.rb index ba09df4b7d..859bb7992b 100644 --- a/activerecord/test/cases/fixtures_test.rb +++ b/activerecord/test/cases/fixtures_test.rb @@ -1,6 +1,7 @@ require 'cases/helper' require 'models/admin' require 'models/admin/account' +require 'models/admin/randomly_named_c1' require 'models/admin/user' require 'models/binary' require 'models/book' @@ -14,6 +15,7 @@ require 'models/matey' require 'models/parrot' require 'models/pirate' require 'models/post' +require 'models/randomly_named_c1' require 'models/reply' require 'models/ship' require 'models/task' @@ -745,3 +747,34 @@ class FixtureLoadingTest < ActiveRecord::TestCase ActiveRecord::TestCase.try_to_load_dependency(:works_out_fine) end end + +class CustomNameForFixtureOrModelTest < ActiveRecord::TestCase + ActiveRecord::Fixtures.reset_cache + + set_fixture_class :randomly_named_a9 => + ClassNameThatDoesNotFollowCONVENTIONS, + :'admin/randomly_named_a9' => + Admin::ClassNameThatDoesNotFollowCONVENTIONS, + 'admin/randomly_named_b0' => + Admin::ClassNameThatDoesNotFollowCONVENTIONS + + fixtures :randomly_named_a9, 'admin/randomly_named_a9', + :'admin/randomly_named_b0' + + def test_named_accessor_for_randomly_named_fixture_and_class + assert_kind_of ClassNameThatDoesNotFollowCONVENTIONS, + randomly_named_a9(:first_instance) + end + + def test_named_accessor_for_randomly_named_namespaced_fixture_and_class + assert_kind_of Admin::ClassNameThatDoesNotFollowCONVENTIONS, + admin_randomly_named_a9(:first_instance) + assert_kind_of Admin::ClassNameThatDoesNotFollowCONVENTIONS, + admin_randomly_named_b0(:second_instance) + end + + def test_table_name_is_defined_in_the_model + assert_equal :randomly_named_table, ActiveRecord::Fixtures::all_loaded_fixtures["admin/randomly_named_a9"].table_name + assert_equal :randomly_named_table, Admin::ClassNameThatDoesNotFollowCONVENTIONS.table_name + end +end diff --git a/activerecord/test/fixtures/admin/randomly_named_a9.yml b/activerecord/test/fixtures/admin/randomly_named_a9.yml new file mode 100644 index 0000000000..bc51c83112 --- /dev/null +++ b/activerecord/test/fixtures/admin/randomly_named_a9.yml @@ -0,0 +1,7 @@ +first_instance:
+ some_attribute: AAA
+ another_attribute: 000
+
+second_instance:
+ some_attribute: BBB
+ another_attribute: 999
diff --git a/activerecord/test/fixtures/admin/randomly_named_b0.yml b/activerecord/test/fixtures/admin/randomly_named_b0.yml new file mode 100644 index 0000000000..bc51c83112 --- /dev/null +++ b/activerecord/test/fixtures/admin/randomly_named_b0.yml @@ -0,0 +1,7 @@ +first_instance:
+ some_attribute: AAA
+ another_attribute: 000
+
+second_instance:
+ some_attribute: BBB
+ another_attribute: 999
diff --git a/activerecord/test/fixtures/randomly_named_a9.yml b/activerecord/test/fixtures/randomly_named_a9.yml new file mode 100644 index 0000000000..bc51c83112 --- /dev/null +++ b/activerecord/test/fixtures/randomly_named_a9.yml @@ -0,0 +1,7 @@ +first_instance:
+ some_attribute: AAA
+ another_attribute: 000
+
+second_instance:
+ some_attribute: BBB
+ another_attribute: 999
diff --git a/activerecord/test/models/admin/randomly_named_c1.rb b/activerecord/test/models/admin/randomly_named_c1.rb new file mode 100644 index 0000000000..2f81d5b831 --- /dev/null +++ b/activerecord/test/models/admin/randomly_named_c1.rb @@ -0,0 +1,3 @@ +class Admin::ClassNameThatDoesNotFollowCONVENTIONS < ActiveRecord::Base
+ self.table_name = :randomly_named_table
+end
diff --git a/activerecord/test/models/randomly_named_c1.rb b/activerecord/test/models/randomly_named_c1.rb new file mode 100644 index 0000000000..18a86c4989 --- /dev/null +++ b/activerecord/test/models/randomly_named_c1.rb @@ -0,0 +1,3 @@ +class ClassNameThatDoesNotFollowCONVENTIONS < ActiveRecord::Base
+ self.table_name = :randomly_named_table
+end
diff --git a/activerecord/test/schema/schema.rb b/activerecord/test/schema/schema.rb index b06175cd3f..b8f34bb739 100644 --- a/activerecord/test/schema/schema.rb +++ b/activerecord/test/schema/schema.rb @@ -505,6 +505,11 @@ ActiveRecord::Schema.define do t.string :type end + create_table :randomly_named_table, :force => true do |t| + t.string :some_attribute + t.integer :another_attribute + end + create_table :ratings, :force => true do |t| t.integer :comment_id t.integer :value |