获取最后一个选择查询的行数

Chr*_*ris 3 postgresql

我正在使用一个计划脚本,它将 PostgreSQL 数据库的(新)行导出到一个文本文件中。此脚本的多个实例也为多个 DB 运行:

COPY (SELECT ... FROM ... GROUP BY zzz) TO STDOUT >file.csv
Run Code Online (Sandbox Code Playgroud)

为了对 file.csv 进行一致性检查,我然后运行查询以获取查询的行数COPY

SELECT count(0) FROM ... GROUP BY zzz >linecount
Run Code Online (Sandbox Code Playgroud)

在 bash 脚本中,检查两者是否相等,如果是这种情况,脚本继续运行,否则它会停止并报告错误(这种情况很少发生,但确实发生了 - 我还没有弄清楚原因)

问题,查询结果比较大(大概count(0)5-10分钟),基本上跑了两次(虽然花的时间更短,但还是3-7分钟)

是否有 PostgreSQL 函数来获取最后一个查询的行数?如果是这种情况,我可以大大减少数据库负载并缩短导出时间。

我已经研究过ROW_COUNT,但它似乎只对UPDATE/INSERT而非有效,SELECT出于简单的原因,我还想避免使用函数。

我愿意接受其他建议,例如首先查询临时表,然后从那里导出(也许count(0)会更快)?

Debian 7 Wheezy、SSD、32GB 内存、PostgreSQL 9.1


更新@克雷格林格

我同意一致性检查在设计上有些“缺陷”。我曾经注意到导入检查有一个我无法解释的问题,然后我再次运行导出,并且文件的行与之前的行不同:

Rowcount DB/LinecountF:532395/532014

rowcount: SELECT count(0)... as described originally
linecount  = wc -l
Run Code Online (Sandbox Code Playgroud)

他们作为 cronjobs 运行,我还没有弄清楚为什么这些行丢失了。第二次运行相同的脚本,一切都很好。它很少发生,但日志文件没有说明任何内容(或来自 cron 的邮件结果)。

我没有检查 PSQL 强硬的退出状态(因为我在自己的检查中建立了)。我去做。

hbn*_*hbn 6

如果您愿意放弃写入 STDOUT,您可以使用 PL/pgSQL 函数获得 COPY 导出的行数,如下所示:

CREATE OR REPLACE FUNCTION copyout(query text, output_path text) RETURNS integer AS $fn$
DECLARE
    result integer;
BEGIN
    EXECUTE 'COPY (' || query || $$) TO '$$ || output_path || $$'$$;
    GET DIAGNOSTICS result = ROW_COUNT;
    RETURN result;
END
$fn$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)

执行如下(注意路径在服务器上而不是客户端上):

> SELECT copyout('SELECT * FROM mytable', '/tmp/myfile.csv');
 copyout
---------
     981
(1 row)
Run Code Online (Sandbox Code Playgroud)

但是 - 刚刚发现这是在 9.3 中添加的(请参阅9.3 发行说明)。对不起。

  • 呵呵。我不知道 `COPY` 在 PL/PgSQL 中设置了 `ROW_COUNT`。每天学点东西。如果可以的话,我会+10。 (4认同)