![](/img/trans.png)
[英]Is it possible to reuse scalar result from a single subquery in insert query in Postgres?
[英]Is tracking the query PID, from the client, possible in Postgres?
我们有一个客户端应用程序,可以对大型数据集进行非常复杂的报告。 左侧是一棵可能包含在报告中的列的树,而右侧是我们动态填充结果的表。
当用户单击要包含在报告中的列时,我们将构建必要的SQL(通常包括很多联接和复杂的子查询),并异步触发这些查询。
问题:用户正在创建复杂的报表,从而导致非常复杂且成本高昂的查询。 这些查询最终将导致备份,并导致我们用尽连接。
我最终在日志中找到如下部分:
169077:2019-09-11 22:14:29 UTC LOG: duration: 65018.497 ms execute <unnamed>:
169105:2019-09-11 22:14:31 UTC LOG: duration: 22494.712 ms execute <unnamed>: SELEC
169129:2019-09-11 22:14:34 UTC LOG: duration: 67866.947 ms execute <unnamed>:
169157:2019-09-11 22:14:40 UTC LOG: duration: 51176.815 ms execute <unnamed>:
169185:2019-09-11 22:14:41 UTC LOG: duration: 51836.988 ms execute <unnamed>:
169213:2019-09-11 22:14:42 UTC LOG: duration: 52655.482 ms execute <unnamed>:
169244:2019-09-11 22:14:46 UTC LOG: duration: 55871.561 ms execute <unnamed>:
哎哟! 您可以在时间戳记上看到,这是一个用户添加了更多他们想报告的列(我通过查询来确认),非常高兴地没有意识到数据库正在经历的痛苦。
这是我想到的一些解决方案:
1)删除异步查询,使最终用户首先构建报告,然后单击一个按钮以实际运行它。 这不是理想的选择,因为如果我们进行了此更改(很遗憾,这是UX题外话),我们当前的用户群(相当大)肯定会感到困惑。
2)当最终用户单击列并且异步触发查询时,以某种方式跟踪在Postgres中实际运行的查询的PID。 当同一用户单击另一列时,终止先前的PID,并开始跟踪新的PID。 这样可以确保在任何给定时间在报表构建过程中仅为此终端用户运行一个查询,并且可以防止长时间运行的查询积累,如上例所示。
#2可能吗? 我用探针考察了可能的跟踪,并简要地看了一下PGBouncer,但是我对两者都不是很熟悉,也无法找到确切的答案。
欢迎任何想法或建议!
这是在客户端实施#2的通用方法。
看起来您正在使用pg_backend_pid
函数。
建立连接后调用它,记住您的PID
,然后使用该连接和PID
启动异步查询。
如果事实证明您稍后需要停止查询,请使用pg_cancel_backend
和先前记住的PID
来取消查询。
或者,您可以使用特定于您用于连接到Postgres的库的函数。
例如,如果使用libpq,则可以使用PQcancel
函数停止查询。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.