退出函数时删除临时 table
Drop temporary table when exiting a function
我在带有 'on commit drop' 选项的函数中使用临时 table。我的问题是,在某些情况下,一个更全局的函数可以调用第一个函数两次,所以 "create temp table" 在提交之前被调用两次 - 所以我有正常的错误 "relation [my_temp_table] already exists".
我在函数末尾使用临时 table 来 return 它在 "return query" 中的行,所以我不能手动删除之前的 table我离开了这个功能。
CREATE OR REPLACE FUNCTION my_function(_value text)
RETURNS setof my_table AS $$
DECLARE
resultCount integer := 0;
BEGIN
create temp table my_temp_table on commit drop as
select *
from my_table
where value = _value ;
select count(*) into resultCount from my_temp_table;
if (resultCount = 0) then
raise exception 'value not found';
end if;
return query
select * from my_temp_table;
END;$$ LANGUAGE plpgsql VOLATILE COST 100;
ALTER FUNCTION my_function(text) OWNER TO postgres
如果您想知道为什么我直接使用临时 table 而不是 my_table,那是因为我需要非常快的响应,而且 my_table 非常大(几十个百万行)所以这样我只能请求一次而不是三次(搜索、计数和 return)。
我找到了一个不使用 temp table 和创建类型的解决方法,但是 my_table 的结构会改变很多次,实际上我有几十个 "my table" 和相关的"my function",所以这是一种无需在每次 table 的结构发生变化时重新编写所有函数的方法。
该函数必须 return 与其请求的 table 相同的结构。
如何在离开函数时删除 table?或者有更好的解决方法吗?
您可以删除 table 以防万一:
...
BEGIN
drop table if exists my_temp_table;
create temp table my_temp_table on commit drop as
....
但是...实际上您不需要临时 table。试试这个代码:
...
return query
select *
from my_table
where value = _value ;
if not found then
raise exception 'value not found';
end if;
...
... return its rows in the "return query", so I can't manually drop the table before I leave the function.
其实你可以。您可以根据自己的情况使用多个 RETURN QUERY
。
手动后:
When a PL/pgSQL function is declared to return SETOF [...] the individual items to return are specified by a sequence of RETURN NEXT or RETURN QUERY commands, and then a final RETURN command with no argument is used to indicate that the function has finished executing
所以你可以这样做:
RETURN QUERY
SELECT * FROM my_temp_table;
DROP TABLE my_temp_table;
RETURN;
我在带有 'on commit drop' 选项的函数中使用临时 table。我的问题是,在某些情况下,一个更全局的函数可以调用第一个函数两次,所以 "create temp table" 在提交之前被调用两次 - 所以我有正常的错误 "relation [my_temp_table] already exists".
我在函数末尾使用临时 table 来 return 它在 "return query" 中的行,所以我不能手动删除之前的 table我离开了这个功能。
CREATE OR REPLACE FUNCTION my_function(_value text)
RETURNS setof my_table AS $$
DECLARE
resultCount integer := 0;
BEGIN
create temp table my_temp_table on commit drop as
select *
from my_table
where value = _value ;
select count(*) into resultCount from my_temp_table;
if (resultCount = 0) then
raise exception 'value not found';
end if;
return query
select * from my_temp_table;
END;$$ LANGUAGE plpgsql VOLATILE COST 100;
ALTER FUNCTION my_function(text) OWNER TO postgres
如果您想知道为什么我直接使用临时 table 而不是 my_table,那是因为我需要非常快的响应,而且 my_table 非常大(几十个百万行)所以这样我只能请求一次而不是三次(搜索、计数和 return)。
我找到了一个不使用 temp table 和创建类型的解决方法,但是 my_table 的结构会改变很多次,实际上我有几十个 "my table" 和相关的"my function",所以这是一种无需在每次 table 的结构发生变化时重新编写所有函数的方法。
该函数必须 return 与其请求的 table 相同的结构。
如何在离开函数时删除 table?或者有更好的解决方法吗?
您可以删除 table 以防万一:
...
BEGIN
drop table if exists my_temp_table;
create temp table my_temp_table on commit drop as
....
但是...实际上您不需要临时 table。试试这个代码:
...
return query
select *
from my_table
where value = _value ;
if not found then
raise exception 'value not found';
end if;
...
... return its rows in the "return query", so I can't manually drop the table before I leave the function.
其实你可以。您可以根据自己的情况使用多个 RETURN QUERY
。
手动后:
When a PL/pgSQL function is declared to return SETOF [...] the individual items to return are specified by a sequence of RETURN NEXT or RETURN QUERY commands, and then a final RETURN command with no argument is used to indicate that the function has finished executing
所以你可以这样做:
RETURN QUERY
SELECT * FROM my_temp_table;
DROP TABLE my_temp_table;
RETURN;