NGinx 代理通行证未执行

问题描述 投票:0回答:1

我正在运行一个非常简单的 Flask 网络服务器:

from flask import Flask

app = Flask(__name__)

@app.route('/api/get_latest_api_version', methods=['GET'])
def get_latest_api_version():
    return "3.0.0"

if __name__ == '__main__':
    app.run(debug=True, host='0.0.0.0')

这是通过

python3 -m gunicorn -b 0.0.0.0:5000 app:app --log-level "debug"
(在 tmux 会话中)调用的。

我还使用以下相关配置将 nginx 作为 systemd 进程运行:

server {
    listen 443 ssl;
    server_name problemsite.ca;

    ssl_certificate /etc/letsencrypt/live/problemsite.ca/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/problemsite.ca/privkey.pem;

    location / {
        proxy_pass http://127.0.0.1:5000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    }
}

问题

Nginx 在接收传入请求并返回错误的网关调用时与 Gunicorn 服务器存在某种无法解释的通信问题。错误消息示例:

<IP SOURCE> - - [04/May/2024:20:58:31 +0000] "GET /api/get_latest_api_version HTTP/1.1" 502 173 "-" "curl/7.68.0"

来自要求

curl -X 'GET' 'https://problemsite.ca/api/get_latest_api_version' -H 'accept: application/json'

其他信息

  • Nginx 版本:nginx/1.14.1
  • Gunicorn版本:gunicorn==21.2.0
  • Flask版本:Flask==2.0.3
  • 本地执行
    curl -X 'GET' 'http://127.0.0.1:5000/api/get_latest_api_version' -H 'accept: application/json'
    返回响应
  • SSL证书和域名正在运行
  • 当外部错误请求传入时,Nginx 正在运行并侦听传入错误日志中明显显示的 443 请求
  • 发出外部 API 请求时,gunicorn 服务器输出中的调试日志为零,尽管 nginx 错误日志中捕获了请求
  • 服务器在装有 Oracle Linux 8 的 Oracle 计算机的免费实例上运行
  • 没有其他 Web 服务器(据我所知)正在运行,可能会导致冲突
  • 从新的虚拟机状态到现在,我总共运行了以下命令:
  • Nginx 作为 systemd 进程运行
  • Gunicorn 在主机的终端中本地运行
  • 一切都以 root 身份运行
  • 我总共运行了以下命令:
pip3 install flask gunicorn
yum install -y nginx tmux
cd /tmp
wget https://dl.fedoraproject.org/pub/epel/epel-release-latest-8.noarch.rpm
rpm -Uvh /tmp/epel-release-latest-8.noarch.rpm
dnf install -y snapd
systemctl enable --now snapd.socket
systemctl start snapd
ln -s /var/lib/snapd/snap /snap
snap install core
snap refresh core
snap install --classic certbot
ln -s /snap/bin/certbot /usr/bin/certbot
firewall-cmd --zone=public --permanent --add-port=80/tcp
firewall-cmd --zone=public --permanent --add-port=443/tcp
firewall-cmd --zone=public --permanent --add-port=5000/tcp
firewall-cmd --reload
certbot certonly --standalone -d "problemsite.ca" --non-interactive --agree-tos -m "[email protected]"
<copy SSL part to nginx config>
systemctl enable nginx
systemctl restart nginx
<create app.py file>

我还尝试过什么

  • 在 nginx SSL 代理通行证站点添加最后一个“/”(
    proxy_pass http://127.0.0.1:5000/;
    )
  • 更改gunicorn服务器以监听127.0.0.1和/或localhost和/或其他接口的地址
  • 将代理通IP更改为localhost和/或0.0.0.0和/或其他接口的其他地址
  • 尝试从多台不同的机器进行外部API调用,每台机器都有相同的错误,表明它与服务器端相关
python flask nginx gunicorn oracle-cloud-infrastructure
1个回答
0
投票

当你让 Flask 在代理后面运行时,你需要确保告诉 Flask 它在代理后面,根据文档

from werkzeug.middleware.proxy_fix import ProxyFix

app = Flask(__name__)

# x_for: X-Forwarded-For
# x_proto: X-Forwarded-Proto
# x_host: X-Forwarded-Host
# x_prefix: X-Forwarded-Prefix
app.wsgi_app = ProxyFix(app.wsgi_app, x_for=1, x_proto=1, x_host=1, x_prefix=1)

并将

proxy_set_header X-Forwarded-Prefix /;
添加到 nginx 配置中的
location /

location / {
    proxy_pass http://127.0.0.1:5000/;
    proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
    proxy_set_header X-Forwarded-Proto $scheme;
    proxy_set_header X-Forwarded-Host $host;
    proxy_set_header X-Forwarded-Prefix /;  
}

确保重新启动或重新加载 nginx 配置和 Gunicorn。

© www.soinside.com 2019 - 2024. All rights reserved.