diff options
Diffstat (limited to 'activerecord/lib/active_record')
7 files changed, 35 insertions, 69 deletions
diff --git a/activerecord/lib/active_record/associations/builder/singular_association.rb b/activerecord/lib/active_record/associations/builder/singular_association.rb index 06a414b874..62d48d3a2c 100644 --- a/activerecord/lib/active_record/associations/builder/singular_association.rb +++ b/activerecord/lib/active_record/associations/builder/singular_association.rb @@ -13,6 +13,19 @@ module ActiveRecord::Associations::Builder private + def define_readers + super + name = self.name + + model.redefine_method("#{name}_loaded?") do + ActiveSupport::Deprecation.warn( + "Calling obj.#{name}_loaded? is deprecated. Please use " \ + "obj.association(:#{name}).loaded? instead." + ) + association(name).loaded? + end + end + def define_constructors name = self.name diff --git a/activerecord/lib/active_record/associations/collection_association.rb b/activerecord/lib/active_record/associations/collection_association.rb index 85a4f47b7d..deb2b9af32 100644 --- a/activerecord/lib/active_record/associations/collection_association.rb +++ b/activerecord/lib/active_record/associations/collection_association.rb @@ -4,7 +4,7 @@ module ActiveRecord module Associations # = Active Record Association Collection # - # AssociationCollection is an abstract class that provides common stuff to + # CollectionAssociation is an abstract class that provides common stuff to # ease the implementation of association proxies that represent # collections. See the class hierarchy in AssociationProxy. # @@ -99,7 +99,6 @@ module ActiveRecord else add_to_target(build_record(attributes, options)) do |record| yield(record) if block_given? - set_owner_attributes(record) end end end @@ -423,7 +422,10 @@ module ActiveRecord end def build_record(attributes, options) - reflection.build_association(scoped.scope_for_create.merge(attributes || {}), options) + record = reflection.build_association + record.assign_attributes(scoped.scope_for_create, :without_protection => true) + record.assign_attributes(attributes, options) + record end def delete_or_destroy(records, method) diff --git a/activerecord/lib/active_record/associations/has_one_association.rb b/activerecord/lib/active_record/associations/has_one_association.rb index 7134dc85c8..2f3a6e71f1 100644 --- a/activerecord/lib/active_record/associations/has_one_association.rb +++ b/activerecord/lib/active_record/associations/has_one_association.rb @@ -10,7 +10,7 @@ module ActiveRecord reflection.klass.transaction do if target && target != record - remove_target!(options[:dependent]) + remove_target!(options[:dependent]) unless target.destroyed? end if record diff --git a/activerecord/lib/active_record/associations/through_association.rb b/activerecord/lib/active_record/associations/through_association.rb index e6ab628719..53c5c3cedf 100644 --- a/activerecord/lib/active_record/associations/through_association.rb +++ b/activerecord/lib/active_record/associations/through_association.rb @@ -14,7 +14,10 @@ module ActiveRecord def target_scope scope = super chain[1..-1].each do |reflection| - scope = scope.merge(reflection.klass.scoped) + scope = scope.merge( + reflection.klass.scoped.with_default_scope. + except(:select, :create_with) + ) end scope end diff --git a/activerecord/lib/active_record/base.rb b/activerecord/lib/active_record/base.rb index d07f9365b3..e1bf2ccc8a 100644 --- a/activerecord/lib/active_record/base.rb +++ b/activerecord/lib/active_record/base.rb @@ -895,7 +895,7 @@ module ActiveRecord #:nodoc: # not use the default_scope: # # Post.unscoped { - # limit(10) # Fires "SELECT * FROM posts LIMIT 10" + # Post.limit(10) # Fires "SELECT * FROM posts LIMIT 10" # } # # It is recommended to use block form of unscoped because chaining unscoped with <tt>scope</tt> @@ -1652,11 +1652,10 @@ MSG return unless new_attributes.is_a?(Hash) - guard_protected_attributes ||= true - if guard_protected_attributes - assign_attributes(new_attributes) - else + if guard_protected_attributes == false assign_attributes(new_attributes, :without_protection => true) + else + assign_attributes(new_attributes) end end diff --git a/activerecord/lib/active_record/fixtures.rb b/activerecord/lib/active_record/fixtures.rb index 0e3ed7aac7..4aa6389a04 100644 --- a/activerecord/lib/active_record/fixtures.rb +++ b/activerecord/lib/active_record/fixtures.rb @@ -13,6 +13,7 @@ require 'active_support/core_ext/array/wrap' require 'active_support/core_ext/object/blank' require 'active_support/core_ext/logger' require 'active_support/ordered_hash' +require 'active_support/core_ext/module/deprecation' if defined? ActiveRecord class FixtureClassNotFound < ActiveRecord::ActiveRecordError #:nodoc: @@ -28,11 +29,9 @@ class FixturesFileNotFound < StandardError; end # # = Fixture formats # -# Fixtures come in 3 flavors: +# Fixtures come in 1 flavor: # # 1. YAML fixtures -# 2. CSV fixtures -# 3. Single-file fixtures # # == YAML fixtures # @@ -74,56 +73,6 @@ class FixturesFileNotFound < StandardError; end # parent_id: 1 # title: Child # -# == CSV fixtures -# -# Fixtures can also be kept in the Comma Separated Value (CSV) format. Akin to YAML fixtures, CSV fixtures are stored -# in a single file, but instead end with the <tt>.csv</tt> file extension -# (Rails example: <tt><your-rails-app>/test/fixtures/web_sites.csv</tt>). -# -# The format of this type of fixture file is much more compact than the others, but also a little harder to read by us -# humans. The first line of the CSV file is a comma-separated list of field names. The rest of the -# file is then comprised -# of the actual data (1 per line). Here's an example: -# -# id, name, url -# 1, Ruby On Rails, http://www.rubyonrails.org -# 2, Google, http://www.google.com -# -# Should you have a piece of data with a comma character in it, you can place double quotes around that value. If you -# need to use a double quote character, you must escape it with another double quote. -# -# Another unique attribute of the CSV fixture is that it has *no* fixture name like the other two formats. Instead, the -# fixture names are automatically generated by deriving the class name of the fixture file and adding an incrementing -# number to the end. In our example, the 1st fixture would be called "web_site_1" and the 2nd one would be called -# "web_site_2". -# -# Most databases and spreadsheets support exporting to CSV format, so this is a great format for you to choose if you -# have existing data somewhere already. -# -# == Single-file fixtures -# -# This type of fixture was the original format for Active Record that has since been deprecated in -# favor of the YAML and CSV formats. -# Fixtures for this format are created by placing text files in a sub-directory (with the name of the model) -# to the directory appointed by <tt>ActiveSupport::TestCase.fixture_path=(path)</tt> (this is automatically -# configured for Rails, so you can just put your files in <tt><your-rails-app>/test/fixtures/<your-model-name>/</tt> -- -# like <tt><your-rails-app>/test/fixtures/web_sites/</tt> for the WebSite model). -# -# Each text file placed in this directory represents a "record". Usually these types of fixtures are named without -# extensions, but if you are on a Windows machine, you might consider adding <tt>.txt</tt> as the extension. -# Here's what the above example might look like: -# -# web_sites/google -# web_sites/yahoo.txt -# web_sites/ruby-on-rails -# -# The file format of a standard fixture is simple. Each line is a property (or column in db speak) and has the syntax -# of "name => value". Here's an example of the ruby-on-rails fixture above: -# -# id => 1 -# name => Ruby on Rails -# url => http://www.rubyonrails.org -# # = Using fixtures in testcases # # Since fixtures are a testing construct, we use them in our unit and functional tests. There are two ways to use the @@ -176,7 +125,7 @@ class FixturesFileNotFound < StandardError; end # = Dynamic fixtures with ERB # # Some times you don't care about the content of the fixtures as much as you care about the volume. In these cases, you can -# mix ERB in with your YAML or CSV fixtures to create a bunch of fixtures for load testing, like: +# mix ERB in with your YAML fixtures to create a bunch of fixtures for load testing, like: # # <% for i in 1..1000 %> # fix_<%= i %>: @@ -752,6 +701,7 @@ module ActiveRecord fixtures["#{@class_name.to_s.underscore}_#{i+=1}"] = ActiveRecord::Fixture.new(data, model_class) end end + deprecate :read_csv_fixture_files def yaml_file_path "#{@fixture_path}.yml" diff --git a/activerecord/lib/active_record/relation/calculations.rb b/activerecord/lib/active_record/relation/calculations.rb index a8a52867ce..0fcae92d51 100644 --- a/activerecord/lib/active_record/relation/calculations.rb +++ b/activerecord/lib/active_record/relation/calculations.rb @@ -146,7 +146,7 @@ module ActiveRecord if options.except(:distinct).present? apply_finder_options(options.except(:distinct)).calculate(operation, column_name, :distinct => options[:distinct]) else - if eager_loading? || includes_values.present? + if eager_loading? || (includes_values.present? && references_eager_loaded_tables?) construct_relation_for_association_calculations.calculate(operation, column_name, options) else perform_calculation(operation, column_name, options) @@ -161,21 +161,20 @@ module ActiveRecord def perform_calculation(operation, column_name, options = {}) operation = operation.to_s.downcase - distinct = nil + distinct = options[:distinct] if operation == "count" column_name ||= (select_for_count || :all) unless arel.ast.grep(Arel::Nodes::OuterJoin).empty? distinct = true - column_name = primary_key if column_name == :all end + column_name = primary_key if column_name == :all && distinct + distinct = nil if column_name =~ /\s*DISTINCT\s+/i end - distinct = options[:distinct] || distinct - if @group_values.any? execute_grouped_calculation(operation, column_name, distinct) else |