【发布时间】:2013-09-01 21:31:55
【问题描述】:
我有一个烧瓶 REST 端点,它执行一些 cpu 密集型图像处理并需要几秒钟才能返回。通常,此端点被调用,然后被客户端中止。在这些情况下,我想取消处理。我怎样才能在烧瓶中做到这一点?
在 node.js 中,我会这样做:
req.on('close', function(){
//some handler
});
我希望 flask 有类似的东西,或者一个同步方法 (request.isClosed()),我可以在处理过程中的某些时间点检查它,如果它关闭则返回,但我找不到。
我想过发送一些东西来测试连接是否仍然打开,如果失败则捕获异常,但似乎 Flask 缓冲了所有输出,因此在处理完成并尝试返回结果之前不会抛出异常:
已建立的连接被主机中的软件中止
如果客户中止了他们的请求,我该如何取消我的处理?
【问题讨论】:
-
“被客户端中止”是什么意思?客户端是否尝试关闭连接?还是他们到达了另一个终点?我认为没有办法使用 Flask 来执行此操作,尽管您当然可以对端点进行编码以允许它们停止处理(使用数据库来跟踪这些任务并让长期运行的任务检查该数据库例如停止标志)。
-
他们关闭了连接。每次他们更改某些选项(复选框)时,我都会重新生成一个图像:如果他们选中一个新框,则会触发一个请求,如果他们在第一个请求完成之前立即选中第二个框,则初始请求会被取消(jqXHR.abort() ) 并使用新选项制作一个新选项。我想过从客户端发出一个额外的请求来写一些“wascancelled”文件/数据库记录(正如你所建议的那样),但这看起来很丑陋。 PHP有connection_aborted(),nodejs有req.on('close'),我希望flask有类似的东西。
-
您可能会发现this e-mail thread 很有趣。它讨论了 WSGI 应用程序如何检测连接何时关闭。我相信它类似于
connection_aborted()在 PHP 中的工作方式:您不能简单地调用它并确定连接是否已关闭。相反,您需要先尝试发回数据(您可以使用streaming 来完成)。 -
我对 Flask 不是很了解,所以无法帮助您确定客户端何时关闭了连接。但是,如果您可以确定这一点,您是否考虑过使用
multiprocessing在单独的进程中进行图像处理。当连接关闭时,您可以调用process.terminate()结束该过程。
标签: python http rest flask wsgi