Flask在Elastic Beanstalk上不显示静态资源
如何让AWS的Elastic Beanstalk识别你Flask应用中的静态资源呢?我在/.ebextensions/python.config里写了一些标准的YAML配置,像这样:
option_settings:
"aws:elasticbeanstalk:container:python:staticfiles":
"/static/": "static/"
我在模板中调用静态资源时,都是用这种方式包裹的:“{{url_for('static', filename='img/office.jpg')}}”。
但是在页面加载时,图片、样式和JavaScript都没有显示出来。这里有一个404错误的日志示例。 IP - - [25/Feb/2013:21:48:13 +0000] "GET /static/css/bootstrap.css HTTP/1.1" 404 328 "http://xyz.elasticbeanstalk.com/"
我是不是漏掉了什么明显的东西?在我本地一切运行得很好,就是在我用git推送到AWS后,静态资源不加载。
9 个回答
四年多以后,我终于搞定了静态文件的设置,方法是:
(文件: .ebextensions/WHATEVER_NAME.config
)
option_settings:
- namespace: aws:elasticbeanstalk:container:python
option_name: StaticFiles
value: /static/=PATH/FROM/MY/APP/BASE/DIR/TO/STATIC/DIR/
...在我的情况下,这个是
value: /static/=distrib/static/
我发现把我的
app = Flask(__name__)
改成
app = Flask(__name__, static_url_path='/static')
既不是必要的,也不是充分的。当我只设置了 static_url_path 而没有设置 StaticFiles 时,它不工作;而当我设置了 StaticFiles 但没有设置 static_url_path 时,它就正常工作了。
<讽刺一下>Elastic Beanstalk 简直简单明了,文档也写得很好!</讽刺一下>
截至目前,我花了很多时间在AWS EB的配置上折腾,最终放弃了让静态文件按我们预期的方式工作的尝试,于是我更新了我的Flask应用创建方式为:
app = Flask(__name__, static_url_path='/s')
这样生成的链接像 /s/scripts/my-script.js
,而且因为我在代码和模板中总是使用 url_for('static', ...)
,所以在AWS外部一切依然正常工作。
2013年9月30日更新:我几乎可以肯定,AWS EB的Python容器完全忽略了 staticFiles
的设置。
我上面提到的改动有一个不太好的缺点,就是所有静态文件的请求都要通过Flask(更准确地说,是通过WSGI)来处理。不过,这个问题并不难解决。
在你的项目根目录下创建一个Apache配置文件,命名为 app-httpd.conf:
Alias /s /opt/python/current/app/static
<Directory /opt/python/current/app/static>
Order allow,deny
Allow from all
</Directory>
这个配置告诉Apache处理所有以 /s
开头的请求,这个前缀正是我们为静态文件选择的,并从我们应用的 static 文件夹中提供文件。
在 .ebextensions/custom-apache.config 创建这个文件:
container_commands:
add_apache_conf:
command: "cp app-httpd.conf /etc/httpd/conf.d"
这个文件将在应用部署时使用,并会把新的.config文件复制到Apache配置加载所有.config文件的目录中。