【发布时间】:2020-11-16 08:21:06
【问题描述】:
我正在制作一个应用程序,让用户上传 csv 数据,并生成该数据的图,将图保存为 pdf,然后将图作为下载返回给用户。问题的关键在于,这个情节实际上需要 1 - 2 分钟才能生成。
应用程序
路线如下:
@app.route("/gen_pdf", methods=["GET","POST"])
def transform2():
f = request.files['input_file1']
if not f:
return "Main input file not found!"
# Read uploaded data as a Stream into a dataframe.
stream = io.StringIO(f.stream.read().decode("UTF8"), newline=None)
csv_input = csv.reader(stream)
contents = []
for row in csv_input:
contents.append(float(row[0]))
#Artificially increase time required to generate plot
time.sleep(60)
plt.hist(contents, bins=100)
fn = "test_histogram.pdf"
plt.savefig(app.config["CLIENT_DIR"]+"/"+fn)
return send_from_directory(app.config["CLIENT_DIR"], filename=fn, as_attachment=True)
gen_pdf.html,为了完整性(这可以嵌入到一些 html 样板中)
{% extends "layout.html" %}
{% block content %}
<h1>Test</h1>
<hr/>
<form action="/transform2" method="post" enctype="multipart/form-data">
<h3>Upload input file (csv)</h3>
<input type="file" name="input_file1" id="input_file1">
<hr/>
<input type="submit" value="Create and Serve PDF" name="submit">
</form>
{% endblock content %}
要上传的数据只是一个单独的 csv 文件,其中包含一列随机生成的数字。
Nginx/Uwsgi 设置
这些是在 Ubuntu 18.04 VM 上设置的,遵循设置 here。
错误
如前所述,这会导致网关 504 错误。但是,如果我将 time.sleep() 命令中的延迟减少到 10 秒,则一切正常,因此该错误在某种程度上源于 pdf 绘图完成之前的超时。
检查journalctl --unit=<my_project>.service -n 100 --no-pager 时,我得到:
SIGPIPE: writing to a closed pipe/socket/fd (probably the client disconnected) on request /transform2 (ip <ip_address>) !!!
uwsgi_response_writev_headers_and_body_do(): Broken pipe [core/writer.c line 306] during POST /transform2 (<ip_address>)
OSError: write error
[pid: 27863|app: 0|req: 156/335] <ip_address> () {50 vars in 1083 bytes} [Mon Jul 27 02:18:38 2020] POST /transform2 => generated 0 bytes in 60835 msecs (HTTP
我知道 SIGPIPE 错误 here 的解释,但该解释似乎不相关(这是一个内部过程,而不是访问者之间)。
【问题讨论】:
标签: python-3.x flask