【发布时间】:2014-12-31 16:46:40
【问题描述】:
问题描述
我正在使用 psycopg2 连接到远程主机上的 PostgreSQL 数据库。我打开一个连接并等待请求,然后对于每个请求,我对连接运行查询并返回数据。
但是当连接已经打开后网络连接丢失时,下一个数据库查询挂起,我必须手动终止程序。
详情:
- 它至少挂了 2 个小时(我等不及了)
- “网络宕机”的情况实际上是 VPN 宕机(db 主机只能通过 VPN 访问)
- 我不能使用异步连接,因为我需要事务
- python 2.6
- psycopg 2.2.1
- debian linux 6 和 7、64 位
- postgresql 8.4 和 9.1
我想要/需要什么
在运行查询之前,我需要一些可靠的方法来检测失败的连接,这样我的程序就不会挂起,或者让cursor.execute(..) 在连接失败时引发异常。 p>
示例:
import psycopg2
import time
conn = psycopg2.connect("host='dbs' dbname='foo' user='joe' password='x'")
time.sleep(10) # I manually turn VPN off during this sleep..
cu = conn.cursor()
cu.execute('SELECT 1') # <- hangs here
print cu.fetchone()
cu.commit()
我尝试了什么(什么没用):
-
“全局”设置 TCP 超时 - 在 psycopg2 导入之前,我添加了:
import socket socket.setdefaulttimeout(10) -
在
psycopg.connection的套接字上设置 TCP 超时:.. conn = psycopg2.connect(... s = socket.fromfd(conn.fileno(), socket.AF_INET, socket.SOCK_STREAM) s.settimeout(5) .. -
为
psycopg.connection的套接字启用keepalive:... conn = psycopg2.connect(... s = socket.fromfd(conn.fileno(), socket.AF_INET, socket.SOCK_STREAM) s.settimeout(5) s.setsockopt(socket.SOL_SOCKET, socket.SO_KEEPALIVE, 1) s.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPIDLE, 1) s.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPINTVL, 3) s.setsockopt(socket.IPPROTO_TCP, socket.TCP_KEEPCNT, 5) ...
【问题讨论】:
-
Jan,你找到解决办法了吗?我们在 2016 年也面临同样的问题:)
-
@scythargon:嗯,有点……我重写了所有需要在 plpgsql 中进行事务的东西,并切换到异步连接。我不会称其为解决方案..更像是一种解决方法..我花了比我感到舒服的时间更多的时间,但我没有其他办法..
标签: python postgresql tcp timeout psycopg2