是否可以在 psql 中组合“-c”和“-v”?

Is it possible to combine `-c` and `-v` in psql?

摘要

为什么这不起作用:

$ psql -X -h localhost -d mydatabase -U postgres -v myschema=foo -c "SELECT :'myschema';"
ERROR:  syntax error at or near ":"
LINE 1: SELECT :'myschema';
               ^

但这按预期工作:

$ psql -X -h localhost -d mydatabase -U postgres -v myschema=foo

mydatabase=# SELECT :'myschema';
 ?column? 
----------
 foo
(1 row)

是否可以在 psql 调用中组合 -c-v

上下文

我正在尝试执行 DO (this one) PostgreSQL statement with psql -c from a bash script, where I want to pass one of the WHERE conditions as a psql variable

像这样:

SCHEMA='foo'

! read -d '' sql_query << "EOF"
DO
$func$
BEGIN
   -- RAISE NOTICE '%', 
   EXECUTE
   (SELECT 'TRUNCATE TABLE ' || string_agg(oid::regclass::text, ', ') || ' CASCADE'
    FROM   pg_class
    WHERE  relkind = 'r'  -- only tables
    AND    relnamespace = :'myschema'::regnamespace
   );
END
$func$;    
EOF

psql -h localhost -U postgres -d mydatabase -v myschema="${SCHEMA}" -c "${sql_query}"

但它失败了:

ERROR:  syntax error at or near ":"
LINE 9:     AND    relnamespace = :'myschema'::regnamespace

尝试调试问题我只写了这个简单的查询:

psql -v myschema=foo -h localhost -d mydatabase -U postgres -c "SELECT :myschema;"
ERROR:  42601: syntax error at or near ":"
LINE 1: SELECT :myschema
               ^
LOCATION:  scanner_yyerror, scan.l:1087

或其变体如:

psql -v myschema="'foo'" -h localhost -d mydatabase -U postgres -c "SELECT :myschema;"
psql -v myschema 'foo' -h localhost -d mydatabase -U postgres -c "SELECT :myschema;"
psql -v myschema=foo -h localhost -d mydatabase -U postgres -c "SELECT :'myschema';"

两者都不起作用。

那么问题来了。可以在 psql 调用中组合 -c-v

DO 语句和 psql 变量

感谢评论,我发现 混合 DO 语句和 psql 变量。

或将其修复为 bash 级别。我就是这样做的:

SCHEMA='foo'

! read -d '' sql_query << EOF
DO
$func$
BEGIN
   -- RAISE NOTICE '%', 
   EXECUTE
   (SELECT 'TRUNCATE TABLE ' || string_agg(oid::regclass::text, ', ') || ' CASCADE'
    FROM   pg_class
    WHERE  relkind = 'r'  -- only tables
    AND    relnamespace = '${SCHEMA}'::regnamespace
   );
END
$func$;    
EOF

psql -h localhost -U postgres -d mydatabase -c "${sql_query}"

但问题仍然是如何(如果可能的话)psql 变量可以与 -c

一起使用

So the question is. It's is possible to combine -c and -v in a psql call.

不,psql 不会扩展命令行传递的查询中的变量。 它隐含在 documentation 中,由下面以粗体显示的位表示:

-c command
--command=command

Specifies that psql is to execute the given command string, command. This option can be repeated and combined in any order with the -f option. When either -c or -f is specified, psql does not read commands from standard input; instead it terminates after processing all the -c and -f options in sequence.

command must be either a command string that is completely parsable by the server (i.e., it contains no psql-specific features), or a single backslash command.