2013-11-11 3 views
4

Я пытаюсь открыть SSH-трубу из одного Linux-бокса в другой, запустить несколько команд оболочки, а затем закрыть SSH.Подпроцесс Python - запуск нескольких команд оболочки по SSH

У меня нет контроля над пакетами на любой коробке, поэтому что-то вроде ткани или парамико не может быть и речи.

Мне посчастливилось использовать следующий код для запуска одной команды bash, в данном случае «время безотказной работы», но я не уверен, как выпустить одну команду за другой. Я ожидаю что-то вроде:

sshProcess = subprocess.call('ssh ' + <remote client>, <subprocess stuff>) 
lsProcess = subprocess.call('ls', <subprocess stuff>) 
lsProcess.close() 
uptimeProcess = subprocess.call('uptime', <subprocess stuff>) 
uptimeProcess.close() 
sshProcess.close() 

Какую часть модуля подпроцесса мне не хватает?

Благодаря

pingtest = subprocess.call("ping -c 1 %s" % <remote client>,shell=True,stdout=open('/dev/null', 'w'),stderr=subprocess.STDOUT) 
if pingtest == 0: 
    print '%s: is alive' % <remote client> 
    # Uptime + CPU Load averages 
    print 'Attempting to get uptime...' 
    sshProcess = subprocess.Popen('ssh '+<remote client>, shell=True,stdout=subprocess.PIPE, stderr=subprocess.STDOUT) 
    sshProcess,stderr = sshProcess.communicate() 
    print sshProcess 
    uptime = subprocess.Popen('uptime', shell=True,stdout=subprocess.PIPE, stderr=subprocess.STDOUT) 
    uptimeProcess,stderr = uptimeProcess.communicate() 
    uptimeProcess.close() 
    print 'Uptime   : ' + uptimeProcess.split('up ')[1].split(',')[0] 
else: 
    print "%s: did not respond" % <remote client> 
+0

Возможно, вам понравилась ткань, которая представляет собой структуру, которая уже делает вид вещей, которые вы хотите использовать http: //fabric.readthedocs .org/ru/1.8/# – Vorsprung

+0

Я согласен, что Fabric был бы полезен. К сожалению, я не контролирую ни одну из них, просто получаю доступ. – user2978190

ответ

10

в основном, если вы звоните подпроцесс создает локальный подпроцесс не удаленный один , так что вы должны взаимодействовать с процессом SSH. так что что-то в этом роде: , но имейте в виду, что если вы динамически создаете мой каталог, то он вполне подходит для инъекции оболочки, тогда строка END должна быть уникальным идентификатором Чтобы избежать уникальности проблемы с концом END, самым простым способом было бы использовать разные ssh команда

from __future__ import print_function,unicode_literals 
import subprocess 

sshProcess = subprocess.Popen(['ssh', 
           <remote client>], 
           stdin=subprocess.PIPE, 
           stdout = subprocess.PIPE, 
           universal_newlines=True, 
           bufsize=0) 
sshProcess.stdin.write("ls .\n") 
sshProcess.stdin.write("echo END\n") 
sshProcess.stdin.write("uptime\n") 
sshProcess.stdin.write("echo END\n") 
sshProcess.stdin.close() 


for line in sshProcess.stdout: 
    if line == "END\n": 
     break 
    print(line,end="") 

for line in sshProcess.stdout: 
    if line == "END\n": 
     break 
    print(line,end="") 

EDIT

  • отсутствует sshProcess & \ п
  • отсутствующего sshProcess.stdout
  • нужно закрыть стандартный ввод, чтобы быть уверенными, чтобы собрать на вход
  • приспосабливается к Python3 и python2

EDIT 2

  • добавить недостающий кронштейн Popen вызова

EDIT 3 - удалить ненужный имп ort (спасибо отклоненному правилу от Domen Blenkuš) - префикс слишком длинной строки

+0

Я получал сообщение об ошибке, что stdin не был распознан, поэтому я добавил имя модуля. Теперь он просто зависает, пока я не CTRL + C. sshProcess = subprocess.Popen ([ 'SSH', remoteClient], STDIN = subprocess.PIPE, стандартный вывод = subprocess.PIPE) sshProcess.stdin.write ('LS') sshProcess.stdin.write (» эхо END ') для линии в sshProcess.stdout.readlines(): если строка == "END \ N": перерыв печати (линия) sshProcess.stdin.write ("Провел") sshProcess.stdin ,написать («эхо-END») для линии в sshProcess.stdout.readlines(): если строка == «END \ п»: перерыв печати (линия) Человек это форматирование является боль в приклад. – user2978190

+0

Я отредактировал свой ответ. Я думаю, что это не так. \ N –

+0

жаль, что вы публикуете в старом вопросе, но когда я пытаюсь это сделать, я получаю 'IOError: файл не открыт для чтения' в строке' для строки в stdout.readlines(): '. Я использовал 'sys import stdout'. Я искал ее, но не повезло. Любая идея, почему это может быть? – Greg

Смежные вопросы