虽然我能够成功配置 nginx 来代理 HTTP 流量(使用本指南),所有代理 HTTPS 请求的尝试都导致代码 400(错误的请求)。
Nginx 调试日志根本没有帮助:
2013/06/05 14:38:33 [info] 74946#0: *589
client sent invalid request while reading client request line, client: 127.0.0.1,
server: google.com, request: "CONNECT google.com:443 HTTP/1.1"
这些请求是什么?在 nginx 中CONNECT
是否可以进行HTTPS 请求?proxy_pass
更新
需要补充的是,代理服务器是我 Web 开发工作流程/工具包的一部分。这是测试/调试客户端 JavaScript 的好方法生产环境(在代理之前使用重写)。
nginx 的配置语言本身也可以说是一门编程语言。它有变量!
答案1
似乎 nginx 不支持使用 SSL 的正向代理模式。您需要使用类似乌贼而是。这里有一个来自 nginx 作者的更多解释的链接:HTTPS 和 nginx 作为正向代理。
答案2
只是为了澄清:正如我在博客的评论提要中所写的,nginx 不处理用于通过 HTTP 代理建立到远程主机的原始 TCP 连接的 CONNECT 方法调用 - 这是有道理的,因为 nginx 不应该作为正向代理工作,无论如何,它恰好可以很好地用于常规 HTTP。
Nginx 根本不知道如何处理这些方法调用,这就是为什么日志中的错误消息毫无用处。我发现自己总是使用 privoxy 进行 HTTPS:http://www.privoxy.org/- 设置起来也非常简单。但仍然不可能过滤或篡改 HTTPS 中继的内容,因为 HTTPS 连接是通过 CONNECT 方法使用原始连接处理的,服务器不知道它中继的是什么。
答案3
如果你不介意从源代码编译 nginx,你可以安装ngx_http_proxy_connect_module。在 Raspberry Pi 上的 Debian 9 “Stretch” 中,以下内容对我有用(在我将 deb-src URL 添加到 /etc/apt/sources.list 并执行 apt-get update 之后):
cd /tmp &&
apt-get source nginx &&
git clone https://github.com/chobits/ngx_http_proxy_connect_module &&
cd nginx-* &&
patch -p1 < ../ngx_http_proxy_connect_module/proxy_connect.patch &&
sudo apt-get install libpcre3-dev &&
./configure --add-module=/tmp/ngx_http_proxy_connect_module &&
make && sudo make install
然后编辑/usr/local/nginx/conf/nginx.conf
并使其看起来像这样(我包含了您想要阻止的域的示例,它适用于 SSL 和非 SSL 代理):
user www-data;
worker_processes auto;
events { }
http {
server_names_hash_bucket_size 128;
server {
listen 8888;
server_name spam.example.com *.spam.example.com;
server_name spam2.example.com *.spam2.example.com;
access_log off;
return 404;
}
server {
listen 8888;
server_name ~.+;
proxy_connect;
proxy_max_temp_file_size 0;
resolver 8.8.8.8;
location / {
proxy_pass http://$http_host;
proxy_set_header Host $http_host;
}
}
}
然后运行/usr/local/nginx/sbin/nginx
。nginx
如果您还在端口 80 上运行生产 Web 服务器,并且不想冒险弄乱它(但请确保/usr/local
在启动时单独启动该版本),它将与 Debian 的库存包非常愉快地共存;或者,通过更多配置,您可以从编译的 nginx 运行这两个服务。但是,如果您确实将编译的 nginx 设置为在防火墙允许流量的端口上运行,请注意您必须手动检查 nginx 安全更新,因为 Debian 软件包系统将不再为您执行此操作。
答案4
我的团队花了一些时间才弄清楚如何实现这一点。最后,我们通过将下面的代码片段嵌入到 nginx.conf 中来实现它:
stream {
map_hash_bucket_size 128;
map $ssl_preread_server_name $sphere {
site-01.example.com site-01;
site-02.example.com site-02;
}
upstream site-01 {
server 192.168.0.1:443;
}
upstream site-02 {
server 192.168.0.2:443;
}
server {
listen 443;
proxy_pass $sphere;
ssl_preread on;
}
}