Chris Seymour
Chris Seymour

Reputation: 85785

Asynchronous object instantiation

How can I make the following object instantiation asynchronous:

class IndexHandler(tornado.web.RequentHandler):
    def get(self, id):
        # Async the following
        data = MyDataFrame(id)
        self.write(data.getFoo())

The MyDataFrame returns a pandas DataFrame object and can take some time depending on the file it has to parse.

Upvotes: 0

Views: 1075

Answers (1)

Ben Darnell
Ben Darnell

Reputation: 22134

MyDataFrame() is a synchronous interface; to use it without blocking you need to do one of two things:

  • Rewrite it to be asynchronous. You can't really make an __init__ method asynchronous, so you'll need to refactor things into a static factory function instead of a constructor. In most cases this path only makes sense if the method depends on network I/O (and not reading from the filesystem or processing the results on the CPU).

  • Run it on a worker thread and asynchronously wait for its result on the main thread. From the way you've framed the question, this sounds like the right approach for you. I recommend the concurrent.futures package (in the standard library since Python 3.2; available via pip install futures for 2.x).

This would look something like:

@tornado.gen.coroutine
def get(self, id):
    data = yield executor.submit(MyDataFrame, id)
    self.write(data.getFoo())

where executor is a global instance of ThreadPoolExecutor.

Upvotes: 3

Related Questions