我連接的web瀏覽器到stdin
並在SSH連接的遠程端運行的命令的stdout
。這聽起來像是你正在嘗試做類似的事情:將套接字連接到運行在遠程計算機上的程序,以便客戶端可以連接到主機/端口並使用所述遠程程序。
您需要做的第一件事就是建立一個SSH連接。我在子進程中使用外部程序ssh
(取決於操作系統的ssh
或plink
)。你可以使用類subprocess.Popen
來做到這一點。子進程啓動(外部)ssh
應用程序以連接到遠程主機並運行所需的命令。然後在那裏聽着它的「標準輸入」並願意回覆它的「標準輸出」。
(你可能使用Python SSH實現如的paramiko這裏)
在一個非常高的水平(其中remote_command
是在遠端運行的東西):
import subprocess
command = ['ssh', '[email protected]', 'remote_command']
sproc = subprocess.Popen(command, shell=False,
stdin = subprocess.PIPE,
stdout = subprocess.PIPE,
stderr = subprocess.PIPE)
這留給你一個子進程,你可以通過它的stdin
,stdout
和stderr
進行交互。
獲得此位先工作。
接下來你需要的是綁定一個套接字,監聽並接受一個連接。然後從客戶端讀取並寫入服務器。我寫了一個輕量級的Socat
(由Socat啓發)類:
import socket
class Socat(object):
EOT = '\004\r\n'
def __init__(self, binding, stream, eot = EOT):
self.stream = stream
self.eot = eot
self.socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.socket.bind(binding)
self.socket.listen(5)
while True:
print "waiting for connection"
(clientsocket, address) = self.socket.accept()
print "connection from %s:%s" % address
data = clientsocket.recv(1024)
self.stream.write(data)
while data:
data = self.stream.readline()
if data:
print "read %s bytes" % len(data)
if data == self.eot:
print "read termination signature"
clientsocket.close()
data = None
else:
clientsocket.send(data)
您應該套接字讀了起來:this和this是有用的在這裏。
然後,您可以使用此連接到您的remote_command
:
Socat(('localhost', 8080), sproc)
有些失位
你會注意到socat
類需要在stream
(不像我的例子),其有write
和readline
方法。我實際上將SSH連接封裝在一個班級中,但我會將其作爲練習給讀者!
(基本上包含sproc
並提供write
和readline
方法class Stream
- 有效sproc.stdin.write()
和sproc.stdout.readline()
- !你的想法)
此外,您還需要一個協議,允許remote_command
信號傳輸的結束。我使用ASCII EOT
字符,我的遠程程序在響應結束時發送。 socat
使用它來關閉客戶端連接並接受新連接。根據您的使用情況,您需要提出適用於您的協議。
最後
上述所有可以改進。以上是我第一次削減,因爲它很容易看到內部工作。我已經將它擴展爲在線程中運行接受循環,並優雅地處理斷開連接等。
但希望以上是合理的出發點。
你想要做的是相當明智的。你可能想研究'pexpect'模塊。它是爲這種事情量身定做的:駕駛交互式應用程序。請參閱https://pexpect.readthedocs.io/en/stable/overview.html以取得良好開端。它還有能力在你期待響應但沒有響應的情況下在你的交互中放置超時。 –