38.2. Видимость изменений в данных
Если в триггерной функции выполняются SQL-команды и эти команды обращаются к таблице, на которую создан триггер, то необходимо знать правила видимости данных, потому что они определяют, будут ли видеть эти SQL-команды изменения в данных, для которых сработал триггер. Кратко:
Триггеры уровня оператора следуют простым правилам видимости: никакие из изменений, произведённых оператором, не видны в триггерах
BEFORE, тогда как в триггерахAFTERвидны все изменения.Изменение данных (вставка, обновление или удаление), заставляющее сработать триггер, не видно для команд SQL, выполняемых в триггере
BEFOREуровня строки, потому что это изменение ещё не произошло.Тем не менее команды SQL, выполняемые в триггере
BEFOREуровня строки, будут видеть изменения данных в строках, которые уже были обработаны в этом операторе. Это требует осторожности, так как порядок обработки строк в целом непредсказуемый; команда SQL, обрабатывающая множество строк, может делать это в любом порядке.Аналогично, триггер
INSTEAD OFуровня строки увидит изменения данных, внесённые при предыдущих вызовах триггераINSTEAD OFдля этой же внешней команды.Когда срабатывает триггер
AFTERуровня строки, все изменения сделанные оператором уже выполнены и видны в вызываемой триггерной функции.
Если триггерная функция написана на одном из стандартных процедурных языков, вышеприведённые утверждения применимы, только если функция объявлена как VOLATILE. Функции объявленные как STABLE или IMMUTABLE в любом случае не будут видеть изменений, сделанных вызывающим оператором.
Дополнительную информацию о правилах видимости данных можно найти в Разделе 46.4. Пример в Разделе 38.4 содержит демонстрацию этих правил.
38.2. Visibility of Data Changes
If you execute SQL commands in your trigger function, and these commands access the table that the trigger is for, then you need to be aware of the data visibility rules, because they determine whether these SQL commands will see the data change that the trigger is fired for. Briefly:
Statement-level triggers follow simple visibility rules: none of the changes made by a statement are visible to statement-level
BEFOREtriggers, whereas all modifications are visible to statement-levelAFTERtriggers.The data change (insertion, update, or deletion) causing the trigger to fire is naturally not visible to SQL commands executed in a row-level
BEFOREtrigger, because it hasn't happened yet.However, SQL commands executed in a row-level
BEFOREtrigger will see the effects of data changes for rows previously processed in the same outer command. This requires caution, since the ordering of these change events is not in general predictable; a SQL command that affects multiple rows can visit the rows in any order.Similarly, a row-level
INSTEAD OFtrigger will see the effects of data changes made by previous firings ofINSTEAD OFtriggers in the same outer command.When a row-level
AFTERtrigger is fired, all data changes made by the outer command are already complete, and are visible to the invoked trigger function.
If your trigger function is written in any of the standard procedural languages, then the above statements apply only if the function is declared VOLATILE. Functions that are declared STABLE or IMMUTABLE will not see changes made by the calling command in any case.
Further information about data visibility rules can be found in Section 46.4. The example in Section 38.4 contains a demonstration of these rules.