Twisted定义
Twisted是一个基于事件驱动的网络引擎框架
网络框架,别人预先定义好的一个框架(一个项目),如.net某个web框架有25个class,从BeginRequest依次执行类里的process方法,程序员自己定义一个类,添加到框架里,应用程序从上到下运行,就会执行自定义代码。框架只知道这个类的列表,不关心你写了什么内容,从上到下执行,类似于一个执行链,C#里叫委托链。也就是把代码类放到这个列表中,委托这个框架替你执行。
事件驱动(not event),把自定义代码注册到框架中,框架代替你执行。或者框架提供几个接口,让你插入数据(python里没有 )。
委托不能为空,事件可以为空。
演示一个最简单的框架
前期准备:
新建一个名为event_drive的python package,里面新建一个event_drive.py文件,这个就是框架主文件,把package目录复制到sys.path中,如:c:\python27\lib\site-package\
event_drive.py:
1 2 3 4 5 6 7 8 9 10 11 12 13 |
|
自定义代码:
1 2 3 4 5 6 7 8 9 |
|
执行过程:
- 导入event_drive文件夹中的event_drive文件
- 自定义一个类MyClass,这个类继承了event_drive文件中BaseHandler类
- 类里实现execute方法,内容无所谓甚至可以为空,方法名称execute不能改变
- 注册事件到框架的委托链,即把类名list.append(MyClass)传进去(下面的Twisted框架是创建对象后改一个字段为类名也是同样的目的)
- 执行run方法,框架自己就把MyClass中的方法执行了
执行结果:
1 2 |
|
Twisted框架:以socket为例
安装Twisted:(linux参考如下,windows直接用安装包)
1 2 3 |
|
ps:twisted调用了zope和win32api模块,先安装这两个,要不会报错。
Twisted_server.py
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 |
|
Twisted_client.py
1 2 3 4 5 6 7 8 9 10 11 12 |
|
执行原理
跟SocketServer原理类似,内部封装,内部有一个while循环,while循环一旦触发,找到这个类,执行这个类的构造方法,创建对象,通过对象,执行预定义的方法,
源码分析
程序执行流程:
- 运行服务端程序
- 创建Protocol的派生类Echo
解释:自定义Echo类,名字随便起,它继承了Protocol类,Protocol类又继承了BaseProtocol类,有了最左边的图
- 创建ServerFactory对象,并将Echo类封装到其protocol字段中
解释:ServerSocket是将MyClass以参数的形式封装,这个是以字段的形式
- 执行reactor的 listenTCP 方法,内部使用 tcp.Port 创建socket server对象,并将该对象添加到了 reactor的set类型的字段 _read 中
解释:
print type(reactor)
==>
<class ‘twisted.internet.selectreactor.SelectReactor‘>
去selectreactor.SelectReactor中找listenTCP,看上面的类继承关系图,继承了好多类。listenTCP和run方法都在基类里。
def listenTCP(self, port, factory, backlog=50, interface=‘‘):
p = tcp.Port(port, factory, backlog, interface, self)
p.startListening()
return p
其中把factory对象传入,就相当于:
1、把Echo类封装到factory字段
2、再把factory对象封装到listenTCP
3、tcp.port里创建了socket连接
- 执行reactor的 run 方法,内部执行 while 循环,并通过 select 来监视 _read 中文件描述符是否有变化,循环中...
解释:SelectReactor中包含两个集合_reads=set()和_writes=set(),不允许重复的集合,有连接后把文件句柄添加到这个集合中。开始执行reactor.run(),它调用基类里的mainLoop方法,又调取的selectreactor.doInteration,找不到?因为它是个重命名doInteration=doSelect,这个方法里面调取的就是select方法,通过调用select,循环这个_reads。一旦有句柄进来,通过反射去_reads里找“doRead”执行方法。
- 客户端请求到达
解释:可以通过debug方式了解调用顺序
- 执行reactor的 _doReadOrWrite 方法,其内部通过反射调用 tcp.Port 类的 doRead 方法,内部 accept 客户端连接并创建Server对象实例(用于封装客户端socket信息)和 创建 Echo 对象实例(用于处理请求) ,然后调用 Echo 对象实例的 makeConnection 方法,创建连接。
- 执行 tcp.Server 类的 doRead 方法,读取数据,
- 执行 tcp.Server 类的 _dataReceived 方法,如果读取数据内容为空(关闭链接),否则,触发Echo 的 dataReceived 方法
- 执行 Echo 的 dataReceived 方法
功能
Twisted主要用于网络操作,它支持许多常见的传输及应用层协议,包括TCP、UDP、SSL/TLS、HTTP、IMAP、SSH、IRC以及FTP。其中包含了诸多功能,例如:网络协议、线程、数据库管理、网络操作、电子邮件等。
优点
- 使用基于事件驱动的编程模型,而不是多线程模型。
- 跨平台:为主流操作系统平台暴露出的事件通知系统提供统一的接口。
- “内置电池”的能力:提供流行的应用层协议实现,因此Twisted马上就可为开发人员所用。
- 符合RFC规范,已经通过健壮的测试套件证明了其一致性。
- 能很容易的配合多个网络协议一起使用。
- 可扩展。
一个非常全面介绍Twisted网站
http://twisted.readthedocs.org/en/twisted-15.5.0/