Группируйте результаты запросов по месяцам и годам в postgresql с указанием суммы месяцев - PullRequest
1 голос
/ 16 марта 2020

На основании этого ответа от Бурака Арслана

SELECT date_trunc('month', txn_date) AS txn_month, sum(amount) as monthly_sum
    FROM yourtable
GROUP BY txn_month

Есть ли способ получить месяцы, которые не дают результатов в запросе?

Итак, скажем, у меня есть:

id      transDate     Product Qty
1234    04/12/2019    ABCD    2     
1245    04/05/2019    ABCD    1
1231    02/07/2019    ABCD    6

Мне также нужно, чтобы третий месяц возвращался со значением 0

MonthYear  totalQty
02/2019    6
03/2019    0
04/2019    3

Спасибо,

- --- ОБНОВЛЕНИЕ ---

Вот последний запрос, который получает последние 24 месяца с текущей даты. с готовым годом и месяцем для любых диаграмм.

Благодаря @ a_horse_with_no_name

SELECT 
    --ONLY USE THE NEXT LINE IF YOU NEED TO HAVE THE ID IN YOUR RESULT
    CASE WHEN t."ItemId" IS NULL THEN 10607 ELSE t."ItemId" END AS "ItemId",
    TO_CHAR(y."transactionDate", 'yyyy-mm-dd') AS txn_month,
    TO_CHAR(y."transactionDate", 'yyyy') AS "Year",
    TO_CHAR(y."transactionDate", 'Mon') AS "Month",
    -coalesce(SUM(t."transactionQty"),0) AS "TotalSold"
FROM generate_series(
    TO_CHAR(CURRENT_DATE - INTERVAL '24 month', 'yyyy-mm-01')::date , 
    TO_CHAR(CURRENT_DATE, 'yyyy-mm-01')::date, 
    INTERVAL '1 month') as y("transactionDate")
  LEFT JOIN "ItemTransactions" AS t 
         ON date_trunc('month', t."transactionDate") = y."transactionDate"
        AND t."ItemTransactionTypeId" = 1
        AND t."ItemId" = 10607
GROUP BY txn_month, "Year", "Month", t."ItemId"
ORDER BY txn_month ASC;

ПРИМЕР ВЫХОДА

ItemId  txn_month   Year    Month   TotalSold
10607   2018-03-01  2018    Mar     2
10607   2018-04-01  2018    Apr     0
10607   2018-05-01  2018    May     8
10607   2018-06-01  2018    Jun     12
10607   2018-07-01  2018    Jul     6
10607   2018-08-01  2018    Aug     4
10607   2018-09-01  2018    Sep     6
10607   2018-10-01  2018    Oct     8
10607   2018-11-01  2018    Nov     4
10607   2018-12-01  2018    Dec     0
10607   2019-01-01  2019    Jan     2
10607   2019-02-01  2019    Feb     3
10607   2019-03-01  2019    Mar     4
10607   2019-04-01  2019    Apr     1
10607   2019-05-01  2019    May     4
10607   2019-06-01  2019    Jun     3
10607   2019-07-01  2019    Jul     5
10607   2019-08-01  2019    Aug     6
10607   2019-09-01  2019    Sep     6
10607   2019-10-01  2019    Oct     6
10607   2019-11-01  2019    Nov     3
10607   2019-12-01  2019    Dec     0
10607   2020-01-01  2020    Jan     4
10607   2020-02-01  2020    Feb     2
10607   2020-03-01  2020    Mar     0

1 Ответ

2 голосов
/ 16 марта 2020

Оставить соединение со списком месяцев:

SELECT t.txn_month, 
       coalesce(sum(yt.amount),0) as monthly_sum
FROM generate_series(date '2019-02-01', date '2019-04-01', interval '1 month') as t(txn_month)
  left join yourtable yt on date_trunc('month', yt.transdate) = t.txn_month
GROUP BY t.txn_month

Онлайн пример


В вашем фактическом запросе вам нужно переместить условия из ГДЕ пункт к условию JOIN. Помещение их в предложение WHERE превращает внешнее соединение во внутреннее соединение:

SELECT t."ItemId",
       y."transactionDate" AS txn_month,
       -coalesce(SUM(t."transactionQty"),0) AS "TotalSold"
FROM generate_series(date '2018-01-01', date '2020-04-01', INTERVAL '1 month') as y("transactionDate")
  LEFT JOIN "ItemTransactions" AS t 
         ON date_trunc('month', t."transactionDate") = y."transactionDate"
        AND t."ItemTransactionTypeId" = 1
        AND t."ItemId" = 10606
-- this WHERE clause isn't really needed because of the date values provided to generate_series()
WHERE AND y."transactionDate" >= NOW() - INTERVAL '2 year'
GROUP BY txn_month, t."ItemId"
ORDER BY txn_month DESC;
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...