如何在龙卷风的autoreload reload_hook中实现非阻塞等待?

时间:2015-11-17 19:08:05

标签: python multithreading python-2.7 tornado

我有一个网页,我想在进行更改时重新加载,但是,我可能有运行的线程,我不想被自动重载打断。我现在的工作原理是,线程能够完成,但在进行更改之后,但在重新加载之前,如果我点击任何内容,网页就不会响应。

@tornado.gen.coroutine
def wait_on_threads():
    """generate for non-blocking sleep"""
    for k, t in webserver.app.config['test_threads'].items():
        if t and t.is_alive():
            yield tornado.gen.sleep(5)
        else:
            webserver.app.config['test_threads'][k] = None


def reload_hook():
    """wait for daemon threads to finish"""
    while any(webserver.app.config['test_threads'].values()):
        wait_on_threads()
    rollback()

...

if __name__ == '__main__':        
        application.listen(address=ip, port=80)
        tornado.autoreload.add_reload_hook(reload_hook)
        tornado.autoreload.start()
        try:
            tornado.ioloop.IOLoop.instance().start()
        except KeyboardInterrupt:
            cleanup_handler()
            webserver.app.logger.info('Exit success.')
            tornado.ioloop.IOLoop.instance().stop()

之前,我刚刚在重装钩子中睡觉并且工作正常,但是当我做出改变时,网页没有响应。线程将在重新加载之前成功完成,并且在重新加载之后,Web服务器将再次响应。我试图用非阻塞方法替换睡眠,并且它再次起作用,但它的行为完全相同,因为Web服务器阻塞并且在重新加载之后不会响应。

我这样做是错误的,还是自动重载功能会导致网页在任何情况下都失去响应能力?

这是龙卷风版本:4.2.1和python 2.7.10

1 个答案:

答案 0 :(得分:1)

Tornado的自动重载功能适用于开发用途,当您不关心中断正在进行的操作时。 (如果延迟重新加载,则在重新加载期间服务器不可用,或者您可以继续向旧进程添加工作,无限期延迟重新启动)。要在不中断的情况下重新启动正在运行的服务,需要一个更复杂的过程,其中旧服务和新服务会在短时间内重叠。

例如,您可以运行两个单独的(一组)进程,并指示负载均衡器将流量从一个转移到另一个。或者您可以在旧进程中调用HTTPServer.stop()来释放端口,然后在启动新进程时让它们继续运行。