[英]run function parallel on python tornado
我目前正在tornado
框架上使用python3
(仍是初學者)進行開發,並且我想在后台運行一個函數。 更准確地說,該功能的任務是下載一個大文件(逐塊),並在每個塊下載后可能還要執行更多操作。 但是調用函數不應等待下載函數完成,而應繼續執行。
下面是一些代碼示例:
@gen.coroutine
def dosomethingfunc(self, env):
print("Do something")
self.downloadfunc(file_url, target_path) #I don't want to wait here
print("Do something else")
@gen.coroutine
def downloadfunc(self, file_url, target_path):
response = urllib.request.urlopen(file_url)
CHUNK = 16 * 1024
with open(target_path, 'wb') as f:
while True:
chunk = response.read(CHUNK)
if not chunk:
break
f.write(chunk)
time.sleep(0.1) #do something after a chunk is downloaded - sleep only as example
我已經在stackoverflow https://stackoverflow.com/a/25083098/2492068上閱讀了此答案,並嘗試使用它。
其實我想,如果我用@gen.coroutine
但沒有yield
的dosomethingfunc
將繼續無需等待downloadfunc
完成。 但是實際上行為是相同的(無論是否產生收益)-僅在downloadfunc
完成下載后才打印"Do something else
”。
我在這里想念的是什么?
為了使Tornado的異步功能受益,必須在某個時刻yielded
非阻塞函數。 由於downloadfunc
的代碼全部被阻塞,因此dosomethingfunc
在調用的函數完成之前不會獲得控制權。
您的代碼有幾個問題:
time.sleep
阻塞,使用tornado.gen.sleep
代替, urlopen
被阻止,請使用tornado.httpclient.AsyncHTTPClient
所以downloadfunc
看起來像:
@gen.coroutine
def downloadfunc(self, file_url, target_path):
client = tornado.httpclient.AsyncHTTPClient()
# below code will start downloading and
# give back control to the ioloop while waiting for data
res = yield client.fetch(file_url)
with open(target_path, 'wb') as f:
f.write(res)
yield tornado.gen.sleep(0.1)
要通過流(按塊)支持來實現它,您可能需要這樣做:
# for large files you must increase max_body_size
# because deault body limit in Tornado is set to 100MB
tornado.web.AsyncHTTPClient.configure(None, max_body_size=2*1024**3)
@gen.coroutine
def downloadfunc(self, file_url, target_path):
client = tornado.httpclient.AsyncHTTPClient()
# the streaming_callback will be called with received portion of data
yield client.fetch(file_url, streaming_callback=write_chunk)
def write_chunk(chunk):
# note the "a" mode, to append to the file
with open(target_path, 'ab') as f:
print('chunk %s' % len(chunk))
f.write(chunk)
現在,您可以在dosomethingfunc
調用它而不使用yield
,其余功能將繼續進行。
編輯
服務器和客戶端均不支持(公開)修改塊大小。 您也可以查看https://groups.google.com/forum/#!topic/python-tornado/K8zerl1JB5o
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.