我将列名存储在变量colls
中,然后执行代码:
DO $$
DECLARE
v_name text := quote_ident('colls');
BEGIN
EXECUTE 'insert into table1 select '|| colls ||' from table2 ';
-- EXECUTE 'insert into table1 select '|| v_name ||' from table2 ';
END$$;
我收到了错误: column" colls"不存在。程序使用colls
作为名称而不是变量。我做错了什么?
我在文档中找到了类似的例子:
https://www.postgresql.org/docs/8.1/static/plpgsql-statements.html#PLPGSQL-STATEMENTS-EXECUTING-DYN
答案 0 :(得分:1)
我的列名存储在变量
中colls
不,你没有。您有一个变量v_name
- 其中包含单个字:'colls'
。关于SQL中的变量:
阅读手册中的章节Identifiers and Key Words和Constants。
如果您在单个变量中有多个列名称,则无法使用quote_ident()
。它会将整个字符串作为单个标识符进行转义。
我想基本的误解是这样的:'colls'
是字符串常量,而不是变量。 DO
语句中没有其他变量,而不是DECLARE
部分中声明的变量。您可能正在寻找 一个函数,该函数将可变数量的列名称作为参数 ......
CREATE OR REPLACE FUNCTION f_insert_these_columns(VARIADIC _cols text[])
RETURNS void AS
$func$
BEGIN
EXECUTE (
SELECT 'INSERT INTO table1 SELECT '
|| string_agg(quote_ident(col), ', ')
|| ' FROM table2'
FROM unnest(_cols) col
);
END
$func$ LANGUAGE plpgsql;
呼叫:
SELECT f_insert_these_columns('abd', 'NeW Deal'); -- column names case sensitive!
SELECT f_insert_these_columns(VARIADIC '{abd, NeW Deal}'); -- column names case sensitive!
请注意我如何删除列名称数组并逐个转义
VARIADIC
参数应该适合您的用例。您可以传递列名列表或数组
无论哪种方式,都可以使用不同的SQL注入
相关,有更多解释: