在两个套接字之间中继,中断插入自己的命令
Relay between two sockets, interrupt to plug in own commands
我有一个程序 A 通过 tcp 套接字与机器 B 通信。现在我有自己的应用程序 C,它也需要偶尔与 B 通信。所以我希望 C 双向中继 A 和 B 之间的所有通信。一旦 C 必须与 B 通话,中继将停止,到 B 的套接字应该刷新/清空所有等待数据,C 应该与 B 通信,接收它需要的东西,然后 之间的中继]A 和 B 应该重新开始。
我对 Python 中的套接字很陌生,所以我只知道一些基本命令,需要一些指向正确方向的信息才能知道要阅读什么以及要注意什么(或一个完整的示例,如果有人碰巧已经做过类似的事情)。
由于中继应该 运行 在后台,而 C 正在做其他事情而不是与 B 交谈,我也想知道我是否应该对此使用线程,或者是否有更好的选择(在下面引用的问题中,使用了异步)?
我也发现了这个问题Need help creating a TCP relay between two sockets,据我了解,中继部分应该与我的问题类似,但我真的无法辨别中继在哪里完成。
好的,我明白了。这是我的解决方案,在 class 中实现以控制机器:
import struct
import socket
import time
import threading
try:
from configparser import ConfigParser
except ImportError:
from ConfigParser import ConfigParser # ver. < 3.0
class machineClass():
def __init__(self):
self.read_config() # gets IP's and Ports for machine and relay socket and stores them in self.machineIP, self.machinePort, self.relayIP and self.relayPort
self.s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.s.connect((self.machineIP, self.machinePort))
self.stopRelayEvent = threading.Event()
self.relayStoppedEvent = threading.Event()
relaySocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
relaySocket.bind((self.relayIP,self.relayPort))
relayThread = threading.Thread(target=self.relay, args=(relaySocket,self.s,self.stopRelayEvent,self.relayStoppedEvent))
relayThread.start()
print(" Machine [connected]")
def relay(self,relaySocket,machineSocket,stopRelayEvent,relayStoppedEvent):
while 1:
if not relayStoppedEvent.isSet():
relayStoppedEvent.set()
relaySocket.listen(1) # waits for connection from software **B**, in loop because **B** reconnects every now and then. While waiting, connection is not blocked for **C** because relayStoppedEvent is set.
relayCon, relayAddr = relaySocket.accept()
relayStoppedEvent.clear()
print('Connected with Software **B** on ' + relayAddr[0] + ':' + str(relayAddr[1]))
while 1:
if not stopRelayEvent.isSet():
if relayStoppedEvent.isSet():
relayStoppedEvent.clear()
data = relayCon.recv(84)
if len(data) == 0:
break # in case connection is lost, break loop and go back to waiting for new connection.
machineSocket.send(data)
relayCon.send(machineSocket.recv(84))
else:
relayStoppedEvent.set()
data = relayCon.recv(84)
def sendDataToMachine(self,data): # Function for **C** to send data to machine **B**
self.stopRelayEvent.set()
self.relayStoppedEvent.wait()
self.s.send(data)
time.sleep(.1)
return_data = self.s.recv(84)
self.stopRelayEvent.clear()
return return_data
我有一个程序 A 通过 tcp 套接字与机器 B 通信。现在我有自己的应用程序 C,它也需要偶尔与 B 通信。所以我希望 C 双向中继 A 和 B 之间的所有通信。一旦 C 必须与 B 通话,中继将停止,到 B 的套接字应该刷新/清空所有等待数据,C 应该与 B 通信,接收它需要的东西,然后 之间的中继]A 和 B 应该重新开始。
我对 Python 中的套接字很陌生,所以我只知道一些基本命令,需要一些指向正确方向的信息才能知道要阅读什么以及要注意什么(或一个完整的示例,如果有人碰巧已经做过类似的事情)。
由于中继应该 运行 在后台,而 C 正在做其他事情而不是与 B 交谈,我也想知道我是否应该对此使用线程,或者是否有更好的选择(在下面引用的问题中,使用了异步)?
我也发现了这个问题Need help creating a TCP relay between two sockets,据我了解,中继部分应该与我的问题类似,但我真的无法辨别中继在哪里完成。
好的,我明白了。这是我的解决方案,在 class 中实现以控制机器:
import struct
import socket
import time
import threading
try:
from configparser import ConfigParser
except ImportError:
from ConfigParser import ConfigParser # ver. < 3.0
class machineClass():
def __init__(self):
self.read_config() # gets IP's and Ports for machine and relay socket and stores them in self.machineIP, self.machinePort, self.relayIP and self.relayPort
self.s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
self.s.connect((self.machineIP, self.machinePort))
self.stopRelayEvent = threading.Event()
self.relayStoppedEvent = threading.Event()
relaySocket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
relaySocket.bind((self.relayIP,self.relayPort))
relayThread = threading.Thread(target=self.relay, args=(relaySocket,self.s,self.stopRelayEvent,self.relayStoppedEvent))
relayThread.start()
print(" Machine [connected]")
def relay(self,relaySocket,machineSocket,stopRelayEvent,relayStoppedEvent):
while 1:
if not relayStoppedEvent.isSet():
relayStoppedEvent.set()
relaySocket.listen(1) # waits for connection from software **B**, in loop because **B** reconnects every now and then. While waiting, connection is not blocked for **C** because relayStoppedEvent is set.
relayCon, relayAddr = relaySocket.accept()
relayStoppedEvent.clear()
print('Connected with Software **B** on ' + relayAddr[0] + ':' + str(relayAddr[1]))
while 1:
if not stopRelayEvent.isSet():
if relayStoppedEvent.isSet():
relayStoppedEvent.clear()
data = relayCon.recv(84)
if len(data) == 0:
break # in case connection is lost, break loop and go back to waiting for new connection.
machineSocket.send(data)
relayCon.send(machineSocket.recv(84))
else:
relayStoppedEvent.set()
data = relayCon.recv(84)
def sendDataToMachine(self,data): # Function for **C** to send data to machine **B**
self.stopRelayEvent.set()
self.relayStoppedEvent.wait()
self.s.send(data)
time.sleep(.1)
return_data = self.s.recv(84)
self.stopRelayEvent.clear()
return return_data