Así es como su función de activación funcionaría correctamente:
CREATE OR REPLACE FUNCTION loca_app.func_historico_mod_usuarios()
RETURNS trigger AS
$func$
BEGIN
EXECUTE format(
'INSERT INTO loca_app.tb_modificacoes
(mod_momento, mod_valor_anterior, mod_valor_atual, mod_usuario, mod_dado)
VALUES (now() , $1.%1$I , $2.%1$I , $3 , $4)
)', TG_ARGV[0])
USING OLD, NEW, TG_RELID
, (SELECT dad_id FROM loca_app.tb_dados
WHERE dad_nome = TG_ARGV[0] -- cast? see blow
LIMIT 1);
RETURN NULL; -- only good for AFTER trigger
END
$func$ LANGUAGE plpgsql;
Puntos principales
-
Pase los valores de fila especiales
OLD
yNEW
así comoTG_RELID
como valores paraEXECUTE
con elUSING
cláusula. Puede que tengas que lanzarTG_RELID
a un tipo de datos adecuado. La definición de la tabla detb_modificacoes
no se revela. O realmente quieres algo más aquí. Consulte a continuación.$1
,$2
y$3
en la cadena SQL pasada aEXECUTE
referirse a expresiones en elUSING
cláusula, no a los parámetros de la función, a los que se puede hacer referencia con la misma sintaxis posicional en el cuerpo de la función fueraEXECUTE
. -
Concatene su comando SQL dinámico usando
format()
. Mucho más limpio y seguro. Citar y escapar identificadores , código y valores ¡adecuadamente!%1$I
y%1$L
son especificadores de formato paraformat()
. Lea el manual para obtener más detalles. -
¡Se requiere el caso correcto! Su convención para deletrear identificadores con letras mayúsculas tiene sentido en Oracle, donde los identificadores sin comillas se convierten en letras mayúsculas. No es útil en Postgres, donde todo se pliega en minúsculas:
-
No uses
ILIKE
enDAD_NOME ILIKE 'USU_NASCIMENTO'
. Los identificadores de Postgres distinguen entre mayúsculas y minúsculas. podrías tener múltiples valores coincidentes endad_nome
. Usa=
en su lugar y pase los identificadores escritos correctamente. Y asegúrate de quedad_nome
se define único. Ver más abajo. -
Tu comentario dice:
MOD_USUARIO , -- Translated to: User (ID)
. Pero eso no es lo que pasas. El manual:Es posible que desee utilizar
current_user
osession_user
en cambio: -
Puedes eliminar
LIMIT 1
de la subconsulta ifdad_nome
se defineUNIQUE
. De lo contrario, debe decidir qué fila elegir en caso de empate, conORDER BY
. -
Las funciones de activación son requeridas para terminar con un
RETURN
declaración. También podría serRETURN NULL
para unAFTER
generar. El manual:
Relacionado:
- Cómo pasar NUEVO.* a EJECUTAR en la función de activación
- Reemplace las comillas dobles con comillas simples en Postgres (plpgsql)
Aparte: Si bien es nuevo en Postgres, es posible que desee utilizar este tipo de SQL dinámico avanzado con cuidado. Necesita entender lo que está haciendo.