2

我正在尝试使用 twisted.words.protocols.irc 模块制作 IRC 机器人。

该机器人将解析来自通道的消息并将它们解析为命令字符串。

一切正常,除非我需要机器人通过发送 whois 命令来识别昵称。在 privmsg 方法(我从中进行解析的方法)返回之前,不会处理 whois 回复。
例子:

from twisted.words.protocols import irc

class MyBot(irc.IRClient):

..........

    def privmsg(self, user, channel, msg):
        """This method is called when the client recieves a message"""
        if msg.startswith(':whois '):
            nick = msg.split()[1]
            self.whois(nick)
            print(self.whoislist)

    def irc_RPL_WHOISCHANNELS(self, prefix, params):
        """This method is called when the client recieves a reply for whois"""
        self.whoislist[prefix] = params

有没有办法让机器人在 self.whois(nick) 之后等待回复?

也许使用线程(我没有任何经验)

4

2 回答 2

2

Deferred是 Twisted 中的一个核心概念,你必须熟悉它才能使用 Twisted。

基本上,您的 whois 检查功能应该返回一个Deferred将在您收到 whois-reply 时触发的。

于 2013-06-01T18:41:30.240 回答
-2

我设法通过将所有处理程序方法作为线程运行来解决此问题,然后在运行 whois 查询之前按照 kirelagin 的建议设置一个字段,并修改接收数据的方法以在收到回复时更改字段。它不是最优雅的解决方案,但它有效。

修改后的代码:

class MyBot(irc.IRClient):
..........

    def privmsg(self, user, channel, msg):
        """This method is called when the client recieves a message"""
        if msg.startswith(':whois '):
            nick = msg.split()[1]

            self.whois_status = 'REQUEST'
            self.whois(nick)
            while not self.whois_status == 'ACK':
                sleep(1)

            print(self.whoislist)

    def irc_RPL_WHOISCHANNELS(self, prefix, params):
        """This method is called when the client recieves a reply for whois"""
        self.whoislist[prefix] = params

    def handleCommand(self, command, prefix, params):
        """Determine the function to call for the given command and call
        it with the given arguments.
        """
        method = getattr(self, "irc_%s" % command, None)
        try:
            # all handler methods are now threaded.
            if method is not None:
                thread.start_new_thread(method, (prefix, params))
            else:
                thread.start_new_thread(self.irc_unknown, (prefix, command, params))
        except:
            irc.log.deferr()

    def irc_RPL_WHOISCHANNELS(self, prefix, params):
        """docstring for irc_RPL_WHOISCHANNELS"""
        self.whoislist[prefix] = params

    def irc_RPL_ENDOFWHOIS(self, prefix, params):
        self.whois_status = 'ACK'
于 2013-06-01T20:23:41.823 回答