如何在不创建函数的情况下 运行 plpgsql?
How to run plpgsql without creating a function?
我想在 Postgres 中以编程方式 运行 a SQL 而无需创建函数。
原因:确保我的 plpgsql 事先工作并在将查询提交给函数之前 "explain analyze" 查询。
我是 Postgres 的新手,我认为这很简单。我在那里找不到任何例子。也许这是不可能的?下面的代码如何工作?
DO
$body$
DECLARE
v_name_short VARCHAR;
BEGIN
v_name_short := 'test Account 1';
RETURN QUERY
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN v_name_short IS NOT NULL THEN
LOWER(a.name_short) = LOWER(v_name_short)
ELSE
1 = 1
END;
END;
$body$
LANGUAGE 'plpgsql';
同样,这里的目标是测试我的 SQL,就像在本例中一样,我想确保我的 CASE 语句仍在使用我创建的索引 (LOWER(name_short))。无论如何,我收到此错误消息:
ERROR: cannot use RETURN QUERY in a non-SETOF function
我问的问题在 Postgres 中可行吗?如果没有,有没有办法在函数内查询分析计划?
一个do
匿名代码块总是returnsvoid
:
The code block is treated as though it were the body of a function with no parameters, returning void
要在 do
块内执行查询,请使用 perform
do $$
begin
perform * from t;
end
$$;
匿名代码块returns无效。但是,您可以使用临时 table 的技巧,例如
CREATE TEMP TABLE IF NOT EXISTS trace (name_short text, name_long text);
DO
$body$
DECLARE
v_name_short VARCHAR;
BEGIN
v_name_short := 'test Account 1';
INSERT INTO trace
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN v_name_short IS NOT NULL THEN
LOWER(a.name_short) = LOWER(v_name_short)
ELSE
1 = 1
END;
END;
$body$
LANGUAGE 'plpgsql';
SELECT * FROM trace;
-- DROP TABLE trace;
使用 EXPLAIN ANALYSE
您只能分析一个简单的 sql 查询,不能分析函数、do 块或脚本。所以你可以试试:
EXPLAIN ANALYSE
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN 'test Account 1' IS NOT NULL THEN
LOWER(a.name_short) = LOWER('test Account 1')
ELSE
1 = 1
END;
请注意,在这种情况下,您不能使用变量,因为规划器无法识别它,请改用文字。
常规 PL/pgSQL 函数和 DO
语句之间存在第三个(未记录的)选项:临时函数:
- How to create a temporary function in PostgreSQL?
- Is there such thing as a "temp function"?
你实际上 可以 得到详细的查询计划每个 SQL 语句在 plpgsql 函数中使用额外的模块 auto-explain。详情:
但是您必须使用 CASE
表达式中每个分支的值来测试您的函数,以确保涵盖所有内容。 Postgres 仅对 CREATE FUNCTION
.
进行表面语法检查
Prepared statements 可能是另一种选择。 PL/pgSQL 在内部处理 SQL 语句,如准备好的语句:
- Difference between language sql and language plpgsql in PostgreSQL functions
我想在 Postgres 中以编程方式 运行 a SQL 而无需创建函数。
原因:确保我的 plpgsql 事先工作并在将查询提交给函数之前 "explain analyze" 查询。
我是 Postgres 的新手,我认为这很简单。我在那里找不到任何例子。也许这是不可能的?下面的代码如何工作?
DO
$body$
DECLARE
v_name_short VARCHAR;
BEGIN
v_name_short := 'test Account 1';
RETURN QUERY
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN v_name_short IS NOT NULL THEN
LOWER(a.name_short) = LOWER(v_name_short)
ELSE
1 = 1
END;
END;
$body$
LANGUAGE 'plpgsql';
同样,这里的目标是测试我的 SQL,就像在本例中一样,我想确保我的 CASE 语句仍在使用我创建的索引 (LOWER(name_short))。无论如何,我收到此错误消息:
ERROR: cannot use RETURN QUERY in a non-SETOF function
我问的问题在 Postgres 中可行吗?如果没有,有没有办法在函数内查询分析计划?
一个do
匿名代码块总是returnsvoid
:
The code block is treated as though it were the body of a function with no parameters, returning void
要在 do
块内执行查询,请使用 perform
do $$
begin
perform * from t;
end
$$;
匿名代码块returns无效。但是,您可以使用临时 table 的技巧,例如
CREATE TEMP TABLE IF NOT EXISTS trace (name_short text, name_long text);
DO
$body$
DECLARE
v_name_short VARCHAR;
BEGIN
v_name_short := 'test Account 1';
INSERT INTO trace
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN v_name_short IS NOT NULL THEN
LOWER(a.name_short) = LOWER(v_name_short)
ELSE
1 = 1
END;
END;
$body$
LANGUAGE 'plpgsql';
SELECT * FROM trace;
-- DROP TABLE trace;
使用 EXPLAIN ANALYSE
您只能分析一个简单的 sql 查询,不能分析函数、do 块或脚本。所以你可以试试:
EXPLAIN ANALYSE
SELECT
a.name_short,
a.name_long
FROM enterprise.account a
WHERE
CASE WHEN 'test Account 1' IS NOT NULL THEN
LOWER(a.name_short) = LOWER('test Account 1')
ELSE
1 = 1
END;
请注意,在这种情况下,您不能使用变量,因为规划器无法识别它,请改用文字。
常规 PL/pgSQL 函数和 DO
语句之间存在第三个(未记录的)选项:临时函数:
- How to create a temporary function in PostgreSQL?
- Is there such thing as a "temp function"?
你实际上 可以 得到详细的查询计划每个 SQL 语句在 plpgsql 函数中使用额外的模块 auto-explain。详情:
但是您必须使用 CASE
表达式中每个分支的值来测试您的函数,以确保涵盖所有内容。 Postgres 仅对 CREATE FUNCTION
.
Prepared statements 可能是另一种选择。 PL/pgSQL 在内部处理 SQL 语句,如准备好的语句:
- Difference between language sql and language plpgsql in PostgreSQL functions