Трябва да смените езика от sql към plpgsql ако искате да използвате процедурните характеристики на PL/pgSQL. Тялото на функцията също се променя.
Имайте предвид, че всички имена на параметри се виждат в тялото на функцията , включително всички нива на SQL изрази. Ако създадете конфликт на именуване, може да се наложи да квалифицирате имена на колони в таблица като това:table.col , за да избегнете объркване. Тъй като се позовавате на функционални параметри чрез позиционна препратка ($n ) както и да е, току-що премахнах имената на параметрите, за да работи.
И накрая, THEN липсваше в IF изявление - непосредствената причина за съобщението за грешка .
Може да се използва COALESCE за заместване на NULL стойности. Но това работи само ако има поне един резултатен ред. COALESCE не може да коригира "без ред", може само да замени действителния NULL стойности.
Има няколко начина за покриване на всички NULL случаи. В функциите plpgsql :
CREATE OR REPLACE FUNCTION point_total(integer, date, OUT result bigint)
RETURNS bigint AS
$func$
BEGIN
SELECT sum(p.points) -- COALESCE would make sense ...
INTO result
FROM picks p
WHERE p.user_id = $1
AND p.gametime > $2
AND p.points IS NOT NULL; -- ... if NULL values were not ruled out
IF NOT FOUND THEN -- If no row was found ...
result := 0; -- ... set to 0 explicitly
END IF;
END
$func$ LANGUAGE plpgsql;
Или можете да затворите цялата заявка в COALESCE израз във външен SELECT . „Няма ред“ от вътрешния SELECT води до NULL в израза. Работете като обикновен SQL или можете да го обвиете в sql функция :
CREATE OR REPLACE FUNCTION point_total(integer, date)
RETURNS bigint AS
$func$
SELECT COALESCE(
(SELECT sum(p.points)
FROM picks p
WHERE p.user_id = $1
AND p.gametime > $2
-- AND p.points IS NOT NULL -- redundant here
), 0)
$func$ LANGUAGE sql;
Свързан отговор:
Относно конфликти при именуване
Един от проблемите най-вероятно беше конфликтът с имената. Има големи промени във версия 9.0 . Цитирам бележките по изданието :
По-късните версии са усъвършенствали поведението. На очевидни места правилната алтернатива се избира автоматично. Намалява потенциала за конфликти, но все още е там. Съветът все още е в сила в Postgres 9.3.