aboutsummaryrefslogtreecommitdiffstats
path: root/activerecord/test/cases/calculations_test.rb
diff options
context:
space:
mode:
authorRyuta Kamizono <kamipo@gmail.com>2017-05-28 09:29:49 +0900
committerRyuta Kamizono <kamipo@gmail.com>2018-06-07 09:58:20 +0900
commit63e35a1323b6a9b7ad7c90217116cdc99a45da1d (patch)
treee9f69cb46ac84e98ec9b725122723e2a14811835 /activerecord/test/cases/calculations_test.rb
parent5dc72378b783e924c5bf079ca660388ec4ac9224 (diff)
downloadrails-63e35a1323b6a9b7ad7c90217116cdc99a45da1d.tar.gz
rails-63e35a1323b6a9b7ad7c90217116cdc99a45da1d.tar.bz2
rails-63e35a1323b6a9b7ad7c90217116cdc99a45da1d.zip
Fix GROUP BY queries to apply LIMIT/OFFSET after aggregations
If `eager_loading` is true, `apply_join_dependency` force applies LIMIT/OFFSET before JOINs by `limited_ids_for` to keep parent records count. But for aggregation queries, LIMIT/OFFSET should be applied after aggregations the same as SQL semantics. And also, we could not replace SELECT list by `limited_ids_for` when a query has a GROUP BY clause. It had never been worked since it will causes generating invalid SQL for MySQL, PostgreSQL, and probably most backends. ``` % ARCONN=postgresql be ruby -w -Itest test/cases/calculations_test.rb -n test_group_by_with_limit Using postgresql Run options: -n test_group_by_with_limit --seed 20925 # Running: E Error: CalculationsTest#test_group_by_with_limit: ActiveRecord::StatementInvalid: PG::GroupingError: ERROR: column "posts.id" must appear in the GROUP BY clause or be used in an aggregate function LINE 1: SELECT DISTINCT "posts"."id", "posts"."type" AS alias_0 FRO... ^ : SELECT DISTINCT "posts"."id", "posts"."type" AS alias_0 FROM "posts" LEFT OUTER JOIN "comments" ON "comments"."post_id" = "posts"."id" GROUP BY "posts"."type" ORDER BY "posts"."type" ASC LIMIT $1 ``` Fixes #8103. Closes #27249.
Diffstat (limited to 'activerecord/test/cases/calculations_test.rb')
-rw-r--r--activerecord/test/cases/calculations_test.rb18
1 files changed, 18 insertions, 0 deletions
diff --git a/activerecord/test/cases/calculations_test.rb b/activerecord/test/cases/calculations_test.rb
index 080d2a54bc..6ceac59eec 100644
--- a/activerecord/test/cases/calculations_test.rb
+++ b/activerecord/test/cases/calculations_test.rb
@@ -705,6 +705,24 @@ class CalculationsTest < ActiveRecord::TestCase
assert_equal [], Topic.includes(:replies).order(:id).offset(5).pluck(:id)
end
+ def test_group_by_with_limit
+ expected = { "Post" => 8, "SpecialPost" => 1 }
+ actual = Post.includes(:comments).group(:type).order(:type).limit(2).count("comments.id")
+ assert_equal expected, actual
+ end
+
+ def test_group_by_with_offset
+ expected = { "SpecialPost" => 1, "StiPost" => 2 }
+ actual = Post.includes(:comments).group(:type).order(:type).offset(1).count("comments.id")
+ assert_equal expected, actual
+ end
+
+ def test_group_by_with_limit_and_offset
+ expected = { "SpecialPost" => 1 }
+ actual = Post.includes(:comments).group(:type).order(:type).offset(1).limit(1).count("comments.id")
+ assert_equal expected, actual
+ end
+
def test_pluck_not_auto_table_name_prefix_if_column_included
Company.create!(name: "test", contracts: [Contract.new(developer_id: 7)])
ids = Company.includes(:contracts).pluck(:developer_id)