Расчет остаточного запаса в PostgreSQL - PullRequest
0 голосов
/ 18 июня 2020

Я пытаюсь вычесть количество внутри продуктов, если продукты добавлены в счет-фактуру. Чтобы выяснить, сколько товаров доступно на складе.

  SELECT
    w_prod.prod_article_pvt_uuid
    ,sum(coalesce(w_prod.quantity, 0) - coalesce(s_item.quantity, 0)) as available
  FROM products w_prod
  LEFT JOIN items s_item ON s_item.whse_prod_pvt_uuid = w_prod.whse_prod_pvt_uuid
  LEFT JOIN documents s_doc ON s_item.sale_doc_pvt_uuid = s_doc.sale_doc_pvt_uuid
  GROUP BY w_prod.prod_article_pvt_uuid

Ожидаемый результат выглядит следующим образом:

+--------------------------------------+-----------+
| prod_article_pvt_uuid                | available |
+--------------------------------------+-----------+
| 470fda1a-54ab-11ea-a21d-de2e50192004 | 5         |
| 9a59a5ba-5ad8-11ea-a21d-de2e50192004 | 10        |
| c2c98260-5482-11ea-a21d-de2e50192004 | 9         |
+--------------------------------------+-----------+

Однако в приведенном выше запросе есть проблемы с c2c98260-5482-11ea-a21d-de2e50192004 и возвращается 21 вместо этого.

Взгляните на SQLFiddle: http://sqlfiddle.com/#! 17 / 9ae0f4 / 1

Любые идеи, что я делаю неправильно и как чтобы исправить?


Таблицы:

create table products
(
    whse_prod_pvt_uuid uuid default uuid_generate_v1() not null
            primary key,
    t timestamp with time zone default CURRENT_TIMESTAMP(6),
    prod_article_pvt_uuid uuid not null,
    quantity numeric(16,6) default 1
);

create table documents
(
    sale_doc_pvt_uuid uuid default uuid_generate_v1() not null
            primary key,
    t timestamp with time zone default CURRENT_TIMESTAMP(6)
);

create table items
(
    sale_item_pvt_uuid uuid default uuid_generate_v1() not null
            primary key,
    t timestamp with time zone default CURRENT_TIMESTAMP(6),
    sale_doc_pvt_uuid uuid not null,
    whse_prod_pvt_uuid uuid not null,
    quantity numeric(16,6) not null
);

1 Ответ

0 голосов
/ 19 июня 2020

Решено так:

SELECT
    w_prod.prod_article_pvt_uuid
    ,(sum(w_prod.quantity) - s.quantity) as available
FROM warehousing.products w_prod
LEFT JOIN (
    SELECT
        w_prod.prod_article_pvt_uuid
        ,sum(s_item.quantity) as quantity
    FROM warehousing.products w_prod
    LEFT JOIN sales.items s_item ON s_item.whse_prod_pvt_uuid = w_prod.whse_prod_pvt_uuid
    LEFT JOIN sales.documents s_doc ON s_item.sale_doc_pvt_uuid = s_doc.sale_doc_pvt_uuid    
    GROUP BY w_prod.prod_article_pvt_uuid
    ) s ON s.prod_article_pvt_uuid = w_prod.prod_article_pvt_uuid
GROUP BY w_prod.prod_article_pvt_uuid, s.quantity

Он будет отображаться в материализованном виде. Если у кого-то есть предложения по оптимизации, не стесняйтесь комментировать или публиковать ответ.

...