12

我有一个触发器,但我需要与我的 postgres 的所有表相关联。下面有这样的命令吗?

CREATE TRIGGER delete_data_alldb
BEFORE DELETE
ON ALL DATABASE
FOR EACH ROW
EXECUTE PROCEDURE delete_data();
4

1 回答 1

14

好吧,没有数据库范围的触发器创建,但是对于所有此类批量管理操作,您可以使用 PostgreSQL 系统表为您生成查询,而不是手动编写它们。在这种情况下,您可以运行:

SELECT
    'CREATE TRIGGER '
    || tab_name
    || ' BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();' AS trigger_creation_query
FROM (
    SELECT
        quote_ident(table_schema) || '.' || quote_ident(table_name) as tab_name
    FROM
        information_schema.tables
    WHERE
        table_schema NOT IN ('pg_catalog', 'information_schema')
        AND table_schema NOT LIKE 'pg_toast%'
) tablist;

这将为您提供一组字符串,这些字符串是 SQL 命令,例如:

CREATE TRIGGER schema1.table1 BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();
CREATE TRIGGER schema1.table2 BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();
CREATE TRIGGER schema1.table3 BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();
CREATE TRIGGER schema2.table1 BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();
CREATE TRIGGER schema2."TABLE2" BEFORE DELETE ON ALL DATABASE FOR EACH ROW EXECUTE PROCEDURE delete_data();
...
etc

您只需要一次运行它们(通过psql或 pgAdmin)。

现在做一些解释:

  • information_schema.tables我使用系统表在我的数据库中选择表的名称。pg_catalog因为实际上有所有表的数据,请记住information_schema从您的select.
  • 如果需要,我使用quote_ident(text)将字符串放在双引号 ( "") 内的函数(即,带有空格或大写字母的名称需要这样做)。
  • 当我有表名列表时,我只是将它们与一些静态字符串连接起来以获取我的 SQL 命令。
  • 我使用子查询编写该命令是因为我希望您更好地了解这里发生了什么。quote_ident(table_schema) || '.' || quote_ident(table_name)您可以通过替换.来编写单个查询tab_name
于 2015-10-21T18:49:40.593 回答