2015-08-05 13 views
9

Wykonuję długo działający skrypt Pythona przez ssh na zdalnej maszynie za pomocą paramiko. Działa jak urok, żadnych problemów do tej pory.Otrzymuję dane wyjściowe z polecenia paramiko ssh exec_command w sposób ciągły

Niestety, standardowe wyjście (odpowiednio stderr) jest wyświetlane tylko po zakończeniu skryptu! Jednak ze względu na czas wykonania zdecydowanie wolałbym, aby wyprowadzał każdą nową linię po wydrukowaniu, a nie później.

remote = paramiko.SSHClient() 
remote.set_missing_host_key_policy(paramiko.AutoAddPolicy()) 
remote.connect("host", username="uname", password="pwd") 

# myScript produces continuous output, that I want to capture as it appears  
stdin, stdout, stderr = remote.exec_command("python myScript.py") 
stdin.close() 
for line in stdout.read().splitlines(): 
    print(line) 

Jak można to osiągnąć?Uwaga: Oczywiście można by rura wyjście do pliku i „mniej” tego pliku za pośrednictwem innej sesji ssh, ale to jest bardzo brzydki i muszę czystsze, idealnie pythonic rozwiązanie :)

+0

aby pomóc innym w przyszłości, myScript.py powinien zawierać sys.stdout.flush() – ItayB

Odpowiedz

8

jak określono w read([size]) documentation, jeśli nie podasz wartości size, będzie ona czytała aż do EOF, co spowoduje, że skrypt zaczeka, aż polecenie zakończy się przed powrotem z read() i wydrukuje dowolne wyjście.

Sprawdź poniższe odpowiedzi: How to loop until EOF in Python? i How to do a "While not EOF", aby zapoznać się z przykładami sposobu wyczuwania obiektu podobnego do pliku.

+8

dzięki @KurzedMetal za wskazanie mi we właściwym kierunku: 'dla linii w iter (lambda: stdout.readline (2048)," "): print (linia, koniec =" ")' ... podstęp! –

7

Miałem do czynienia z podobnym problemem. Udało mi się go rozwiązać dodając get_pty = True do paramiko:

stdin, stdout, stderr = client.exec_command("/var/mylongscript.py", get_pty=True) 
4

minimalną i kompletny pracy przykład jak używać this answer (testowane w Pythonie 3.6.1)

# run.py 
from paramiko import SSHClient 

ssh = SSHClient() 
ssh.load_system_host_keys() 

ssh.connect('...') 

print('started...') 
stdin, stdout, stderr = ssh.exec_command('python -m example', get_pty=True) 

for line in iter(stdout.readline, ""): 
    print(line, end="") 
print('finished.') 

i

# example.py, at the server 
import time 

for x in range(10): 
    print(x) 
    time.sleep(2) 

bieg na lokalnym komputerze z

python -m run 
+1

To nie działa z Pythonem 2.7. – Patryk

+0

@Patryk, czy możesz dokładniej określić, co dokładnie nie działa? –

Powiązane problemy