![](/img/trans.png)
[英]plpgsql function with text array parameter coming from node postgres
[英]Postgresql complex logic function ( plpgsql )
好吧,我有這個模式
https://dbfiddle.uk/?rdbms=postgres_10&fiddle=56b0781c13dfb545e9f07f82da6ae34d
我需要制定一個 function 來接受 jsonb 的輸入
[
{
bill_id : 1,
product_id : 1,
delivered: 50
},
{
bill_id : 1,
product_id : 2,
delivered: 400
}
]
使用上述 jsonb 輸入 function 應該更新bill_products並將其插入到庫存表中。 此外,如果所有bill_products都已交付,則應在bill表中將批准的 boolean 更新為 true
我是 plpgsql 的新手,有人可以幫我解決這個問題。
我想這應該這樣做:
DO LANGUAGE plpgsql $$
DECLARE
input CONSTANT jsonb := '...';
delivery jsonb;
updated bill_products;
BEGIN
FOR delivery IN SELECT jsonb_array_elements(input) LOOP
UPDATE bill_products
SET delivered = delivered + (delivery->>'delivered')::numeric
WHERE bill_id = (delivery->>'bill_id')::int
AND pro_id = (delivery->>'product_id')::int
RETURNING *
INTO STRICT updated;
INSERT INTO inventory(pro_id, quantity)
VALUES (updated.pro_id, updated.delivered);
END LOOP;
UPDATE bill
SET approved = NOT EXISTS (SELECT 1
FROM bill_products
WHERE bill_products.bill_id = bill.bill_id
AND delivered < quantity)
WHERE bill_id IN (SELECT DISTINCT (d->>'bill_id')::int
FROM jsonb_array_elements(input) d);
END;
$$;
( 在線演示)
或者,使用普通的 SQL 而不是循環可能更簡單:
WITH updates AS (
UPDATE bill_products
SET delivered = delivered + (delivery->>'delivered')::numeric
FROM jsonb_array_elements(input) delivery
WHERE bill_id = (delivery->>'bill_id')::int
AND pro_id = (delivery->>'product_id')::int
RETURNING pro_id, delivered
) INSERT INTO inventory(pro_id, quantity)
SELECT * FROM updates;
( 在線演示)
請注意,在inventory
和bill_products
表中重復交付信息並不是好的數據庫設計。 您可能應該省略bill_prodcts.delivered
列,而是在每次需要時計算相應庫存條目的總和。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.