Debe cambiar el idioma de sql
a plpgsql
si desea utilizar las funciones de procedimiento de PL/pgSQL. El cuerpo de la función también cambia.
Tenga en cuenta que todos los nombres de los parámetros están visibles en el cuerpo de la función , incluidos todos los niveles de sentencias SQL. Si crea un conflicto de nombres, es posible que deba calificar los nombres de las columnas como este:table.col
, para evitar confusión. Dado que se refiere a los parámetros de función por referencia posicional ($n
) de todos modos, simplemente eliminé los nombres de los parámetros para que funcione.
Finalmente, THEN
faltaba en el IF
instrucción:la causa inmediata del mensaje de error .
Se podría usar COALESCE para sustituir NULL
valores. Pero eso solo funciona si hay al menos una fila resultante. COALESCE
no puede corregir "sin fila", solo puede reemplazar NULL
real valores.
Hay varias formas de cubrir todos los NULL
casos. En funciones 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;
O puede encerrar toda la consulta en un COALESCE
expresión en un SELECT
externo . "Sin fila" desde el interior SELECT
da como resultado un NULL
en la expresión. Trabaje como SQL simple, o puede envolverlo en una función 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;
Respuesta relacionada:
Sobre los conflictos de nombres
Un problema era probablemente el conflicto de nombres. Ha habido cambios importantes en la versión 9.0 . Cito las notas de la versión :
Las versiones posteriores han refinado el comportamiento. En lugares obvios, la alternativa correcta se elige automáticamente. Reduce el potencial de conflictos, pero sigue ahí. El consejo aún se aplica en Postgres 9.3.