Las funciones escritas en PL/pgSQL
o SQL
se pueden definir como RETURNS void
. Recientemente me encontré con una extraña diferencia en el resultado.Funciones de PostgreSQL que devuelven nulo
Considérese la siguiente demostración:
CREATE OR REPLACE FUNCTION f_sql()
RETURNS void AS
'SELECT NULL::void' -- "do nothing", no special meaning
LANGUAGE sql;
CREATE OR REPLACE FUNCTION f_plpgsql()
RETURNS void AS
$$
BEGIN
NULL; -- "do nothing", no special meaning
END;
$$ LANGUAGE plpgsql;
La función f_sql()
utiliza el único camino posible para un SELECT
(como último comando) en una función SQL que RETURNS void
. Lo uso simplemente porque es la forma más sencilla para los fines de esta prueba: cualquier otra función, con UPDATE
o DELETE
por ejemplo, muestra el mismo comportamiento.
Ahora, void
es un tipo ficticio. Mientras que la función plpgsql
parece devolver el equivalente de una cadena vacía como tipo void
, efectivamente ''::void
. La función sql
parece devolver NULL::void
.
db=# SELECT f_sql() IS NULL;
?column?
----------
t
db=# SELECT f_sql()::text IS NULL;
?column?
----------
t
db=# SELECT f_plpgsql() IS NULL;
?column?
----------
f
db=# SELECT f_plpgsql()::text = '';
?column?
----------
t
Esto puede tener efectos secundarios sutiles y confusos.
¿Cuál es la razón detrás de la diferencia?
Están declarados como inválidos; tal vez no tengamos que ver cómo se comparan sus valores devueltos con * cualquier cosa *. (Si * realmente * deseaba disuadir a las personas de mirar el valor de retorno, podría hacer que devuelva un valor aleatorio. Podría hacerlo la próxima vez que escriba algo que debería volverse vacío.) –
@Catcall: Sí, se podría argumentar que fue un error verificar un valor vacío en absoluto. Todavía se siente con errores que el valor es diferente dependiendo del idioma elegido. Eso no debería ser Archivaré un informe de error cuando lo haga y veremos qué piensa el equipo central al respecto. –
Y varios años tarde [me tropiezo] (http://dba.stackexchange.com/q/65310/1396) en la misma cosa! Aún así, aprendí el útil truco de 'SELECT NULL :: void' en una función de retorno de sql vacía: por cierto, el capítulo parece haber desaparecido del enlace que proporcionó (aunque el truco aún funciona en 9.3). –