我有一个像这样的简单龙卷风应用程序,让用户下载一个大文件。我需要能够检测客户端何时丢弃并引发异常。
class MainHandler(tornado.web.RequestHandler):
def get(self):
print "hello"
self.write("A"*10000000)
self.flush()
self.finish()
print "world"
如果我在下载As,打印"世界"时卷曲此方法和ctrl-C声明仍然执行。我希望能够检测curl命令何时关闭并引发异常,而不是继续完成我的get()方法。
在龙卷风中这样做的最佳方法是什么?
答案 0 :(得分:2)
首先,您必须使处理程序异步。其次,您可以覆盖on_connection_close
以在连接中止时收到警报。
import tornado.ioloop
import tornado.web
from tornado import gen
class MainHandler(tornado.web.RequestHandler):
def initialize(self):
self.aborted = False
@gen.coroutine
def get(self):
print "hello"
self.write("A"*10000000)
yield gen.Task(self.flush) # This is asynchronous, so on_connection_close can run while this flushes.
self.finish()
if not self.aborted:
print "world"
def on_connection_close(self):
self.aborted = True
print("aborted")
application = tornado.web.Application([
(r"/test", MainHandler),
])
application.listen(8888)
tornado.ioloop.IOLoop.instance().start()
请注意,如果您的处理程序中的唯一异步调用是self.flush
,则无法保证此功能:除非您正在编写大量数据,否则龙卷风可能会将所有数据刷新到在客户端中止连接之前的缓冲区。但它在我的机器上与此示例代码一致。
答案 1 :(得分:1)
问题是.write
没有阻止。它只是将数据添加到写缓冲区并立即返回。如果要在写入所有数据后执行某些操作,则.flush会提供一个回调参数,该参数将在写入所有数据时调用。
def print_world():
print "world"
和
#self.flush() replace this with the following
self.flush(callback=print_world)