Отбросить ВСЕ триггеры из БД Postgres? - PullRequest
11 голосов
/ 22 июня 2010

Есть ли способ удалить ВСЕ триггеры из ВСЕХ таблиц в Postgres?Я знаю, что есть таблица pg_trigger, на которую я могу посмотреть, но она не выглядит так, как будто она содержит достаточно информации, чтобы я мог расшифровать, какие триггеры я добавил в свои таблицы.

Похоже, появляются ограничения внешнего ключав таблице pg_trigger, которую я НЕ хочу отбрасывать.Я просто хочу удалить созданный пользователем триггер из моих таблиц и сохранить ФК.

Есть предложения?

Ответы [ 8 ]

22 голосов
/ 03 апреля 2011

Спасибо, Джеймс.

Функция из Удалить ВСЕ триггеры из Postgres DB? удаляет только вхождение из первой таблицы и оставляет триггеры с тем же именем в других таблицах.Вот фиксированная функция:

CREATE OR REPLACE FUNCTION strip_all_triggers() RETURNS text AS $$ DECLARE
    triggNameRecord RECORD;
    triggTableRecord RECORD;
BEGIN
    FOR triggNameRecord IN select distinct(trigger_name) from information_schema.triggers where trigger_schema = 'public' LOOP
        FOR triggTableRecord IN SELECT distinct(event_object_table) from information_schema.triggers where trigger_name = triggNameRecord.trigger_name LOOP
            RAISE NOTICE 'Dropping trigger: % on table: %', triggNameRecord.trigger_name, triggTableRecord.event_object_table;
            EXECUTE 'DROP TRIGGER ' || triggNameRecord.trigger_name || ' ON ' || triggTableRecord.event_object_table || ';';
        END LOOP;
    END LOOP;

    RETURN 'done';
END;
$$ LANGUAGE plpgsql SECURITY DEFINER;

select strip_all_triggers();
2 голосов
/ 24 апреля 2012

Просто каскадно отбросьте язык, на котором вы создали триггеры.
Например, я создаю триггеры в plpgsql, поэтому следующий запрос мгновенно удаляет все триггеры -

DROP LANGUAGE plpgsql CASCADE;
2 голосов
/ 11 августа 2010

ОБНОВЛЕНИЕ: См. Реальное решение для полной функции, которую вы хотите.

Хорошо, я придумал функцию, которая делает это для меня:

CREATE OR REPLACE FUNCTION strip_all_triggers() RETURNS text AS $$ DECLARE
        triggNameRecord RECORD;
    triggTableRecord RECORD;
BEGIN
    FOR triggNameRecord IN select distinct(trigger_name) from information_schema.triggers where trigger_schema = 'public' LOOP
        SELECT distinct(event_object_table) INTO triggTableRecord from information_schema.triggers where trigger_name = triggNameRecord.trigger_name;
        RAISE NOTICE 'Dropping trigger: % on table: %', triggNameRecord.trigger_name, triggTableRecord.event_object_table;
        EXECUTE 'DROP TRIGGER ' || triggNameRecord.trigger_name || ' ON ' || triggTableRecord.event_object_table || ';';
    END LOOP;

    RETURN 'done';
END;
$$ LANGUAGE plpgsql SECURITY DEFINER;

select strip_all_triggers();

Это исключит любой триггер в вашей общедоступной схеме.

1 голос
/ 22 июня 2010

Проще всего будет pg_dump -s определить объекты и отфильтровать его для строк, начинающихся с CREATE TRIGGER.

Что-то вроде

./pg_dump -s db_name | grep '^CREATE TRIGGER' | \
  while read _ _ triggername _; do \
    echo drop trigger "$triggername;"; \
  done

(в bash) должно работать (просмотрите его изатем запустите в базе данных).

Но, возможно, вам следует рассмотреть вместо alter table table_name disable trigger trigger_name.

1 голос
/ 22 июня 2010

Взгляните на информационную схему:

SELECT * FROM information_schema.triggers;
0 голосов
/ 30 марта 2019

Верхний ответ все еще некорректен, потому что нет необходимости в двух циклах.

Это может быть сделано:

CREATE PROCEDURE _DropTableTriggers()
AS
$$
DECLARE
    _rec    RECORD;
BEGIN
    FOR _rec IN
        SELECT  DISTINCT    event_object_table, trigger_name
        FROM    INFORMATION_SCHEMA.triggers
    LOOP
        EXECUTE 'DROP TRIGGER ' || _rec.trigger_name || ' ON ' || _rec.event_object_table || ';';
    END LOOP;
END
$$ LANGUAGE plpgsql SECURITY DEFINER;
0 голосов
/ 20 августа 2016

Я предпочитаю это (на основе , чем ), чем принятый ответ @ kuznetso3v, потому что это дает мне возможность проверить DROP STATEMENT s перед выполнением их с помощью copy-paste:

SELECT 'DROP TRIGGER ' || trigger_name || ' ON ' || event_object_table || ';'
FROM information_schema.triggers
WHERE trigger_schema = 'public';
0 голосов
/ 22 июня 2010

Вы можете начать с этого запроса, чтобы найти имена триггеров outr:

select * from pg_trigger t,pg_proc where
 pg_proc.oid=t.tgfoid
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...