繁体   English   中英

Twisted Python接口实例可以不实现该接口的所有功能吗?

[英]Can Twisted Python interface instance not implementing all functions of that interface?

在浏览本博客中的示例时,我发现当ClientFactory实例(它是PoetryClientFactory的一个参数)或Protocol实例(它是PoetryProtocol的一个参数)没有实现为ClientFactory或Protocol接口定义的所有功能时。 ClientFactory接口实现startedConnecting,clientConnectionFailed和clientConnectionLost,但PoetryClientFactory不实现startedConnecting和clientConnectionLost。 怎么了?

# This is the Twisted Get Poetry Now! client, version 2.0.

# NOTE: This should not be used as the basis for production code.

import datetime, optparse

from twisted.internet.protocol import Protocol, ClientFactory


def parse_args():
    usage = """usage: %prog [options] [hostname]:port ...

This is the Get Poetry Now! client, Twisted version 2.0.
Run it like this:

  python get-poetry.py port1 port2 port3 ...

If you are in the base directory of the twisted-intro package,
you could run it like this:

  python twisted-client-2/get-poetry.py 10001 10002 10003

to grab poetry from servers on ports 10001, 10002, and 10003.

Of course, there need to be servers listening on those ports
for that to work.
"""

    parser = optparse.OptionParser(usage)

    _, addresses = parser.parse_args()

    if not addresses:
        print parser.format_help()
        parser.exit()

    def parse_address(addr):
        if ':' not in addr:
            host = '127.0.0.1'
            port = addr
        else:
            host, port = addr.split(':', 1)

        if not port.isdigit():
            parser.error('Ports must be integers.')

        return host, int(port)

    return map(parse_address, addresses)


class PoetryProtocol(Protocol):

    poem = ''
    task_num = 0

    def dataReceived(self, data):
        self.poem += data
        msg = 'Task %d: got %d bytes of poetry from %s'
        print  msg % (self.task_num, len(data), self.transport.getPeer())

    def connectionLost(self, reason):
        self.poemReceived(self.poem)

    def poemReceived(self, poem):
        self.factory.poem_finished(self.task_num, poem)


class PoetryClientFactory(ClientFactory):

    task_num = 1

    protocol = PoetryProtocol # tell base class what proto to build

    def __init__(self, poetry_count):
        self.poetry_count = poetry_count
        self.poems = {} # task num -> poem

    def buildProtocol(self, address):
        proto = ClientFactory.buildProtocol(self, address)
        proto.task_num = self.task_num
        self.task_num += 1
        return proto

    def poem_finished(self, task_num=None, poem=None):
        if task_num is not None:
            self.poems[task_num] = poem

        self.poetry_count -= 1

        if self.poetry_count == 0:
            self.report()
            from twisted.internet import reactor
            reactor.stop()

    def report(self):
        for i in self.poems:
            print 'Task %d: %d bytes of poetry' % (i, len(self.poems[i]))

    def clientConnectionFailed(self, connector, reason):
        print 'Failed to connect to:', connector.getDestination()
        self.poem_finished()


def poetry_main():
    addresses = parse_args()

    start = datetime.datetime.now()

    factory = PoetryClientFactory(len(addresses))

    from twisted.internet import reactor

    for address in addresses:
        host, port = address
        reactor.connectTCP(host, port, factory)

    reactor.run()

    elapsed = datetime.datetime.now() - start

    print 'Got %d poems in %s' % (len(addresses), elapsed)


if __name__ == '__main__':
    poetry_main()

我不确定我要问的是什么,但是从本质上讲,如果您不需要对某个事件采取行动(例如,当客户端开始连接或连接断开时),则不需要实现该功能。 它主要只是一个界面。 如果您不实现这些功能,则会从ClientFactoryProtocol或您继承的任何类中调用一个不执行任何操作的空函数。

如果您自己实现接口,则它看起来像这样:

from zope.interface import implementer
from twisted.internet.interfaces import IProtocol
@implementer(IProtocol)
class MyProtocol(object):
    " ... "

在这种情况下,您确实需要实现所有方法,因为此@implementer声明仅表示您打算提供所有相关方法。

但是,在Twisted中更常见的做法是子类化,如下所示:

from twisted.internet.protocol import Protocol
class MyProtocol(Protocol, object):
    " ... "

这种情况下,你并不需要实现所有的方法,因为Protocol的超类已经提供了对所有方法的实现IProtocol 通常,Twisted提供了一个超类,该类具有Twisted应用程序开发人员必须实现的许多更常用接口的所有方法的默认版本或空版本。

我也不太确定您要问什么。

IMO,获取github的源代码是最快的学习方法。 如您所见, startedConnectingclientConnectionLost (不过为空代码)具有默认实现。

因此,您只需要实现所需的回调,而无需实现该接口中定义的所有方法。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM