And*_*eno 1 python https nginx flask gunicorn
我正在使用 Flask 构建一个网络应用程序。目前我使用 Gunicorn 为应用程序提供服务,使用 nginx 作为反向代理。Chrome 开发工具抱怨一个端点不是 HTTPS:
混合内容:“ https://example.com:88/ ”上的页面已通过 HTTPS 加载,但请求了不安全的 XMLHttpRequest 端点“ http://example.com/geo2?coordinates= ”。此请求已被阻止;内容必须通过 HTTPS 提供。
在 app.py 中,我为 Flask 设置了 HTTPS:
context = ('ssl/server.crt', 'ssl/server.key')
app.run(host='0.0.0.0', port=443, ssl_context=context, threaded=True, debug=True)
Run Code Online (Sandbox Code Playgroud)
我正在执行 gunicorn :
gunicorn --bind 0.0.0.0:8282 app:app
Run Code Online (Sandbox Code Playgroud)
我的 nginx 配置(为简洁起见省略了所有 SSL 设置):
server {
listen 88 ssl;
server_name example.com www.example.com;
root /var/www/app/;
index index.html;
location / {
proxy_pass http://192.168.1.5:8282/;
proxy_redirect off;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-Host $server_name;
}
}
Run Code Online (Sandbox Code Playgroud)
我注意到我只看到一个端点 /geo2 的错误。我的应用程序设置为在 /geo 收到 POST 请求时重定向到此端点。代码是:
return redirect(url_for('reload_index', coordinates=coordinates))
Ajax 正在发送 POST 请求:
$.ajax({
type: "POST",
url: "/geo",
contentType: "application/json; charset=utf-8",
data: JSON.stringify(coordinates),
dataType: "json",
success: function(response) {
console.log(response);
},
error: function(err) {
console.log(err);
}
});
Run Code Online (Sandbox Code Playgroud)
鉴于 Flask 设置为使用 HTTPS,我对为什么任何端点都是 HTTP 感到困惑。我错过了什么?在过去的几个月里,我自学了所有这些,所以我很可能忽略了一些东西。
Flask 不知道您的代理服务器正在使用什么协议。您必须通过在 nginx 配置文件中设置适当的标头来告诉 Flask:
proxy_set_header X-Forwarded-Proto $scheme;
Run Code Online (Sandbox Code Playgroud)
然后使用中间件修复您的请求:
from werkzeug.contrib.fixers import ProxyFix
app.wsgi_app = ProxyFix(app.wsgi_app)
Run Code Online (Sandbox Code Playgroud)