问题描述
我有一个 Flask 应用程序,它接收一个用户/投资组合 ID 表单,然后创建一个页面来显示用户数据、信息、图表等。我正在尝试为每个用户插入一个下载 CSV 数据链接/按钮投资组合/工具。
我是通过烧瓶会议来做的。由于 CSV 数据超出了 cookie 限制,我需要使用特殊会话。到目前为止,我已经尝试使用 Redis 没有成功(但它可能是一个选项),所以我使用的是文件系统 Flask 会话,它给出了一个错误 OSError: [Errno 36] 文件名太长 em>.
这是我的代码的简化:
app.py
from flask import Flask,render_template,redirect,request,session,send_file
from flask_wtf import FlaskForm
from flask_session import Session #this module has upper and lower case versions - I'm using lower
from wtforms import StringField,SelectField,SubmitField,validators
from wtforms.validators import DataRequired
from flask_bootstrap import Bootstrap
#import my modules
app = Flask(__name__)
SESSION_TYPE = 'filesystem' #redis #filesystem
app.config.from_object(__name__)
Session(app)
Bootstrap(app)
app.config.from_mapping(SECRET_KEY=.....)
...
#home route
@app.route('/',methods=['GET','POST'])
def home():
form = DataForm(request.form)
if request.method == 'POST' and form.validate_on_submit():
data_id = request.form['data_id']
target= request.form['target']
return redirect(f"/data/{target}/{data_id}")
return render_template('home.html',form=form)
#route which receives user/portfolio id,gets data and creates display page
@app.route('/data/<target>/<data_id>')
def customeranalysis(target,data_id):
data_id = procedures.handle_id(data_id)
if target == 'user':
user_infos,user_names,graphs,annual_tables,twelve_months_tables,monthly_tables,csvs = procedures.user_info(data_id)
for i in range(len(user_names)):
session[user_names[i]] = csvs[i]
return render_template('data_display_page.html',user_id=data_id,dfs=user_infos,names=user_names,graphs=graphs,annual_tables=annual_tables,twelve_months_tables=twelve_months_tables,monthly_tables=monthly_tables)
if target == 'portfolio':
#same as previous if,a little different
#route for the download page,to which the download link in previous route points
@app.route("/get_csv/<filename>",'POST'])
def get_csv(filename):
df = session[filename]
try:
return send_file(df,as_attachment=True,attachment_filename='dados.csv'
)
except FileNotFoundError:
abort(404)
if __name__ == '__main__':
app.run(debug=True,host='0.0.0.0')
因此,在我的 data_display_page.html 模板页面中,我有以下代码,用于创建下载链接:
data_display_page.html
{% for i in range(names| length) %}
...
<a href="{{url_for('get_csv',filename=names[i])}}" id="download" class="btn btn-outline-info">Download data</a>
...
当我运行 docker-compose 时,一切运行良好,但是当我点击下载加载链接并被重定向时,我在浏览器和控制台上收到内部服务器错误,我得到以下信息:
cmd: docker-compose 错误
web_1 | 172.27.0.1 - - [15/Apr/2021 18:34:15] "GET /data/portfolio/portfolio_api_id HTTP/1.1" 200 -
web_1 | [2021-04-15 18:34:47,836] ERROR in app: Exception on /get_csv/portfolio_name[GET]
web_1 | Traceback (most recent call last):
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/app.py",line 2447,in wsgi_app
web_1 | response = self.full_dispatch_request()
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/app.py",line 1952,in full_dispatch_request
web_1 | rv = self.handle_user_exception(e)
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/app.py",line 1821,in handle_user_exception
web_1 | reraise(exc_type,exc_value,tb)
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/_compat.py",line 39,in reraise
web_1 | raise value
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/app.py",line 1950,in full_dispatch_request
web_1 | rv = self.dispatch_request()
web_1 | File "/usr/local/lib/python3.8/site-packages/flask/app.py",line 1936,in dispatch_request
web_1 | return self.view_functions[rule.endpoint](**req.view_args)
web_1 | File "/code/app.py",line 86,in get_csv
web_1 | return send_file(df,web_1 | File "/usr/local/lib/python3.8/site-packages/flask/helpers.py",line 629,in send_file
web_1 | file = open(filename,"rb")
web_1 | OSError: [Errno 36] File name too long: #Long string which is actually not the CSV's name,but the CSV string itself
不知何故,它认为文件名是整个 CSV 字符串,包括所有列和行等。
解决方法
暂无找到可以解决该程序问题的有效方法,小编努力寻找整理中!
如果你已经找到好的解决方法,欢迎将解决方案带上本链接一起发送给小编。
小编邮箱:dio#foxmail.com (将#修改为@)