From a8b10a2a8d6f8d861453803264b9ef1b0cadbc6b Mon Sep 17 00:00:00 2001 From: Pratik Naik Date: Mon, 28 Dec 2009 01:08:34 +0530 Subject: Add relation#merge to merge two relations --- activerecord/lib/active_record/relation.rb | 22 +++++++++++++++++----- activerecord/test/cases/relations_test.rb | 8 ++++++++ 2 files changed, 25 insertions(+), 5 deletions(-) diff --git a/activerecord/lib/active_record/relation.rb b/activerecord/lib/active_record/relation.rb index d1f4dc2101..967e429fc3 100644 --- a/activerecord/lib/active_record/relation.rb +++ b/activerecord/lib/active_record/relation.rb @@ -12,6 +12,18 @@ module ActiveRecord @loaded = false end + def merge(r) + joins(r.relation.joins(r.relation)). + group(r.send(:group_clauses).join(', ')). + order(r.send(:order_clauses).join(', ')). + where(r.send(:where_clause)). + limit(r.taken). + offset(r.skipped). + select(r.send(:select_clauses).join(', ')) + end + + alias :& :merge + def preload(*associations) create_new_relation(@relation, @readonly, @associations_to_preload + Array.wrap(associations)) end @@ -25,7 +37,7 @@ module ActiveRecord end def select(selects) - create_new_relation(@relation.project(selects)) + selects.present? ? create_new_relation(@relation.project(selects)) : create_new_relation end # TODO : This is temporary. We need .from in Arel. @@ -37,11 +49,11 @@ module ActiveRecord end def group(groups) - create_new_relation(@relation.group(groups)) + groups.present? ? create_new_relation(@relation.group(groups)) : create_new_relation end def order(orders) - create_new_relation(@relation.order(orders)) + orders.present? ? create_new_relation(@relation.order(orders)) : create_new_relation end def reverse_order @@ -57,11 +69,11 @@ module ActiveRecord end def limit(limits) - create_new_relation(@relation.take(limits)) + limits.present? ? create_new_relation(@relation.take(limits)) : create_new_relation end def offset(offsets) - create_new_relation(@relation.skip(offsets)) + offsets.present? ? create_new_relation(@relation.skip(offsets)) : create_new_relation end def on(join) diff --git a/activerecord/test/cases/relations_test.rb b/activerecord/test/cases/relations_test.rb index 2ec8c0d3a2..c639fb978d 100644 --- a/activerecord/test/cases/relations_test.rb +++ b/activerecord/test/cases/relations_test.rb @@ -328,4 +328,12 @@ class RelationTest < ActiveRecord::TestCase assert davids.loaded? end + def test_relation_merging + devs = Developer.where("salary >= 80000") & Developer.limit(2) & Developer.order('id ASC').where("id < 3") + assert_equal [developers(:david), developers(:jamis)], devs.to_a + + dev_with_count = Developer.limit(1) & Developer.order('id DESC') & Developer.select('developers.*, count(id) id_count').group('id') + assert_equal [developers(:poor_jamis)], dev_with_count.to_a + assert_equal 1, dev_with_count.first.id_count.to_i + end end -- cgit v1.2.3