Python Tornado-使POST在异步函数继续工作时立即返回

Python Tornado-使POST在异步函数继续工作时立即返回,python,tornado,Python,Tornado,下面我有一个处理程序: class PublishHandler(BaseHandler): def post(self): message = self.get_argument("message") some_function(message) self.write("success") 我面临的问题是一些函数()需要一些时间来执行,我希望调用post请求时立即返回,如果可能的话,在另一个线程/进程中执行一些函数() 我使用berk

下面我有一个处理程序:

class PublishHandler(BaseHandler):

    def post(self):
        message = self.get_argument("message")
        some_function(message)
        self.write("success")
我面临的问题是一些函数()需要一些时间来执行,我希望调用post请求时立即返回,如果可能的话,在另一个线程/进程中执行一些函数()

我使用berkeley db作为数据库,我尝试做的事情相对简单


我有一个用户数据库,每个用户都有一个过滤器。如果筛选器与消息匹配,服务器将向用户发送消息。目前,我正在测试数千名用户,因此每次通过post请求发布消息时,它都会遍历数千名用户以找到匹配项。这是我做事情的天真实现,因此我的问题。如何更好地执行此操作?

您可以使用
IOLoop
add\u callback
方法来完成此操作,如下所示:

loop.add_callback(lambda: some_function(message))
Tornado将在下一个IOLoop过程中执行回调,这可能(我必须深入Tornado的内心才能确定,或者测试它)允许在代码执行之前完成请求

缺点是您编写的长时间运行的代码仍然需要时间来执行,这可能会阻止另一个请求。如果你同时收到很多这样的请求,那就不太理想了

更简单的解决方案是在单独的线程或进程中运行它。使用Python的最佳方法是使用进程,这是由于GIL(如果您不熟悉它,我强烈建议您阅读它)。然而,在单处理器机器上,线程实现也可以很好地工作,并且可能更容易实现


如果使用线程路由,可以构建一个漂亮的“异步执行器”模块,其中包含一个互斥体、一个线程和一个队列。如果您想使用单独的进程,请查看
多处理
模块。

我已经尝试过了,我相信在调用回调之前,请求不会完成

我认为一个肮脏的黑客应该调用两个级别的add_回调,例如:

  def get(self):
    ...
    def _defered():
      ioloop.add_callback(<whatever you want>)
    ioloop.add_callback(_defered)
    ...
def get(self):
...
def_延迟():
ioloop.add_回调()
ioloop.add\u回调(\u延迟)
...
但这些充其量只是黑客。我现在正在寻找一个更好的解决方案,可能最终会得到一些消息队列或简单的线程解决方案