1
0
Fork 0
mirror of https://github.com/rails/rails.git synced 2022-11-09 12:12:34 -05:00

Move Relation calculation methods to a separate module

This commit is contained in:
Pratik Naik 2009-12-28 19:12:15 +05:30
parent 8f5d9eb0e2
commit e8ca22d129
3 changed files with 54 additions and 45 deletions

View file

@ -48,6 +48,7 @@ module ActiveRecord
autoload :Attributes
autoload :AutosaveAssociation
autoload :Relation
autoload :RelationalCalculations
autoload :Base
autoload :Batches
autoload :Calculations

View file

@ -4,6 +4,7 @@ module ActiveRecord
delegate :length, :collect, :map, :each, :all?, :to => :to_a
attr_reader :relation, :klass, :associations_to_preload, :eager_load_associations
include RelationalCalculations
def initialize(klass, relation, readonly = false, preload = [], eager_load = [])
@klass, @relation = klass, relation
@readonly = readonly
@ -204,20 +205,6 @@ module ActiveRecord
end
end
def count(*args)
column_name, options = construct_count_options_from_args(*args)
distinct = options[:distinct] ? true : false
column = if @klass.column_names.include?(column_name.to_s)
Arel::Attribute.new(@relation.table, column_name)
else
Arel::SqlLiteral.new(column_name == :all ? "*" : column_name.to_s)
end
relation = select(column.count(distinct))
@klass.connection.select_value(relation.to_sql).to_i
end
def destroy_all
to_a.each {|object| object.destroy}
reset
@ -351,36 +338,5 @@ module ActiveRecord
}.join(',')
end
def construct_count_options_from_args(*args)
options = {}
column_name = :all
# We need to handle
# count()
# count(:column_name=:all)
# count(options={})
# count(column_name=:all, options={})
# selects specified by scopes
# TODO : relation.projections only works when .select() was last in the chain. Fix it!
case args.size
when 0
column_name = @relation.send(:select_clauses).join(', ') if @relation.respond_to?(:projections) && @relation.projections.present?
when 1
if args[0].is_a?(Hash)
column_name = @relation.send(:select_clauses).join(', ') if @relation.respond_to?(:projections) && @relation.projections.present?
options = args[0]
else
column_name = args[0]
end
when 2
column_name, options = args
else
raise ArgumentError, "Unexpected parameters passed to count(): #{args.inspect}"
end
[column_name || :all, options]
end
end
end

View file

@ -0,0 +1,52 @@
module ActiveRecord
module RelationalCalculations
def count(*args)
column_name, options = construct_count_options_from_args(*args)
distinct = options[:distinct] ? true : false
column = if @klass.column_names.include?(column_name.to_s)
Arel::Attribute.new(@relation.table, column_name)
else
Arel::SqlLiteral.new(column_name == :all ? "*" : column_name.to_s)
end
relation = select(column.count(distinct))
@klass.connection.select_value(relation.to_sql).to_i
end
private
def construct_count_options_from_args(*args)
options = {}
column_name = :all
# We need to handle
# count()
# count(:column_name=:all)
# count(options={})
# count(column_name=:all, options={})
# selects specified by scopes
# TODO : relation.projections only works when .select() was last in the chain. Fix it!
case args.size
when 0
column_name = @relation.send(:select_clauses).join(', ') if @relation.respond_to?(:projections) && @relation.projections.present?
when 1
if args[0].is_a?(Hash)
column_name = @relation.send(:select_clauses).join(', ') if @relation.respond_to?(:projections) && @relation.projections.present?
options = args[0]
else
column_name = args[0]
end
when 2
column_name, options = args
else
raise ArgumentError, "Unexpected parameters passed to count(): #{args.inspect}"
end
[column_name || :all, options]
end
end
end