我需要帮助将此SQL转换为ActiveRecord查询。
SELECT
MAX(total_sales.start_date) AS maximum_start_date,
customers.external_id, product_categories.external_id AS product_category_id
FROM
total_sales
INNER JOIN
customers
ON
customers.id = total_sales.customer_id
LEFT JOIN
product_categories
ON
product_categories.id = total_sales.product_category_id
WHERE
(customers.organization_id = 1)
GROUP BY
customers.external_id,
product_categories.external_id
我试过
TotalSales.joins(:customer).includes(:product_category).
where("customers.organization_id = ?", 1).
group("customers.external_id, product_categories.external_id").
maximum(:start_date)
它几乎生成了我想要的查询。这就是它产生的结果:
SELECT
MAX("total_sales"."start_date") AS maximum_start_date,
customers.external_id, product_categories.external_id AS customers_external_id_product_categories_external_id
FROM
"total_sales"
INNER JOIN "customers" ON
"customers"."id" = "total_sales"."customer_id"
LEFT OUTER JOIN "product_categories" ON
"product_categories"."id" = "total_sales"."product_category_id"
WHERE
(customers.organization_id = 1)
GROUP BY
customers.external_id, product_categories.external_id
但这会在Rails上返回:
=> {"DIA"=>Wed, 01 Jan 2014, "MES"=>Wed, 01 Jan 2014, nil=>Wed, 01 Jan 2014}
如果我在DB控制台上运行该查询,则返回
"2014-01-01";"CLIENTE.1";"DIA"
"2014-01-01";"CLIENTE.1";"MES"
"2014-01-01";"CLIENTE.1";""
"2014-01-01";"CLIENTE.10";"DIA"
"2014-01-01";"CLIENTE.10";"MES"
"2014-01-01";"CLIENTE.10";""
"2014-01-01";"CLIENTE.100";"DIA"
"2014-01-01";"CLIENTE.100";"MES"
...
这就是我想要的。在DB控制台上它可以工作,但在Rails上却没有。 :(
答案 0 :(得分:0)
这似乎是Rails中的一个错误。如果您使用std::make_pair({a,c,e}, {g,f,e})
来改变您的行:
group
为:
group("customers.external_id, product_categories.external_id").
它有效。 NB!你应该使用两个用逗号分隔的字符串。
当Rails从SQL呈现结果时,它必须认为该组只有一个字段(如果它在一个字符串中),尽管它构建了正确的SQL查询。
您将获得此结果:
group("customers.external_id", "product_categories.external_id").
我假设您知道如何使用它。
一点提示,使用=> {["CLIENTE.1", "DIA"]=>Wed, 01 Jan 2014, ["CLIENTE.1", "MES"]=>Wed, 01 Jan 2014,
["CLIENTE.1", nil]=>Wed, 01 Jan 2014, ["CLIENTE.10", "DIA"]=>Wed, 01 Jan 2014,
["CLIENTE.10", "MES"]=>Wed, 01 Jan 2014, ["CLIENTE.10", nil]=>Wed, 01 Jan 2014, ...}
来避免“硬代码”表名,你可以使用这个:
Arel
答案 1 :(得分:0)
包括!= LEFT JOIN
如果您希望查询以某种方式依赖于includes(othertable)
,则不应使用othertable
,因为includes
它具有不同的语义。
对于包含你只是说ActiveRecord,你打算尽快从对象中获取对象,所以它应该优化它。但它是面向对象的。您的示例中会得到TotalSales
个对象。
join是一个关系数据库的东西,可以混合表的列。我们通常不会在对象世界中做这样的事情。这就是为什么这经常变得困难。
如果你需要左连接,你需要告诉rails。根据rails指南,您需要使用SQL片段。
TotalSales.joins('LEFT OUTER JOIN product_categories ON product_categories.id = total_sales.product_category_id')
...