我正在开发一个Flask应用程序,运行在Heroku上,允许用户上传图片。该应用程序有一个页面,在表格中显示用户的图片。
为了开发目的,我将上传的文件保存到Heroku的ephemeral文件系统中,一切正常:图片正确加载和显示(我使用的是here中显示的最后一种方法,暗示使用send_from_directory())。现在我已经将存储迁移到S3并尝试适应代码。我使用boto3将文件上传到存储桶中:这很好用。我的疑问与下载以填充用户页面相关。
如here所述,我可以将文件设置为“public-read”并使用URL(我认为这就是Flask-S3的作用),但我宁愿不要留下免费访问文件的方式。因此,我的解决方案尝试是将文件下载到Heroku的文件系统中,并再次使用send_from_directory()服务图像,如下所示:
为了开发目的,我将上传的文件保存到Heroku的ephemeral文件系统中,一切正常:图片正确加载和显示(我使用的是here中显示的最后一种方法,暗示使用send_from_directory())。现在我已经将存储迁移到S3并尝试适应代码。我使用boto3将文件上传到存储桶中:这很好用。我的疑问与下载以填充用户页面相关。
如here所述,我可以将文件设置为“public-read”并使用URL(我认为这就是Flask-S3的作用),但我宁愿不要留下免费访问文件的方式。因此,我的解决方案尝试是将文件下载到Heroku的文件系统中,并再次使用send_from_directory()服务图像,如下所示:
app.py
@app.route('/download/<resource>')
def download_image(resource):
""" resource: name of the file to download"""
s3 = boto3.client('s3',
aws_access_key_id=current_app.config['S3_ACCESS_KEY'],
aws_secret_access_key=current_app.config['S3_SECRET_KEY'])
s3.download_file(current_app.config['S3_BUCKET_NAME'],
resource,
os.path.join('tmp',
resource))
return send_from_directory('tmp', # Heroku's filesystem
resource,
as_attachment=False)
然后,在模板中,我生成图像的URL如下:
...
<img src="{{ url_for('app.download_image',
resource=resource) }}" height="120" width="120">
...
它可以工作,但出于某些原因,我认为这不是正确的方式:其中之一是,我应该管理Heroku的文件系统以避免在动态重启之间使用完所有空间(我应该从文件系统中删除图像)。
哪种方式是最佳/首选方式,还考虑到性能?非常感谢