Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Difference between IOLoop.current().run_in_executor() and ThreadPoolExecutor().submit()

I'm quite new to Python Tornado and have been trying to start a new thread to run some IO blocking code whilst allowing the server to continue to handle new requests. I've been doing some reading but still can't seem to figure out what the difference is between these two functions?

For example calling a method like this:

from concurrent.futures import ThreadPoolExecutor

with ThreadPoolExecutor(1) as executor:
    future = executor.submit(report.write_gresb_workbook)
    print(future.result())

compared to:

from concurrent.futures import ThreadPoolExecutor
from tornado import ioloop

with ThreadPoolExecutor(1) as executor:
    my_success = await ioloop.IOLoop.current().run_in_executor(executor, report.write_gresb_workbook)
    print(my_success)

write_gresb_workbook takes some information from the object report and writes it to an excel spreadsheet (however I'm using openpyxl which takes ~20s to load an appropriately formatted workbook and another ~20s to save it which stops the server from handling new requests!)

The function simply returns True or False (which is what my_success is) as the report object has the path of the output file attached to it.

I haven't quite gotten either of these methods to work yet so they might be incorrect but was just looking for some background information.

Cheers!

like image 463
dylanmorroll Avatar asked Mar 04 '23 07:03

dylanmorroll


1 Answers

IOLoop.run_in_executor and Executor.submit do essentially the same thing, but return different types. IOLoop.run_in_executor returns an asyncio.Future, while Executor.submit returns a concurrent.futures.Future.

The two Future types have nearly identical interfaces, with one important difference: Only asyncio.Future can be used with await in a coroutine. The purpose of run_in_executor is to provide this conversion.

like image 88
Ben Darnell Avatar answered Apr 06 '23 21:04

Ben Darnell