PostgreSQL
 sql >> Base de données >  >> RDS >> PostgreSQL

PostgreSQL ne peut pas commencer/terminer les transactions en PL/pgSQL

Une fonction plpgsql s'exécute automatiquement dans une transaction. Tout réussit ou tout échoue. Le manuel :

Les fonctions et les procédures de déclenchement sont toujours exécutées dans une transaction établie par une requête externe - elles ne peuvent pas démarrer ou valider cette transaction, car il n'y aurait pas de contexte pour leur exécution. Cependant, un bloc contenant une EXCEPTION La clause forme en fait une sous-transaction qui peut être annulée sans affecter la transaction externe. Pour plus d'informations à ce sujet, consultez la section 42.6.6.

Donc, si vous en avez besoin, vous pouvez intercepter une exception qui pourrait théoriquement se produire (mais c'est très peu probable).
Détails sur le piégeage des erreurs dans le manuel.

Votre fonction revue et simplifiée :

CREATE FUNCTION foo(v_weather text
                  , v_timeofday text
                  , v_speed text
                  , v_behavior text)
  RETURNS SETOF custombehavior
  LANGUAGE plpgsql AS
$func$
BEGIN

DELETE FROM custombehavior
WHERE  weather = 'RAIN'
AND    timeofday = 'NIGHT'
AND    speed = '45MPH';

INSERT INTO custombehavior (weather, timeofday, speed, behavior)
SELECT v_weather, v_timeofday, v_speed, v_behavior
WHERE  NOT EXISTS (
   SELECT FROM defaultbehavior
   WHERE  a = 'RAIN'
   AND    b = 'NIGHT'
   AND    c = '45MPH'
   );

RETURN QUERY
SELECT * FROM custombehavior WHERE ... ;

END
$func$;

Si vous avez réellement besoin de commencer/terminer des transactions comme indiqué dans le titre, regardez les procédures SQL dans Postgres 11 ou version ultérieure (CREATE PROCEDURE ). Voir :

  • Dans PostgreSQL, quelle est la différence entre une "procédure stockée" et d'autres types de fonctions ?