2016-01-20 86 views
0

我新的扭曲,试图写我的第一个应用程序,我居然坚持了这个问题:扭曲deferToThread TCP连接

我有一个加载了一堆模块运行的主线程,放入系统中的每一个模块位于远程服务器,并可以通过一个TCP连接,这里什么模块运行的代码如下所示:

#!/usr/bin/env python 
# -*- coding: utf-8 -*- 
import socket 
import struct 

from twisted.internet import endpoints 
from twisted.internet.defer import inlineCallbacks 
from twisted.spread import pb 
from txapp.core import get_modules 

from txmod.spread import EnvelopeSpreadReceiver 


@inlineCallbacks 
def listen(reactor): 
    modules = yield get_modules() 

    for mod in modules: 
     endpoint = endpoints.serverFromString(reactor, 'tcp:%d:%s' % 
               (int(mod.get('module_server_port') or 0), 
               socket.inet_ntoa(struct.pack('!L', mod.get('module_server_ipaddr'))),)) 
     endpoint.listen(pb.PBServerFactory(EnvelopeSpreadReceiver())) 
     print 'PBServerFactory starting on %s:%d for module %s' % (
      socket.inet_ntoa(struct.pack('!L', mod.get('module_server_ipaddr'))), 
      int(mod.get('module_server_port')), 
      mod.get('module_name')) 


def main(): 
    from twisted.internet import reactor 
    listen(reactor) 
    reactor.run() 


if __name__ == "__main__": 
    main() 

给定服务器可以在不同的端口运行多个模块,但通常这将是:1个服务器,1个模块

运行应用程序的主服务器将尝试连接到每个模块,运行代码并期望结果(成功与否)。

我在如何使此代码无法阻塞的问题上苦苦挣扎:如果服务器无法响应,tcp连接可能会挂起,所以我应该将每个模块的tcp连接放在与deferToThread分开的线程上?

主应用程序将每天处理数百万个请求,所以它应该是完全不阻塞的。

这是处理这个问题的正确方法吗?有人能指出我如何实现这一目标的正确方向吗?

回答

0

Twisted的事件循环API不是线程安全的,如Twisted's threading documentation所涵盖。这意味着您绝对不能拨打deferToThread来处理连接;如果你尝试过,它会崩溃。

等待的TCP连接不会导致事件循环卡住;用于向连接发送和接收数据的API已经是非阻塞的。所以我认为你在这里没有问题要解决,它已经为你解决了。

+0

非常感谢你;) – kitensei