如何将带有 uuid 的 Select 转换为 java 中的 plpgsql

How to translate a Select with uuid to plpgsql in java

我有以下简单的select:

SELECT * FROM db.table WHERE uuid::varchar LIKE ('389519a6-ba79-4a4d-a696-c818808d3b26');

在 pgadmin v4 中工作得很好。

现在我尝试用 plpgsql 函数做同样的事情:

 queries[0] = "DROP FUNCTION createtemptable(text,text,text);"
            + "CREATE OR REPLACE FUNCTION createTempTable(name TEXT, id TEXT, units TEXT) "
            + "RETURNS void AS $$ "
            + "DECLARE "
            + "nameid TEXT; "
            + "BEGIN "
            + "nameid := name || id;"
            + "EXECUTE 'SET search_path = schema_name; "
            + "CREATE TABLE IF NOT EXISTS ' || quote_ident(nameid) || ' "
            + "AS SELECT * FROM ' || quote_ident(name) || ' "
            + "WHERE uuid LIKE ' || uuid(units) ;"
            + "END; $$ "
            + "LANGUAGE plpgsql;";

导致:

DROP FUNCTION createtemptable(text,text,text);
CREATE OR REPLACE FUNCTION createTempTable(name TEXT, id TEXT, units TEXT)
RETURNS void AS $$ 
DECLARE nameid TEXT; 
BEGIN 
    nameid := name || id;
    EXECUTE 
        'SET search_path = opsim; 
        CREATE TABLE IF NOT EXISTS ' || quote_ident(nameid) || ' AS 
            SELECT * FROM ' || quote_ident(name) || ' 
                WHERE uuid LIKE ' || uuid(units);
END; $$ LANGUAGE plpgsql;

最后我想交出一组单位 uuid 并为它们创建一个 temp_table。在过去的几个小时里,我将错误追溯到顶部的 select。

奇怪的是:它在 pgadmin 中工作得很好,但失败了:

org.postgresql.util.PSQLException: Error: Syntaxerror at „a6“

不管我是将它们都保留为 uuid,还是将它们作为字符串进行比较,它总是在那个时候中断。我也不知道为什么。

根据阿姨 google 和我在过去 4 小时内研究的所有内容,它应该有效。有谁知道我忘记遮盖什么东西或……什么的吗?

编辑:改进了评论中的建议。我不能 quote_ident 个单位,因为这会添加不需要的引号。

使用 format() 安全地格式化动态 SQL 语句:

CREATE OR REPLACE FUNCTION createTempTable(name TEXT, id TEXT, units TEXT) 
   RETURNS void 
AS 
$$ 
BEGIN 
  EXECUTE format(
    'CREATE TABLE IF NOT EXISTS db.%I AS 
     SELECT * 
     FROM db.%I
     WHERE uuid = %L', name||id, name, units);
END; 
$$ LANGUAGE plpgsql;

如果您只传递一个值,我不清楚为什么要使用 where uuid IN (...)

如果要为 UUID 传递多个值,请使用数组而不是逗号分隔的字符串:

CREATE OR REPLACE FUNCTION createTempTable(name TEXT, id TEXT, <b>units TEXT[]</b>) 
   RETURNS void 
AS 
$$ 
BEGIN 
  EXECUTE format(
    'CREATE TABLE IF NOT EXISTS %I AS 
     SELECT * 
     FROM %I
     WHERE uuid::varchar = <b>any()</b>', name||id, name) <b>using units</b>;
END; 
$$ LANGUAGE plpgsql;

你这样使用它:

select createtemptable(
        'anders', 
        'one', 
        array['389519a6-ba79-4a4d-a696-c818808d3b26','389519a6-ba77-4a4d-a696-c818808d3b26']
       );

这是一个例子:http://rextester.com/SOAK47342