Z dobrego podręcznika:
36.1. Przegląd zachowań wyzwalaczy
[...]
W przypadku wyzwalacza na poziomie wiersza dane wejściowe obejmują również NEW wiersz dla INSERT i UPDATE wyzwalacze i/lub OLD wiersz dla UPDATE i DELETE wyzwalacze. Wyzwalacze na poziomie instrukcji nie mają obecnie możliwości sprawdzenia poszczególnych wierszy zmodyfikowanych przez instrukcję.
Oraz z procedur wyzwalania:
NEW
Typ danych RECORD; zmienna przechowująca nowy wiersz bazy danych dla INSERT /UPDATE operacje w wyzwalaczach na poziomie wiersza. Ta zmienna ma wartość NULL w wyzwalaczach na poziomie instrukcji i dla DELETE operacje.
Zwróć uwagę, co mówi o wyzwalaczach na poziomie wiersza i wyzwalaczach na poziomie instrukcji.
Masz wyzwalacz na poziomie instrukcji:
...
FOR EACH STATEMENT
EXECUTE PROCEDURE f_log_datei();
Wyzwalacze na poziomie instrukcji są wyzwalane raz na instrukcję, a instrukcja może dotyczyć wielu wierszy, więc pojęcie dotkniętego wiersza (czyli to, co NEW i OLD dotyczą) po prostu nie ma zastosowania.
Jeśli chcesz użyć NEW (lub OLD ) w wyzwalaczu, chcesz, aby wyzwalacz był wykonywany dla każdego wiersza, którego dotyczy problem, a to oznacza, że chcesz wyzwalacza na poziomie wiersza:
CREATE TRIGGER log_datei AFTER INSERT OR UPDATE OR DELETE
ON dateien
FOR EACH ROW
EXECUTE PROCEDURE f_log_datei();
Właśnie zmieniłem FOR EACH STATEMENT do FOR EACH ROW .
Twój wyzwalacz powinien również coś zwracać:
Funkcja wyzwalacza musi zwracać NULL lub wartość rekordu/wiersza o dokładnie takiej samej strukturze tabeli, dla której został uruchomiony wyzwalacz.
[...]
Wartość zwracana wyzwalacza na poziomie wiersza uruchomionego AFTER lub wyzwalacz na poziomie instrukcji uruchamiany BEFORE lub AFTER jest zawsze ignorowana; równie dobrze mogłoby być zerowe. Jednak każdy z tych typów wyzwalaczy może przerwać całą operację, zgłaszając błąd.
Więc powinieneś RETURN NEW; lub RETURN NULL; w spuście. Masz wyzwalacz AFTER, więc nie ma znaczenia, którego RETURN użyjesz, ale wybrałbym RETURN NEW; .