Создание рекурсивных потоков соединений - PullRequest
0 голосов
/ 19 декабря 2011

Я создаю новый поток подключения каждый раз, когда устанавливается соединение с клиентом.Однако во второй раз, когда я запускаю клиентский скрипт, я получаю сообщение об ошибке, почему?

Клиент

from multiprocessing.connection import Client
conn = Client(('localhost', 5555), authkey='secret_password')
conn.send('Hello World!')
conn.close()

Сервер

import time
from multiprocessing.connection import Listener
from threading import Thread

_threads = []
_listener = Listener(('localhost', 5555), authkey='secret_password')

def start_server_thread():
    global _threads
    _threads.append(Thread(target=threaded_server))
    _threads[-1].daemon = True
    _threads[-1].start()

def threaded_server():
    conn = _listener.accept()
    print str(conn.recv())
    conn.close()
    _listener.close()

if __name__ == "__main__":
    start_server_thread()
    while True:
        time.sleep(1)

Ошибка

Traceback (most recent call last):
  File "C:\dev\spyker\t2.py", line 3, in <module>
    conn = Client(('localhost', 5555), authkey='secret_password')
  File "C:\Python26\lib\multiprocessing\connection.py", line 143, in Client
    c = SocketClient(address)
  File "C:\Python26\lib\multiprocessing\connection.py", line 263, in SocketClient
    s.connect(address)
  File "<string>", line 1, in connect
socket.error: [Errno 10061] No connection could be made because the target machine actively refused it

Ответы [ 3 ]

2 голосов
/ 19 декабря 2011

У вас есть несколько проблем с этим кодом сервера.

Вы закрываете прослушиватель после первого подключения

Вы не зацикливаетесь на дополнительных соединениях

import time
from multiprocessing.connection import Listener
from threading import Thread

_threads = []

def start_server_thread():
    global _threads
    _threads.append(Thread(target=threaded_server))
    _threads[-1].daemon = True
    _threads[-1].start()

def threaded_server():
    while True:
        conn = _listener.accept()
        print str(conn.recv())
        conn.close()


if __name__ == "__main__":
    _listener = Listener(('localhost', 5555), authkey='secret_password')

    start_server_thread()
    while True:
        time.sleep(1)

    _listener.close()

Отказ от ответственности: я думаю, что это довольно грязный способ написать сервер. Я публикую только исправление для вашего текущего кода: -)

Вот слегка очищенная версия того же кода. Все еще не на 100% идеален, но чище, я думаю?

import time
from multiprocessing.connection import Listener
from threading import Thread

class Server(Listener):

    def __init__(self, *args, **kwargs):
        super(Server, self).__init__(*args, **kwargs)
        self._thread = None
        self._stopping = False


    def serve(self):
        self._stopping = False
        self._thread = Thread(target=self._serve)
        self._thread.daemon = True
        self._thread.start()

    def _serve(self):
        threads = []
        while not self._stopping:
            conn = self.accept()
            t = Thread(target=self.handleConnection, args=(conn,))
            t.start()
            threads.append(t)


    def stop(self):
        if not self._stopping:
            print "Stopping."
            self._stopping = True
            self._thread.join(3)
            self.close()  

    def handleConnection(self, conn):
        print str(conn.recv())
        conn.close()        


if __name__ == "__main__":
    listener = Server(('localhost', 5555), authkey='secret_password')
    listener.serve()

    try:
        while True:
            time.sleep(1)
    except KeyboardInterrupt, e:
        listener.stop()
2 голосов
/ 19 декабря 2011

Обнаружено несколько ошибок:

  • Возможно, вы хотите, чтобы ваш thread-сервер имел бесконечный цикл и принимал более одного соединения. Сейчас он принимает только первый и существует.
  • Вы закрываете слушателя после окончания обработки, что, вероятно, не то, что вы хотите. Вы можете принять больше подключений, используя тот же слушатель.

Правильный threadaded_server ():

def threaded_server():
    while True:
        conn = _listener.accept()
        print str(conn.recv())
        conn.close()
0 голосов
/ 20 декабря 2011

Исправленный код, используя советы из других ответов.Исправленные строки отмечены:

import time
from multiprocessing.connection import Listener
from threading import Thread

_threads = []
_listener = Listener(('localhost', 5555), authkey='secret_password')

def start_server_thread():
    global _threads
    _threads.append(Thread(target=threaded_server))
    _threads[-1].daemon = True
    _threads[-1].start()

def threaded_server():
    conn = _listener.accept()
    start_server_thread()         # <== each connection creates the next one
    print str(conn.recv())
    conn.close()
                                  # <== removed _listener.close()
if __name__ == "__main__":
    start_server_thread()
    try:                          # <==
        while True:
            time.sleep(1)
    except KeyboardInterrupt, e:  # <== catch ^c
        _listener.close()         # <==
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...