В postgresql можно ли создать триггеры для таблицы с триггерами на CREATE TABLE?

Возможно ли в Postgres иметь триггер на CREATE TABLE, который будет создавать триггеры для вновь созданной таблицы?

например,

CREATE TABLE base_abc(
   ...
) inherits( base );

Я хотел бы автоматически добавлять триггеры в новую таблицу base_abc это, например, будет вычислять значение столбца на основе имен столбцов.

аналогично, возможно ли запустить ALTER TABLE, чтобы триггеры можно было отбрасывать и создавать заново?

для контекста посмотрите, как лучше всего расширить postgresql для индексации объектов json?

1 ответ

Решение

Не думайте, что есть способ реализовать такие "триггеры", используя встроенные функции PostgreSQL, но вы определенно можете написать хранимую функцию, которая будет делать то, что вы хотите - т.е. создать производную таблицу и затем триггер для этой таблицы.

Вы также можете написать один для изменения таблиц.

Нашел этот вопрос при поиске в Google, и, поскольку все изменилось, решил добавить современный ответ. Начиная с 9.3 у нас есть триггеры событий. Прочтите онлайн-документацию для получения дополнительной информации.

То, что вы просите, можно сделать примерно так:

event_tg_example=# CREATE OR REPLACE FUNCTION add_tg_fn()
        RETURNS event_trigger LANGUAGE plpgsql AS $f$
DECLARE
    obj record;
BEGIN
  FOR obj IN SELECT * FROM pg_event_trigger_ddl_commands()
  LOOP
  execute format('create function %I() returns trigger as $tgf$ begin raise info %L, $i$here$i$; return old; end $tgf$ language $l$plpgsql$l$', 'blah_'||obj.objid::regclass,'%');
  execute format ('CREATE TRIGGER tg_blah BEFORE DELETE ON %I FOR EACH ROW EXECUTE PROCEDURE %I();', obj.objid::regclass, 'blah_'||obj.objid::regclass);

  END LOOP;
END
$f$
;
CREATE FUNCTION
event_tg_example=# CREATE EVENT TRIGGER add_tg_tg
   ON ddl_command_end
WHEN TAG IN ('CREATE TABLE')
   EXECUTE PROCEDURE add_tg_fn()
;
CREATE EVENT TRIGGER
event_tg_example=# create table t(i int);
CREATE TABLE
event_tg_example=# insert into t values (1);
INSERT 0 1
event_tg_example=# delete from t where i = 1;
INFO:  here
DELETE 1
event_tg_example=#

Имейте в виду, что это всего лишь рабочий пример, не копируйте / вставляйте его вслепую

Другие вопросы по тегам