2011-08-23 92 views
9

我正在調試一些代碼,這將導致我不斷登錄/退出某些外部sftp服務器。有誰知道如果paramiko自動關閉外部服務器上的ssh/sftp會話,如果在代碼中引發了非paramiko異常?我無法在文檔中找到它,並且由於每次迭代都必須儘早完成連接,因此我不想以20個打開的連接結束連接。paramiko關閉ssh連接上一個非paramiko例外

回答

15

不,paramiko不會自動關閉ssh/sftp會話。如果例外由paramiko編碼或其他方式產生,這並不重要; paramiko代碼中沒有捕獲任何異常並自動關閉它們,所以你必須自己做。

可以確保它被封閉在一個嘗試它包裹/ finally塊,像這樣:

client = None 
try: 
    client = SSHClient() 
    client.load_system_host_keys() 
    client.connect('ssh.example.com') 
    stdin, stdout, stderr = client.exec_command('ls -l') 
finally: 
    if client: 
     client.close() 
+0

謝謝你,問題是我正在調試幾千行代碼(並且仍在添加它)。 paramiko沒有提出例外情況,但在其他地方出現問題時,可以通過「subprocess」或「os」等方式說明。我想我可以在每個異常中都放置一個'client.close()',但這不是很漂亮。 – Ben

+2

如果你將調用放在'try'塊內的'subprocess'或'os',那麼無論產生什麼異常,總是會調用finally子塊。如果你想讓它變得更漂亮,那麼你可能想要將客戶端包裝在一個'Context Manager'中並使用'with'語句。 http://docs.python.org/reference/datamodel.html#context-managers – aculich

+0

這位先生是一個點,所以+1!不回答這個問題,並且如果所有的終端都是相同的,那麼把每個單獨的東西放在'try ... finally'塊中是沒有意義的。但是,把呼叫放到一個班級裏面沒什麼問題,所以我總是很乾淨地關閉它。 – Ben

3

SSHClient()可以作爲一個上下文管理器,所以你可以做

with SSHClient() as ssh: 
    ssh.connect(...) 
    ssh.exec_command(...) 

而不是手動關閉。