如何将 Flask 静态指向 Amazon S3 URL?

Jav*_*aaa 4 heroku static-files flask

我有一个在 Heroku 上托管的 Flask 应用程序,但希望从 Amazon S3 提供静态文件。

在我的模板中,我使用 url_for() 来引用静态文件。在 Flask 应用程序的初始化中,我想把

app = Flask(__name__, static_url_path="http://my-bucket.s3.amazonaws.com")
Run Code Online (Sandbox Code Playgroud)

确保使用http://my-bucket.s3.amazonaws.com/static/而不是 mysite.com/static/。但是我收到这个错误:

ValueError: urls must start with a leading slash
Run Code Online (Sandbox Code Playgroud)

如果我将其更改为带有前导斜杠的值,它就可以工作,但我希望静态 URL 指向 S3(一个外部域),因此它需要以 http:// 开头。

我究竟做错了什么?如何通过 Flask 和 Heroku 将 S3 用于静态文件?

Mar*_*ers 5

如果您使用static_*对象的任何选项Flask,则假设它将负责提供这些文件。配置的路由static既作为提供静态文件的视图,又作为url_for()生成 URL 的目标。

因此,仅使用 Flask,您就必须将所有url_for('static', ...)调用替换为对 CDN 的硬编码 URL。

相反,您应该改用Flask-CDN,这是一个方便的 Flask 插件,用于处理 Flask 托管的静态文件和 CDN 托管的静态文件之间的无缝切换:

from flask_cdn import CDN

app = Flask(__name__)
cdn = CDN(app)
Run Code Online (Sandbox Code Playgroud)

并将CDN_DOMAIN配置选项设置为http://my-bucket.s3.amazonaws.com部署到生产时。

在调试模式下,url_for()将生成旧的/static/..url 供 Flask 处理,在生产模式下,url_for()为这些 url 加上前缀CDN_DOMAIN值。如果后者保留默认None设置,则不会发生此类 URL 更改,从而可以在本地运行 Flask,并debug根据需要关闭。

请注意, 的行为url_for()针对 Jinja 模板进行更改;如果您需要在视图中生成静态 URL,则必须flask.url_for()换成flask_cdn.url_for().