我有一个Category
has_many
的模型Pendencies
。我想创建一个范围,该范围按active = true
的倾向量对类别进行排序,而不排除active = false
。
到目前为止,我有:
scope :order_by_pendencies, -> { left_joins(:pendencies).group(:id).order('COUNT(pendencies.id) DESC')}
这将根据未决数目进行排序,但是我想按具有active = true
的未决进行排序。
另一种尝试是:
scope :order_by_pendencies, -> { left_joins(:pendencies).group(:id).where('pendencies.active = ?', true).order('COUNT(pendencies.id) DESC')}
这将按具有pendencies.active = true
的未决数目进行排序,但不包括pendencies.active = false
。
谢谢您的帮助。
答案 0 :(得分:1)
根据要求提供C#答案:
method() {
....OrderBy((category) => category.Count(pendencies.Where((pendency) => pendency.Active))
}
或直接使用SQL:
SELECT category.id, ..., ActivePendnecies
FROM (SELECT category.id, ..., count(pendency) ActivePendnecies
FROM category
LEFT JOIN pendency ON category.id = pendency.id AND pendnecy.Active = 1
GROUP BY category.id, ...) P
ORDER BY ActivePendnecies;
即使代码会将其丢弃,我们也必须在SQL中输出ActivePendnecies
,因为否则优化器将有权丢弃ORDER BY
。
答案 1 :(得分:1)
我猜您想按活动的待命数量进行排序,而不忽略没有活动的待命类别。
那将是这样的:
scope :order_by_pendencies, -> {
active_count_q = Pendency.
group(:category_id).
where(active: true).
select(:category_id, "COUNT(*) AS count")
joins("LEFT JOIN (#{active_count_q.to_sql}) AS ac ON ac.category_id = id").
order("ac.count DESC")
}
等效的SQL查询:
SELECT *, ac.count
FROM categories
LEFT JOIN (
SELECT category_id, COUNT(*) AS count
FROM pendencies
GROUP BY category_id
WHERE active = true
) AS ac ON ac.category_id = id
ORDER BY ac.count DESC
请注意,如果某个类别没有活动的未决要求,则计数将为null,并将被添加到列表的末尾。 可以添加一个类似的子查询,以根据未完成的总金额进行排序...
答案 2 :(得分:0)
目前,我开发了以下方法(它正在工作,但我认为这不是最好的方法):
require_once '../php-includes/connect.inc.php'; global $db; $assess_id=$_POST['assess_id']; $quest_ref=$_POST['quest_ref']; $email=$_POST['email']; $type=$_POST['type']; if($type=="file"){ $file=$_FILES["file"]; $fileName=$file["name"][0]; if(empty($fileName)){ echo "No File Selected"; return; } $fileType=$file["type"][0]; $fileData=$file["tmp_name"][0];}scope :order_by_pendencies, -> { scoped = Category.left_joins(:pendencies) .group(:id) .order('COUNT(pendencies.id) DESC') .where('pendencies.active = ?', true) all = Category.all (scoped + all).uniq}