Открыть сервис

Триггеры SQL

Триггер SQL — это хранимая процедура особого типа, которая автоматически выполняется (срабатывает) при наступлении определённого события в базе данных, связанного с изменением данных в таблице или представлении (вставка, обновление или удаление строк). Триггеры являются частью серверной логики СУБД и используются для обеспечения целостности данных, реализации сложных бизнес-правил, аудита изменений и каскадных операций, не зависящих от клиентского приложения.

История

Концепция триггеров была впервые реализована в коммерческих СУБД в конце 1980-х — начале 1990-х годов. Одной из первых систем, включивших триггеры, стала InterBase (1985). В 1986 году стандарт SQL-86 не предусматривал триггеров; они были добавлены в стандарт SQL:1999 (ISO/IEC 9075-2:1999) как часть объектно-реляционных расширений. До этого триггеры существовали как проприетарные расширения в Sybase (1987), Oracle (1992) и Microsoft SQL Server (1993). В PostgreSQL триггеры появились в версии 6.0 (1997). Стандарт SQL:2003 уточнил синтаксис и семантику триггеров, включая поддержку триггеров INSTEAD OF для представлений.

Классификация триггеров

По времени срабатывания относительно события

По уровню срабатывания

По типу события

По области действия

Устройство и синтаксис

Триггер состоит из трёх основных частей:

  1. Событие — определяет, при какой операции (INSERT, UPDATE, DELETE) и на каком объекте (таблица, представление) триггер должен срабатывать.
  2. Время срабатывания — BEFORE, AFTER или INSTEAD OF.
  3. Тело триггера — блок кода на процедурном языке СУБД (PL/SQL в Oracle, T-SQL в Microsoft SQL Server, PL/pgSQL в PostgreSQL, SQL/PSM в DB2), который выполняется при активации триггера.

Обобщённый синтаксис (по стандарту SQL:2003):

``sql CREATE TRIGGER trigger_name {BEFORE | AFTER | INSTEAD OF} {INSERT | UPDATE | DELETE} ON table_name [FOR EACH {ROW | STATEMENT}] [WHEN (condition)] BEGIN -- тело триггера END; ``

Внутри тела триггера доступны специальные переменные (псевдозаписи):

Применение

Обеспечение целостности данных

Триггеры используются для реализации ограничений, которые невозможно или сложно задать через декларативные ограничения (PRIMARY KEY, FOREIGN KEY, CHECK, UNIQUE). Например:

Аудит и логирование

Триггеры AFTER INSERT/UPDATE/DELETE могут автоматически записывать информацию об изменениях в специальную таблицу аудита: кто, когда, какие данные изменил, старые и новые значения. Это позволяет отслеживать действия пользователей без модификации кода приложения.

Поддержка материализованных представлений

В некоторых СУБД триггеры используются для автоматического обновления материализованных представлений при изменении базовых таблиц.

Реализация сложной бизнес-логики

Триггеры могут выполнять вычисления, обновлять связанные таблицы, вызывать хранимые процедуры, отправлять уведомления (например, через DBMS_SCHEDULER или pg_notify).

Защита от удаления или изменения критических данных

Триггеры BEFORE DELETE могут отменять операцию, если удаляемая строка соответствует определённым условиям (например, нельзя удалить пользователя с активными заказами).

Примеры

Пример 1. Триггер BEFORE INSERT для автоматической установки значения по умолчанию (PostgreSQL):

```sql CREATE OR REPLACE FUNCTION set_created_at() RETURNS TRIGGER AS $$ BEGIN NEW.created_at = NOW(); RETURN NEW; END; $$ LANGUAGE plpgsql;

CREATE TRIGGER trg_set_created_at BEFORE INSERT ON users FOR EACH ROW EXECUTE FUNCTION set_created_at(); ```

Пример 2. Триггер AFTER UPDATE для аудита (Oracle):

``sql CREATE OR REPLACE TRIGGER audit_salary_change AFTER UPDATE OF salary ON employees FOR EACH ROW BEGIN INSERT INTO salary_audit (employee_id, old_salary, new_salary, changed_by, change_date) VALUES (:OLD.employee_id, :OLD.salary, :NEW.salary, USER, SYSDATE); END; ``

Пример 3. Триггер INSTEAD OF на представлении (Microsoft SQL Server):

``sql CREATE TRIGGER trg_employee_details_insert ON EmployeeDetailsView INSTEAD OF INSERT AS BEGIN INSERT INTO Employees (Name, DepartmentID) SELECT i.Name, d.DepartmentID FROM inserted i JOIN Departments d ON i.DepartmentName = d.DepartmentName; END; ``

Критика и ограничения

Интересные факты

Источники

BFOmetr — база данных и аналитика по компаниям России.

На главную BFOmetr →