Od PostgreSQL 8.4 (který zřejmě používáte) existují výchozí hodnoty parametrů funkcí . Pokud dáte svůj parametr na poslední místo a poskytnete výchozí hodnotu, můžete jej z volání jednoduše vynechat:
CREATE OR REPLACE FUNCTION foofunc(_param1 integer
, _param2 date
, _ids int[] DEFAULT '{}')
RETURNS SETOF foobar -- declare return type!
LANGUAGE plpgsql AS
$func$
BEGIN -- required for plpgsql
IF _ids <> '{}'::int[] THEN -- exclude empty array and NULL
RETURN QUERY
SELECT *
FROM foobar
WHERE f1 = _param1
AND f2 = _param2
AND id = ANY(_ids); -- "IN" is not proper syntax for arrays
ELSE
RETURN QUERY
SELECT *
FROM foobar
WHERE f1 = _param1
AND f2 = _param2;
END IF;
END -- required for plpgsql
$func$;
Hlavní body:
-
Klíčové slovo
DEFAULT
se používá k deklaraci výchozích hodnot parametrů. Krátká alternativa:=
. -
Odstranil jsem nadbytečný
param1
z chaotického příkladu. -
Protože vrátíte
SELECT * FROM foobar
, deklarujte návratový typ jakoRETURNS SETOF foobar
místoRETURNS SETOF record
. Druhý formulář s anonymními záznamy je velmi nepraktický, při každém volání byste museli poskytnout seznam definic sloupců. -
Používám pole celých čísel (
int[]
) jako parametr funkce. UpravenoIF
výraz aWHERE
odpovídající klauzuli. -
IF
příkazy nejsou dostupné v prostém SQL. Musí býtLANGUAGE plpgsql
za to.
Volejte s nebo bez _ids
:
SELECT * FROM foofunc(1, '2012-1-1'::date);
Účinně to samé:
SELECT * FROM foofunc(1, '2012-1-1'::date, '{}'::int[]);
Musíte se ujistit, že hovor je jednoznačný. Pokud máte jinou funkci se stejným názvem a dvěma parametry, Postgres nemusí vědět, kterou vybrat. Explicitní obsazení (jak předvádím) to zužuje. Jinak fungují také netypové řetězcové literály, ale být explicitní nikdy neuškodí.
Volání z jiné funkce:
CREATE FUNCTION foofuncwrapper(_param1 integer, _param2 date)
RETURNS SETOF foobar
LANGUAGE plgpsql AS
$func$
DECLARE
_ids int[] := '{1,2,3}';
BEGIN
-- whatever
RETURN QUERY
SELECT * FROM foofunc(_param1, _param2, _ids);
END
$func$;