U moet de taal wijzigen van sql
naar plpgsql
als u de procedurele kenmerken van PL/pgSQL wilt gebruiken. De functietekst verandert ook.
Houd er rekening mee dat alle parameternamen zichtbaar zijn in de hoofdtekst van de functie , inclusief alle niveaus van SQL-instructies. Als u een naamgevingsconflict creëert, moet u mogelijk kolomnamen als volgt kwalificeren:table.col
, om verwarring te voorkomen. Aangezien u naar functieparameters verwijst door middel van positionele referentie ($n
) hoe dan ook, ik heb zojuist parameternamen verwijderd om het te laten werken.
Tot slot, THEN
ontbrak in de IF
statement - de directe oorzaak van de foutmelding .
Je zou COALESCE ter vervanging van NULL
waarden. Maar dat werkt alleen als er ten minste één resulterende rij is. COALESCE
kan "geen rij" niet repareren, het kan alleen de werkelijke NULL
vervangen waarden.
Er zijn verschillende manieren om alle NULL
. te dekken gevallen. In plpgsql-functies :
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;
Of u kunt de hele zoekopdracht insluiten in een COALESCE
uitdrukking in een buitenste SELECT
. "Geen rij" van de binnenste SELECT
resulteert in een NULL
in de uitdrukking. Werk als gewone SQL, of je kunt het in een sql-functie plaatsen :
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;
Gerelateerd antwoord:
Over naamgevingsconflicten
Een probleem was waarschijnlijk het naamgevingsconflict. Er zijn grote wijzigingen aangebracht in versie 9.0 . Ik citeer de release-opmerkingen :
Latere versies hebben het gedrag verfijnd. Op voor de hand liggende plekken wordt automatisch het juiste alternatief gekozen. Vermindert de kans op conflicten, maar het is er nog steeds. Het advies is nog steeds van toepassing in Postgres 9.3.