SSL 终止 Nginx + 后端 Nginx 不工作(在 HTTPS 中获取混合内容结果)

SSL 终止 Nginx + 后端 Nginx 不工作(在 HTTPS 中获取混合内容结果)

我根据本教程设置了 2 个 nginx 网络服务器https://www.digitalocean.com/community/tutorials/how-to-set-up-nginx-load-balancing-with-ssl-termination

问题是,通过 SSL 的简单测试 php 页面可以很好地加载,但是当我尝试安装一些 PHP 应用程序(例如 Moodle)时,我收到了混合内容警告并且 UI 坏了......(有些处于 HTTP 模式,有些处于 HTTPS 模式,等等...)

如何才能让所有内容都加载到所有 HTTPS 中(修复混合内容问题)?

以下是前端 SSL Nginx 配置:

# File: \etc\nginx\sites-available\main.big.vm

upstream mainBigVm {
    server main.big.vm:80;
}

server {
    listen 80;

    listen 443 ssl;
    ssl on;
    ssl_certificate         /etc/nginx/cert.crt;
    ssl_certificate_key     /etc/nginx/cert.key;

    server_name main.big.vm;

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

以下是后端 Nginx 配置(在服务器 main.big.vm 中):

# File: \etc\nginx\sites-available\default

server {
    listen 80 default_server;
    listen [::]:80 default_server;

    root /var/www/html;

    index index.html index.htm index.nginx-debian.html index.php;

    server_name _;

    location / {
        try_files $uri $uri/ =404;
    }

    location ~ \.php$ {
        fastcgi_pass unix:/var/run/php5217-fpm.sock;
        fastcgi_index index.php;
        fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
        include fastcgi_params;
    }
}

更新 170430-1

我已经尝试了前端建议的配置,但仍然不起作用。

upstream mainBigVm {
    server main.big.vm:80;
}

#suggestion
server {
    listen 80;
    location / {
        return 301 https://$host$request_uri;
    }
}

server {
    listen 80;

    listen 443 ssl;
    ssl on;
    ssl_certificate         /etc/nginx/cert.crt;
    ssl_certificate_key     /etc/nginx/cert.key;

    server_name main.big.vm;

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

更新 170501-1

我也注意到一个奇怪的行为。如果我输入带有结尾斜杠的 HTTPS URL,则 URL 会被加载,但如果我输入时不带结尾斜杠,则 URL 会以某种方式转换为 HTTP,并自动添加结尾斜杠

答案1

最后我终于搞定了。我找到了我以前关于 SSL nginx 反向代理与 Apache 的笔记,需要开启此配置

# file \apps\httpd\2225\conf.d\nginx-reverse-proxy.conf

# Make sure mod_env is loaded.
# This make sure variable _SERVER[HTTPS] is set if using Nginx as reverse proxy for Apache
# This will help some application to work, since many apps using _SERVER[HTTPS] to work with SSL
# Make sure Nginx has config: proxy_set_header X-Forwarded-Proto $scheme;

SetEnvIf X-Forwarded-Proto https HTTPS=on

由于我使用的是 Nginx 后端,因此我得到了这个配置来测试:

location ~ \.php$ {
    fastcgi_pass unix:/var/run/php5217-fpm.sock;
    fastcgi_index index.php;
    fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
    include fastcgi_params;
    fastcgi_param HTTPS 'on'; # I tested by adding this line to check
}

有用,现在我的 Moodle 可以在 HTTPS 前端(css、js、图片等)中顺利加载。现在我只需要一个类似于 Apache 的 Nginx 配置,SetEnvIf X-Forwarded-Proto https HTTPS=on或者确保我的所有后端每次都在 SSL 上运行

更新 170502:我在这里找到了这个例子https://stackoverflow.com/questions/4848438/fastcgi-application-behind-nginx-is-unable-to-detect-that-https-secure-connectio

答案2

在您的前端监听 80 然后立即将其永久重定向到 443

server { listen 80; location / { return 301 https://$host$request_uri; } }

答案3

扫描提供该链接的页面的 HTML 源代码mixed content warning,查看哪些资源是通过 HTTP 而不是 HTTPS 加载的。如果它们是外部资源,那么您就没那么幸运了。如果它们是内部资源,由于 HTML 页面是由您的 PHP 代码生成的,请查看您可以在 PHP 软件中执行哪些操作(可能是某些配置?)以确保所有图像/CSS/脚本等都使用该https方案而不是http一个方案。

相关内容