Nginx 负载均衡 HTTPs 集群

时间:2021-04-20 08:50:43

标签: nginx ssl load-balancing consul nginx-upstreams

我想使用 Nginx 作为 Consul 集群的负载均衡器。 Consul 集群只能通过 TLS 访问。

在这里,我尝试反向代理单个 Consul 服务器以检查 TLS 证书是否有效

server {
    listen 80;
    listen [::]:80;
    
    location  /consul/ {

        resolver 127.0.0.1;

        proxy_pass https://core-consul-server-1-dev.company.io:8500;

        sub_filter_types text/css application/javascript;
        sub_filter_once off;
        sub_filter /v1/ /consul_v1/;

        proxy_ssl_certificate      /etc/nginx/certs/agent.crt;
        proxy_ssl_certificate_key  /etc/nginx/certs/agent.key;
        proxy_ssl_trusted_certificate  /etc/nginx/certs/ca.crt;
        proxy_ssl_verify        on;
        proxy_ssl_verify_depth  4;      

    }
}

这个配置工作正常,我可以调用它

curl http://core-proxy-server-1-dev.company.io/consul/consul_v1/agent/members

现在我尝试做这样的上游:

upstream consul {
    server core-consul-server-1-dev.company.io:8500;
    server core-consul-server-2-dev.company.io:8500;
}

server {

    listen 80;
    listen [::]:80;
  
    
    location  /consul/ {

        resolver 127.0.0.1;

        proxy_pass https://consul;
        sub_filter_types text/css application/javascript;
        sub_filter_once off;
        sub_filter /v1/ /consul_v1/;
        
        proxy_ssl_certificate      /etc/nginx/certs/agent.crt;
        proxy_ssl_certificate_key  /etc/nginx/certs/agent.key;
        proxy_ssl_trusted_certificate  /etc/nginx/certs/ca.crt;
        proxy_ssl_verify        on;
        proxy_ssl_verify_depth  4;      

    } 
}

在调用与之前相同的 curl 命令时,出现以下错误:

2021/04/20 08:38:59 [debug] 3364#3364: *1 X509_check_host(): no match
2021/04/20 08:38:59 [error] 3364#3364: *1 upstream SSL certificate does not match "consul" while SSL handshaking to upstream, client: 10.10.xx.xxx, server: , request: "GET /consul/consul_v1/agent/members HTTP/1.1", upstream: "https://10.10.yy.yyy:8500/consul/consul_v1/agent/members", host: "core-proxy-server-1-dev.company.io"

然后我试过这样:

upstream consul_1 {
    server core-consul-server-1-dev.company.io:8500;
}

upstream consul_2 {
    server core-consul-server-2-dev.company.io:8500;
}

map $http_host $backend {
    core-consul-server-1-dev.company.io       consul_1;
    core-consul-server-2-dev.company.io       consul_2;

}

server {

    listen 80;
    listen [::]:80;
  
    
    location  /consul/ {

        resolver 127.0.0.1;

        proxy_pass https://$backend;
        sub_filter_types text/css application/javascript;
        sub_filter_once off;
        sub_filter /v1/ /consul_v1/;
        
        proxy_ssl_certificate      /etc/nginx/certs/agent.crt;
        proxy_ssl_certificate_key  /etc/nginx/certs/agent.key;
        proxy_ssl_trusted_certificate  /etc/nginx/certs/ca.crt;
        proxy_ssl_verify        on;
        proxy_ssl_verify_depth  4;      

    }

}

但也没有运气;

2021/04/20 08:45:05 [error] 3588#3588: *1 invalid URL prefix in "https://", client: 10.10.xx.xxx, server: , request: "GET /consul/consul_v1/agent/members HTTP/1.1", host: "core-proxy-server-1-dev.company.io"

有什么想法吗?有人可以帮我一个吗?

1 个答案:

答案 0 :(得分:1)

我想通了。

在这个变体中:

upstream consul {
    server core-consul-server-1-dev.company.io:8500;
    server core-consul-server-2-dev.company.io:8500;
}

server {

    listen 80;
    listen [::]:80;
  
    
    location  /consul/ {

        resolver 127.0.0.1;

        proxy_pass https://consul;
        sub_filter_types text/css application/javascript;
        sub_filter_once off;
        sub_filter /v1/ /consul_v1/;
        
        proxy_ssl_certificate      /etc/nginx/certs/agent.crt;
        proxy_ssl_certificate_key  /etc/nginx/certs/agent.key;
        proxy_ssl_trusted_certificate  /etc/nginx/certs/ca.crt;
        proxy_ssl_verify        on;
        proxy_ssl_verify_depth  4;      

    } 
}

上游名称 consul 也应与我在证书中定义的 alt_names 匹配。所以将配置更改为下面的配置就成功了:

upstream core-consul-server-1-dev.company.io{
    server core-consul-server-1-dev.company.io:8500;
    server core-consul-server-2-dev.company.io:8500;
}

server {

    listen 80;
    listen [::]:80;
  
    
    location  /consul/ {

        resolver 127.0.0.1;

        proxy_pass https://core-consul-server-1-dev.company.io;
        sub_filter_types text/css application/javascript;
        sub_filter_once off;
        sub_filter /v1/ /consul_v1/;
        
        proxy_ssl_certificate      /etc/nginx/certs/agent.crt;
        proxy_ssl_certificate_key  /etc/nginx/certs/agent.key;
        proxy_ssl_trusted_certificate  /etc/nginx/certs/ca.crt;
        proxy_ssl_verify        on;
        proxy_ssl_verify_depth  4;      

    } 
}

我应该稍后在 alt_names 中添加一个通用名称,以便我可以将流引用为

core-consul-server-dev.company.io