[英]Use distinct method with order on a many to many relation with ActiveRecord
我在 ActiveRecord 中定義了一個經典的多對多關系:
class Developer < ApplicationRecord
has_many :developers_code_reviews
has_many :code_reviews, through: :developers_code_reviews
end
class DevelopersCodeReview < ApplicationRecord
belongs_to :code_review
belongs_to :developer
end
class CodeReview < ApplicationRecord
has_many :developers_code_reviews
has_many :developers, through: :developers_code_reviews
end
我基本上想要一個按code_review.created_at
排序的Developer
數組,沒有雙打。
我的第一次嘗試是基本的: Developer.order('code_reviews.created_at': :asc)
觸發此錯誤: ActiveRecord::StatementInvalid: Mysql2::Error: Unknown column 'code_reviews.created' in 'order clause
。
經過幾次谷歌搜索后,我了解到 ActiveRecord 不會自動執行Developer.joins(:code_reviews).order('code_reviews.created_at': :asc)
因此我添加了它: Developer.joins(:code_reviews).order('code_reviews.created_at': :asc)
。 這個有效,但里面有雙打。 我需要一個開發人員在這個數組中只出現一次。
如果我嘗試在該查詢上創建一個不同的,ActiveRecord/MySQL 會抱怨沒有在 SELECT 中的列上執行ORDER BY
。 我怎么解決這個問題?
我用谷歌搜索了很多我找不到任何東西。
筆記
MYSQL 查詢可以使用雙打,如下所示:
SELECT `developers`.*
FROM `developers`
INNER JOIN `developers_code_reviews` ON `developers_code_reviews`.`developer_id` = `developers`.`id`
INNER JOIN `code_reviews` ON `code_reviews`.`id` = `developers_code_reviews`.`code_review_id`
ORDER BY `code_reviews`.`created_at` ASC
我想對開發人員有一個不同的看法。
由於這個關於 MySQL 子查詢的清晰示例,我找到了答案: http : //www.mysqltutorial.org/mysql-subquery/
通過這個例子,我明白我需要一個如下所示的子查詢:
SELECT *
FROM developers
LEFT OUTER JOIN (
SELECT developer_id, max(updated_at) max_updated_at
FROM developers_code_reviews
GROUP BY developer_id
) dcr
ON developers.id = dcr.developer_id
ORDER BY maxupdt
在我的情況下轉換為 ruby:
class DevelopersCodeReview < ApplicationRecord
belongs_to :code_review
belongs_to :developer
class << self
def developer_queue
select('developer_id, max(updated_at) max_updated_at').
group(:developer_id)
end
end
end
class Developer < ApplicationRecord
belongs_to :slack_workspace
belongs_to :project, optional: true
class << self
def queue
developer_queue = DevelopersCodeReview.developer_queue.to_sql
joins("LEFT OUTER JOIN (#{developer_queue}) dcr ON id = dcr.developer_id").
order(max_updated_at: :asc)
end
end
end
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.