如何在 PostgreSQL 函数中使用 COMMIT 和 ROLLBACK
how to use COMMIT and ROLLBACK in a PostgreSQL function
我正在使用三个插入语句,如果第三个语句有错误,我想回滚第一个和第二个。如果没有办法做到这一点,请告诉我在 PostgresqQL 中处理这个问题的不同方法。
如果我使用 COMMIT
或 ROLLBACK
,我会得到一个错误。
CREATE OR REPLACE FUNCTION TEST1 ()
RETURNS VOID
LANGUAGE 'plpgsql'
AS $$
BEGIN
INSERT INTO table1 VALUES (1);
INSERT INTO table1 VALUES (2);
INSERT INTO table1 VALUES ('A');
COMMIT;
EXCEPTION
WHEN OTHERS THEN
ROLLBACK;
END;$$;
以上代码无效; PostgreSQL 函数不支持 COMMIT
和 ROLLBACK
。
您不能在函数中使用像 SAVEPOINT
、COMMIT
或 ROLLBACK
这样的事务语句。 The documentation 说:
In procedures invoked by the CALL
command as well as in anonymous code blocks (DO
command), it is possible to end transactions using the commands COMMIT
and ROLLBACK
.
Ex negativo,因为函数不是用 CALL
调用的过程,你不能在函数中这样做。
PL/pgSQL中启动块的BEGIN
与启动事务的SQL语句BEGIN
不同。
只要从你的函数中删除 COMMIT
,你就有了解决方案:因为整个函数总是 运行 在一个事务中,第三个语句中的任何错误都会导致 ROLLBACK
这也撤消了前两个语句。
与其他 SQL 语言相比,您应该认为 Postgres 总是会在发生错误时隐式地处理 commit/rollback 当您在事务中时.
doc 是这样说的:
Transactions are a fundamental concept of all database systems. The essential point of a transaction is that it bundles multiple steps into a single, all-or-nothing operation. The intermediate states between the steps are not visible to other concurrent transactions, and if some failure occurs that prevents the transaction from completing, then none of the steps affect the database at all.
CREATE OR REPLACE FUNCTION TEST1 ()
RETURNS VOID
LANGUAGE 'plpgsql'
AS $$
BEGIN
INSERT INTO table1 VALUES (1);
INSERT INTO table1 VALUES (2);
INSERT INTO table1 VALUES ('A');
COMMIT;
EXCEPTION
WHEN OTHERS THEN
ROLLBACK;
END;$$;
我正在使用三个插入语句,如果第三个语句有错误,我想回滚第一个和第二个。如果没有办法做到这一点,请告诉我在 PostgresqQL 中处理这个问题的不同方法。
如果我使用 COMMIT
或 ROLLBACK
,我会得到一个错误。
CREATE OR REPLACE FUNCTION TEST1 ()
RETURNS VOID
LANGUAGE 'plpgsql'
AS $$
BEGIN
INSERT INTO table1 VALUES (1);
INSERT INTO table1 VALUES (2);
INSERT INTO table1 VALUES ('A');
COMMIT;
EXCEPTION
WHEN OTHERS THEN
ROLLBACK;
END;$$;
以上代码无效; PostgreSQL 函数不支持 COMMIT
和 ROLLBACK
。
您不能在函数中使用像 SAVEPOINT
、COMMIT
或 ROLLBACK
这样的事务语句。 The documentation 说:
In procedures invoked by the
CALL
command as well as in anonymous code blocks (DO
command), it is possible to end transactions using the commandsCOMMIT
andROLLBACK
.
Ex negativo,因为函数不是用 CALL
调用的过程,你不能在函数中这样做。
PL/pgSQL中启动块的BEGIN
与启动事务的SQL语句BEGIN
不同。
只要从你的函数中删除 COMMIT
,你就有了解决方案:因为整个函数总是 运行 在一个事务中,第三个语句中的任何错误都会导致 ROLLBACK
这也撤消了前两个语句。
与其他 SQL 语言相比,您应该认为 Postgres 总是会在发生错误时隐式地处理 commit/rollback 当您在事务中时.
doc 是这样说的:
Transactions are a fundamental concept of all database systems. The essential point of a transaction is that it bundles multiple steps into a single, all-or-nothing operation. The intermediate states between the steps are not visible to other concurrent transactions, and if some failure occurs that prevents the transaction from completing, then none of the steps affect the database at all.
CREATE OR REPLACE FUNCTION TEST1 ()
RETURNS VOID
LANGUAGE 'plpgsql'
AS $$
BEGIN
INSERT INTO table1 VALUES (1);
INSERT INTO table1 VALUES (2);
INSERT INTO table1 VALUES ('A');
COMMIT;
EXCEPTION
WHEN OTHERS THEN
ROLLBACK;
END;$$;