2009-08-15 84 views
17

我有一個python應用程序,它打開一個數據庫連接,可以在線掛上幾個小時,但有時候數據庫服務器會重新啓動,而python仍然有連接,它將無法使用OperationalError異常。確保psycopg2數據庫連接有效

所以我正在尋找任何可靠的方法來「ping」數據庫,並知道連接是活着的。我檢查了一個psycopg2文檔,但找不到那樣的東西。當然,我可以發出像SELECT 1一些簡單的SQL語句並捕獲異常,但我希望有一個本地方法,像PHP pg_connection_status

感謝。

回答

8

pg_connection_status使用PQstatus來實現。 psycopg不公開該API,因此該檢查不可用。 psycopg只能調用PQstatus本身的兩個地方是在建立新連接時和執行開始時。所以是的,你需要發出一個簡單的SQL語句來確定連接是否仍然存在。

+0

我在閱讀psycopg2來源時得出了同樣的結論。謝謝。 – HardQuestions 2009-08-15 14:43:39

+0

將向psycopg作者提交請求以添加此功能。 – HardQuestions 2009-08-15 14:46:43

+0

請參閱下面的Jaymon的回答。 – sage88 2017-02-03 08:24:39

30

這個問題確實是老了,但還是彈出在谷歌搜索,所以我認爲這是有價值知道psycopg2.connection實例現在有一個closed attribute這將是0當連接是開放的,且大於零當連接關閉。下面的例子說明了:

import psycopg2 
import subprocess 

connection = psycopg2.connect(
    database=database, 
    user=username, 
    password=password, 
    host=host, 
    port=port 
) 

print connection.closed # 0 

# restart the db externally 
subprocess.check_call("sudo /etc/init.d/postgresql restart", shell=True) 

# this query will fail because the db is no longer connected 
try: 
    cur = connection.cursor() 
    cur.execute('SELECT 1') 
except psycopg2.OperationalError: 
    pass 

print connection.closed # 2 
+3

您是否嘗試過殺死數據庫連接TCP句柄(在Windows上)。 'connection.closed'不幸的是不會改變值。 – Vyktor 2014-11-19 10:01:46

+0

@Vyktor你是對的!問題是,Python的連接不知道它已經被切斷,直到它試圖與數據庫進行通信。我更新了這個例子。好消息是,您可以封裝執行代碼的查詢來檢查錯誤連接並根據需要重新連接。 – Jaymon 2014-12-11 23:17:13

+0

我的連接在查詢過程中因爲數據庫重新啓動而關閉'cur.execute('SELECT 1')'在我的情況下拋出了一個'InterfaceError',消息'cursor already closed' – raphael 2016-08-19 13:57:33

6

connection.closed不反映連接關閉/服務器切斷。它只是表示使用connection.close()

客戶端關閉爲了確保連接仍然有效的連接,讀取屬性connection.isolation_level。這將在pgcode ==「57P01」的情況下引發OperationalError,以防連接中斷。

這爲往返數據庫增加了一點延遲,但應該優於SELECT 1或類似的。

import psycopg2 
dsn = "dbname=postgres" 
conn = psycopg2.connect(dsn) 

# ... some time elapses, e.g. connection within a connection pool 

try: 
    connection.isolation_level 
except OperationalError as oe: 
    conn = psycopg2.connect(dsn) 

c = conn.cursor() 
c.execute("SELECT 1") 
+1

用psycopg2 2.5.2和psql 8.4測試 - 隔離無論如何,等級總是零。 – 2014-02-03 12:05:46