Tuesday, March 15, 2011

postgresql function

CREATE OR REPLACE FUNCTION "DiskCount"("P1" character varying, "P2" character varying, "P3" character varying, "P4" character varying)
RETURNS int AS
$BODY$
DECLARE
res int;
BEGIN
SELECT count(*) INTO res FROM "GET_СкладскиеОстаткиСоСвойствами" where .......;
RETURN res;
END;
$BODY$
LANGUAGE 'plpgsql' VOLATILE

Нет, можно еще так (обычно я так и пользую):

CREATE OR REPLACE FUNCTION "DiskCount"( IN "P1" character varying, IN "P2" character varying, IN "P3" character varying, IN "P4" character varying, OUT res int)
RETURNS int AS
$BODY$
BEGIN
SELECT count(*) INTO res FROM "GET_СкладскиеОстаткиСоСвойствами" where .......;
END;
$BODY$
LANGUAGE 'plpgsql' VOLATILE


CREATE OR REPLACE FUNCTION "DiskCount"("P1" character varying, "P2" character varying, "P3" character varying, "P4" character varying)
RETURNS int AS
$BODY$
DECLARE
res int;
BEGIN
SELECT count(*) INTO res FROM "GET_СкладскиеОстаткиСоСвойствами" where .......;
RETURN res;
END;
$BODY$
LANGUAGE 'plpgsql' VOLATILE

CREATE FUNCTION upsert_fillrate_alarming(integer, boolean) RETURNS VOID AS '
DECLARE
num ALIAS FOR $1;
dat ALIAS FOR $2;

BEGIN
LOOP
-- First try to update.
UPDATE alarming SET fill_rate = dat WHERE equipid = num;
IF FOUND THEN
RETURN;
END IF;
-- Since its not there we try to insert the key
-- Notice if we had a concurent key insertion we would error
BEGIN
INSERT INTO alarming (equipid, fill_rate) VALUES (num, dat);
RETURN;
EXCEPTION WHEN unique_violation THEN
-- Loop and try the update again
END;
END LOOP;
END;
' LANGUAGE 'plpgsql';

CREATE FUNCTION upsert (sql_update TEXT, sql_insert TEXT)
RETURNS VOID
LANGUAGE plpgsql
AS $$
BEGIN
LOOP
-- first try to update
EXECUTE sql_update;
-- check if the row is found
IF FOUND THEN
RETURN;
END IF;
-- not found so insert the row
BEGIN
EXECUTE sql_insert;
RETURN;
EXCEPTION WHEN unique_violation THEN
-- do nothing and loop
END;
END LOOP;
END;
$$;

CREATE TABLE db (a INT PRIMARY KEY, b TEXT);

CREATE FUNCTION merge_db(key INT, data TEXT) RETURNS VOID AS
$$
BEGIN
LOOP
-- first try to update the key
UPDATE db SET b = data WHERE a = key;
IF found THEN
RETURN;
END IF;
-- not there, so try to insert the key
-- if someone else inserts the same key concurrently,
-- we could get a unique-key failure
BEGIN
INSERT INTO db(a,b) VALUES (key, data);
RETURN;
EXCEPTION WHEN unique_violation THEN
-- do nothing, and loop to try the UPDATE again
END;
END LOOP;
END;
$$
LANGUAGE plpgsql;

SELECT merge_db(1, 'david');
SELECT merge_db(1, 'dennis');

No comments: