如何在PL / pgSQL中编写原子事务

时间:2019-01-07 15:13:43

标签: postgresql transactions plpgsql

我有多个selectinsertupdate语句来完成交易,但是在将更改提交到之前,我似乎无法确保所有语句都成功。桌子。

交易似乎不是原子的。

我的函数中确实有beginend,但是交易似乎不是原子的。

CREATE FUNCTION public.testarray(salesid integer, items json) RETURNS         integer
LANGUAGE plpgsql
AS $$
declare
 resu text;
 resu2 text := 'TH';
 ssrow RECORD;
 oserlen int := 0;
 nserlen int := 0;
 counter int := 0;
begin

 select json_array_length(items::json->'oserial') into oserlen;
 while counter < nserlen loop
   select items::json#>>array['oserial',counter::text] into resu;
   select * into strict ssrow from salesserial where fk_salesid=salesid     and serialnum=resu::int;
   insert into stockloct(serialnum,fk_barcode,source,exflag)     values(ssrow.serialnum,ssrow.fk_barcode,ssrow.fk_salesid,true);
   counter := counter + 1;
 end loop; 

 counter := 0;
 select json_array_length(items::json->'nserial') into nserlen;
 while counter < nserlen loop
   select items::json#>>array['nserial',counter::text,'serial'] into resu2;
   select * into ssrow from stockloc where serialnum=resu2::int;
   insert into salesserial(fk_salesid,serialnum,fk_barcode)     values(salesid,ssrow.serialnum,ssrow.fk_barcode);
   counter := counter + 1;
 end loop;
 select items::json#>'{nserial,0,serial}' into resu2;
 return resu;
end;
$$;

即使第一个插入失败,第二个插入似乎也能够成功。

1 个答案:

答案 0 :(得分:0)

我看到“失败”是指“不插入任何行”。

这并不奇怪,因为从不执行第一个循环:counternserlen始终为0。

也许您是说第一个WHILE条件是counter < oserlen

您似乎也对PL / pgSQL的BEGIN感到困惑:虽然看起来像BEGIN开始了事务,但是却大不相同。这只是PL / pgSQL块中的“左括号”。