您如何释放未被客户端应用程序正确关闭的 PostgreSQL 连接?
我有一个数据挖掘应用程序,可以启动多个进程,所有进程都连接到本地 PostgreSQL 9.1 数据库以检索数据。它运行了几个小时,但随后因错误而死:
FATAL: remaining connection slots are reserved for non-replication superuser connections
Run Code Online (Sandbox Code Playgroud)
对此进行研究表明,这很可能是由于应用程序未正确关闭其连接造成的。然而,即使应用程序被杀死,这些连接也永远不会被释放。PostgreSQL 是否会自动关闭连接,是否存在某种超时?
我还尝试将 Postgres 的 max_connections 从 100 增加到 200,但是重新启动给了我错误:
2014-02-23 10:51:15 EST FATAL: could not create shared memory segment: Invalid argument
2014-02-23 10:51:15 EST DETAIL: Failed system call was shmget(key=5432001, size=36954112, 03600).
2014-02-23 10:51:15 EST HINT: This error usually means that PostgreSQL's request for a shared memory segment exceeded your kernel's SHMMAX parameter. You can either reduce the request size or reconfigure the kernel with larger SHMMAX. To reduce the request size (currently 36954112 bytes), reduce PostgreSQL's shared memory usage, perhaps by reducing shared_buffers or max_connections.
If the request size is already small, it's possible that it is less than your kernel's SHMMIN parameter, in which case raising the request size or reconfiguring SHMMIN is called for.
The PostgreSQL documentation contains more information about shared memory configuration.
Run Code Online (Sandbox Code Playgroud)
我的系统是 Ubuntu 12.04,有 8GB 内存,所有其他 PG 设置都是默认设置,所以我不确定为什么它认为系统没有足够的内存。
然后我尝试使用 pgbouncer 来汇集和重用连接。这似乎工作得更好一点,但即使这样最终也没有连接,给我错误:
ERROR: no more connections allowed
Run Code Online (Sandbox Code Playgroud)
如何进一步诊断和解决此问题?
您可以通过更改最大共享内存设置来增加最大连接数,但是如果问题是您的连接没有被关闭,那么您应该真正解决这个问题。如果软件不受您的控制并且由于未关闭连接而出现故障,您可以使用一些 cron 作业,例如:
select pg_terminate_backend(procpid)
from pg_stat_activity
where usename = 'yourusername'
and current_query = '<IDLE>'
and query_start < current_timestamp - interval '5 minutes'
;
Run Code Online (Sandbox Code Playgroud)
这就是我为消除来自类似错误软件的泄漏连接所做的工作。
或者,您可以通过连接池运行有问题的软件,该连接池具有类似的功能来终止空闲连接,例如 pgpool。
注意:较新版本的 Postgres 列名略有不同:
select pg_terminate_backend(pid)
from pg_stat_activity
where usename = 'YOURDATABASEUSERNAME*'
and state = 'idle'
and query_start < current_timestamp - interval '5 minutes'
;
Run Code Online (Sandbox Code Playgroud)
| 归档时间: |
|
| 查看次数: |
38937 次 |
| 最近记录: |