我遇到了一個postgres查詢的奇怪問題。除了一個非常特定的場景外,查詢可以在多種情況下使用各種其他分組,總和等方式正常工作。Postgres:使用Case和Group By時需要的聚合函數,但僅在使用連接時
下面的代碼是從5個不同的表中計算行(忽略這個事實本身是愚蠢的,它是一個非常糟糕和令人討厭的數據庫結構),並根據CASE函數中返回的值對它們進行分組。它正常工作時,它是如下:
SELECT SUM(count) as count, status FROM
(SELECT count(fsp.id) as count, CASE WHEN fsp.stageonecompletetime = 0 THEN 'in-progress'
WHEN fsp.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN fsp.completedtime = 0 THEN 'awaiting-authorisation'
WHEN fsp.senttodate = 0 THEN 'awaiting-distribution'
WHEN fsp.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.fleet_solution_policy fsp WHERE TO_TIMESTAMP(fsp.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(fsp.createdtime) < '2016-10-03' GROUP BY status
UNION ALL
SELECT count(cba.id) as count, CASE WHEN cba.stageonecompletetime = 0 THEN 'in-progress'
WHEN cba.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN cba.completedtime = 0 THEN 'awaiting-authorisation'
WHEN cba.senttodate = 0 THEN 'awaiting-distribution'
WHEN cba.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.casing_buyback_agreement cba WHERE TO_TIMESTAMP(cba.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(cba.createdtime) < '2016-10-03' GROUP BY status
UNION ALL
SELECT count(ftp.id) as count, CASE WHEN ftp.stageonecompletetime = 0 THEN 'in-progress'
WHEN ftp.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN ftp.completedtime = 0 THEN 'awaiting-authorisation'
WHEN ftp.senttodate = 0 THEN 'awaiting-distribution'
WHEN ftp.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.fleet_tyre_policy ftp WHERE TO_TIMESTAMP(ftp.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(ftp.createdtime) < '2016-10-03' GROUP BY status
UNION ALL
SELECT count(ds.id) as count, CASE WHEN ds.stageonecompletetime = 0 THEN 'in-progress'
WHEN ds.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN ds.completedtime = 0 THEN 'awaiting-authorisation'
WHEN ds.senttodate = 0 THEN 'awaiting-distribution'
WHEN ds.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.dealer_sla ds WHERE TO_TIMESTAMP(ds.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(ds.createdtime) < '2016-10-03' GROUP BY status
UNION ALL
SELECT count(cg.id) as count, CASE WHEN cg.stageonecompletetime = 0 THEN 'in-progress'
WHEN cg.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN cg.completedtime = 0 THEN 'awaiting-authorisation'
WHEN cg.senttodate = 0 THEN 'awaiting-distribution'
WHEN cg.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.casing_grid cg WHERE TO_TIMESTAMP(cg.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(cg.createdtime) < '2016-10-03' GROUP BY status) allDocuments
GROUP BY status
但是,當我必須做在查詢連接,讓我通過用戶過濾結果,如下我得到一個惱人的錯誤:
SELECT SUM(count) as count, status FROM
(SELECT count(fsp.id) as count, CASE WHEN fsp.stageonecompletetime = 0 THEN 'in-progress'
WHEN fsp.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN fsp.completedtime = 0 THEN 'awaiting-authorisation'
WHEN fsp.senttodate = 0 THEN 'awaiting-distribution'
WHEN fsp.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.fleet_solution_policy fsp JOIN users u1 ON u1.id = fsp.user_id WHERE TO_TIMESTAMP(fsp.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(fsp.createdtime) < '2016-10-03' AND lower(u1.username) = 'Test' GROUP BY status
UNION ALL
SELECT count(cba.id) as count, CASE WHEN cba.stageonecompletetime = 0 THEN 'in-progress'
WHEN cba.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN cba.completedtime = 0 THEN 'awaiting-authorisation'
WHEN cba.senttodate = 0 THEN 'awaiting-distribution'
WHEN cba.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.casing_buyback_agreement cba JOIN users u4 ON u4.id = cba.user_id WHERE TO_TIMESTAMP(cba.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(cba.createdtime) < '2016-10-03' AND lower(u4.username) = 'Test' GROUP BY status
UNION ALL
SELECT count(ftp.id) as count, CASE WHEN ftp.stageonecompletetime = 0 THEN 'in-progress'
WHEN ftp.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN ftp.completedtime = 0 THEN 'awaiting-authorisation'
WHEN ftp.senttodate = 0 THEN 'awaiting-distribution'
WHEN ftp.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.fleet_tyre_policy ftp JOIN users u2 ON u2.id = ftp.user_id WHERE TO_TIMESTAMP(ftp.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(ftp.createdtime) < '2016-10-03' AND lower(u2.username) = 'Test' GROUP BY status
UNION ALL
SELECT count(ds.id) as count, CASE WHEN ds.stageonecompletetime = 0 THEN 'in-progress'
WHEN ds.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN ds.completedtime = 0 THEN 'awaiting-authorisation'
WHEN ds.senttodate = 0 THEN 'awaiting-distribution'
WHEN ds.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.dealer_sla ds JOIN users u3 ON u3.id = ds.user_id WHERE TO_TIMESTAMP(ds.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(ds.createdtime) < '2016-10-03' AND lower(u3.username) = 'Test' GROUP BY status
UNION ALL
SELECT count(cg.id) as count, CASE WHEN cg.stageonecompletetime = 0 THEN 'in-progress'
WHEN cg.stagetwocompletetime = 0 THEN 'awaiting-final-review'
WHEN cg.completedtime = 0 THEN 'awaiting-authorisation'
WHEN cg.senttodate = 0 THEN 'awaiting-distribution'
WHEN cg.senttodate > 0 AND superseded = 0 THEN 'completed'
ELSE 'archived' END AS status FROM fleet_documents.casing_grid cg JOIN users u5 ON u5.id = cg.user_id WHERE TO_TIMESTAMP(cg.createdtime) >= '2016-09-03' AND TO_TIMESTAMP(cg.createdtime) < '2016-10-03' AND lower(u5.username) = 'Test' GROUP BY status) allDocuments
GROUP BY status
我得到的錯誤如下:錯誤:列「fsp.stageonecompletetime」必須出現在GROUP BY子句中或用於聚合函數中。
現在,我不明白爲什麼我得到這個錯誤,只有當我與用戶表進行連接時才返回。
任何幫助將不勝感激。
不知道它是否會有所幫助,因爲我在Oracle SQL環境中工作,但在那裏您不能只將狀態放入組中,您必須在子句時刪除整個案例。你嘗試過嗎? –
你能解釋一下'TO_TIMESTAMP'在這裏做什麼嗎?創建的時間是否以字符串形式存儲?如果是這樣,以什麼格式?並不'降低(用戶名)='測試'看起來很有趣? –
嘿,是的,'測試'是我的錯(因爲我在提交這個問題時改變了實際的用戶名),我忘記了它更低。 – bigad1992