PostgreSQL存储过程如何返回多个不同查询结果集?
在PostgreSQL存储过程中返回多个结果集
需求
将以下MS SQL存储过程移植到PostgreSQL,实现调用后返回两个独立的查询结果集:
CREATE PROCEDURE dbo.TestMe AS BEGIN SELECT * FROM T_FMS_Configuration; SELECT * FROM T_FMS_Navigation; END GO
已尝试两种方式但不符合预期:
- 函数结合refcursor:满足多结果集需求,但要求必须使用存储过程而非函数
- 存储过程结合临时表:需创建临时表,希望采用类似函数的refcursor方式实现
尝试的refcursor存储过程报错ERROR: Cursor »Ref1« not existing,寻求正确实现方法。
可行方案
方案1:直接返回多结果集(最贴合MS SQL行为)
PostgreSQL 11及以上版本的存储过程支持直接在过程体内执行多个SELECT语句,客户端会自动接收多个独立结果集,无需额外处理:
CREATE OR REPLACE PROCEDURE dbo.TestMe() LANGUAGE plpgsql AS $$ BEGIN SELECT * FROM dbo."T_FMS_Configuration"; SELECT * FROM dbo."T_FMS_Navigation"; END; $$;
调用方式:
CALL dbo.TestMe();
执行后客户端将收到两个结果集,与MS SQL的执行效果完全一致。
方案2:使用refcursor输出结果集(解决原报错)
若必须使用refcursor,需注意存储过程的refcursor类型OUT参数需正确传递游标变量或带引号的游标名,原报错是因为游标名未被正确识别。
存储过程定义
CREATE OR REPLACE PROCEDURE get_two_datasets(OUT cursor1 refcursor, OUT cursor2 refcursor) LANGUAGE plpgsql AS $$ BEGIN OPEN cursor1 FOR SELECT * FROM dbo."T_FMS_Configuration"; OPEN cursor2 FOR SELECT * FROM dbo."T_FMS_Navigation"; END; $$;
正确调用方式
方式A:使用游标变量
在同一会话中执行:
-- 声明游标变量 DECLARE ref1 refcursor; DECLARE ref2 refcursor; -- 调用存储过程为变量赋值游标 CALL get_two_datasets(ref1, ref2); -- 从游标中获取所有数据 FETCH ALL IN ref1; FETCH ALL IN ref2;
方式B:显式指定游标名
调用时需用双引号包裹游标名(确保标识符大小写匹配):
CALL get_two_datasets('"Ref1"', '"Ref2"'); -- 读取游标数据 FETCH ALL IN "Ref1"; FETCH ALL IN "Ref2";
内容的提问来源于stack exchange,提问作者Stefan Steiger
相关产品推荐
相关产品推荐

