我有兩個模型,分別命名為'customer'和'membership',客戶可以有很多會員資格。我想根據會員資格的創建日期和取消日期列對記錄進行排序。會員資格記錄應該是最新創建的記錄,取消的記錄不應該包括零值。例如,如果一個ID為1的客戶有兩條會員記錄,創建日期為2020年12月25日和2020年12月27日,取消日期為2021年1月1日和nil,那么這條記錄應該排在最下面,因為最新的會員資格仍然有效,因為其取消日期為nil,不應該出現在asc或desc的排序串列中。但是,如果一個客戶有2個會員資格,創建日期為2020年12月25日和2020年12月27日,取消日期為2000年1月1日和2000年1月5日,那么應該彈出一條記錄,取消日期為2000年1月5日。
Database Table - Customer
身份名稱
1 A
2 B
3 C
4 D
5 E
資料庫 Table - Membership
id customer_id created_at cancelled_at
1 1 1 jan 2000 5 jan 2000
2 1 2 jan 2000 nil
3 2 1 Dec 1999 2 Dec 1999 1999
4 5 15 一月 2000 16 一月 2000
5 5 17 12000 20 12000
那么 結果應該是(for asc 訂單 of cancelelled_at)
customer_id name cancelled at at
2 B 2 Dec 1999
5 E 20 Jan 2000
1 A nil
3 C nil
4 D nil
我的查詢沒有產生所需的輸出:
Customer.joins('LEFT JOIN memberships')
.where("memberships.cancel_at = (SELECT MAX(memberships.cancel_at) FROM memberships WHERE customers.id = memberships.customer_id)" )
.group('customers.id')
.order('MAX(memberships.created_at) ASC')
uj5u.com熱心網友回復:
解決這個問題的一個非常有效的方法是使用橫向連接:
SELECT c.*, latest_membership. cancelled_at AS cancelled_at
FROM customers c
LEFT JOIN LATERAL (
SELECT cancelled_at
FROM membersships m
WHERE m.customer_id = c.id --側面參考
ORDER BY m.created_at
LIMIT 1
) AS latest_membership ON TRUE >。
ORDER BY latest_membership.cancelled_at ASC NULLS LAST
這個花哨的新玩具可能有點難以理解,但它基本上就像一個foreach回圈 - 除了在SQL中。PostgreSQL將遍歷結果集中的每一行,并使用該行作為引數評估一個子查詢。很瘋狂的東西!
ActiveRecord不支持 "開箱即用 "的橫向連接,因為它是Postgres的特定功能,而且它的目標是成為多語言。但是你可以用SQL字串或Arel創建它們。
Customer
.select(
'customers.*'。
'latest_membership.cancelled_at AS cancelled_at')
)
.joins(<<~SQL)
LEFT JOIN LATERAL (
SELECT cancelled_at
FROM membersships m
WHERE m.customer_id = c.id --側面參考
ORDER created_at
LIMIT 1
) AS latest_membership ON TRUE )
SQL
.order('bearest_membership.cancelled_at ASC NULLS LAST')
轉載請註明出處,本文鏈接:https://www.uj5u.com/yidong/332302.html
標籤:
上一篇:我想在按下esc鍵時關閉模態。
