Python asynchat:如何存储个别连接的信息,以及如何知道客户端何时断开连接

1 投票
1 回答
720 浏览
提问于 2025-04-16 22:13

为了好玩,我正在用asynchat写一个简单的IRC服务器。我想弄清楚一些基本概念(我具体的问题在代码后面)。我决定不使用Twisted的任何东西,这样我可以自己实现更多功能。首先,这是我写的代码:

import asyncore,asynchat
import socket

class Connection(asynchat.async_chat):
    def __init__(self, server, sock, addr):
        asynchat.async_chat.__init__(self, sock)
        self.set_terminator('\n')
        self.data = ""
        print "client connecting:",addr
        # do some IRC protocol initialization stuff here

    def collect_incoming_data(self, data):
        self.data = self.data + data

    def found_terminator(self):
        print self.data
        self.data = ''

class Server(asyncore.dispatcher):
    def __init__(self, host, port):
        asyncore.dispatcher.__init__(self)
        self.create_socket(socket.AF_INET, socket.SOCK_STREAM)
        self.bind((host, port))
        self.listen(5)

    def handle_accept(self):
        conn, addr = self.accept()
        Connection(self, conn, addr)

    def handle_close(self):
        self.close()

s = Server('127.0.0.1',5006)
asyncore.loop()

在我看来,这段代码的结构和Twisted的客户端工厂很像:Server类只初始化一次,每当有客户端连接时,它基本上会实例化一个Connection。第一个问题是:在Server中用一个列表来存储所有连接的客户端,这样跟踪它们是否是最好的方法?

另外,我不明白我该如何知道某个特定的客户端何时关闭了与我的socket的连接?Connection实现了asynchat(以及asyncore),但是在Connection类中添加handle_close()这个回调函数并不会在客户端断开连接时触发。看起来这个回调只在服务器上的绑定socket被销毁时才会被调用。我没有看到任何为此目的而设计的方法。这个socket总是保持打开状态,无论客户端是否连接,对吧?

1 个回答

0

要处理客户端关闭连接的情况,可以查看一下handle_error这个方法。你的客户端是否正常关闭了连接呢?

handle_error():当出现异常但没有被其他方式处理时会被调用。默认情况下,它会打印出简化的错误追踪信息。

希望这些信息对你有帮助。

撰写回答