如何在DigitalOcean负载平衡器上配置SSL通道

负载平衡器在多个后端服务器之间分配流量。当平衡加密的Web流量时,有两个主要配置选项:SSL终止和SSL直通。在本指南中,我们将演示如何使用SSL Passthrough配置DigitalOcean负载平衡器,确保数据保持直接加密到后端。

介绍

负载平衡器在多个后端服务器之间分配流量。 如果其中一个服务器出现故障,负载均衡器将重定向流量到其他服务器,确保您的服务继续可用。 负载平衡器还允许您添加其他资源来处理临时流量峰值或更一般的需求增加。 当平衡加密的Web流量时,有两个主要配置选项:SSL终止和SSL直通。

使用SSL终止,SSL请求在负载均衡器上解密,并以未加密的方式发送到后端。 这会在负载平衡器上放置更慢和更多的CPU密集型解密工作,并简化SSL证书的管理。 但是,负载平衡器和后端之间的流量未加密,这意味着它对该网段上的任何邻居都可见。

另一个选项是SSL Passthrough,它直接将SSL连接发送到后端。 与SSL终止不同,请求保持加密,解密负载分布在后端服务器上。 但是,必须在每个服务器上复制证书信息。 此外,您不能添加或修改HTTP头,因此您可能会丢失客户端的IP地址,端口和X-forwrded-*头中包含的其他信息。

在本指南中,我们将演示如何使用SSL Passthrough配置DigitalOcean负载平衡器,确保数据保持直接加密到后端。 要了解SSL终止,请参阅如何在DigitalOcean负载平衡器上配置SSL终止

先决条件

在本教程中,我们将使用:

一个Ubuntu 16.04 Droplet与:

  • sudo用户和基本防火墙。 指南, 与Ubuntu 16.04的初始服务器安装 ,可以帮助您。 我们已经在SFO1数据中心中创建了它,并将其称为backend-01 在本教程中,我们将在配置SSL证书之后创建第一个Droplet的映像,因此在教程结尾处,我们将使用两个后端服务器进行平衡。

此外,为了生成SSL证书,您将需要:

  • 您控制的域 :您必须拥有或控制您计划用于SSL证书的注册域名。 如果您还没有注册的域名,您可以向任何域名注册商注册一个域名(例如Namecheap,Omnis等)。 在本指南中,我们将使用passthrough.example.com作为域名。

在教程中,我们将在Droplet上安装Nginx并使用Let's Encrypt配置SSL。 由于我们设置了SSL直通,我们与负载平衡器一起使用的所有网络服务器都需要相同的证书,因此我们将创建第一台服务器的映像,并用它创建其他实例。

第1步 - 设置后端-01

我们将从在我们的后端服务器上安装Web服务器开始。 首先,刷新apt包的索引,然后使用以下命令安装nginx

sudo apt-get update
sudo apt-get install nginx

我们将在教程中稍后使用Ubuntu 16.04的Let's Encrypt客户端,因此我们现在也将安装:

sudo apt-get install letsencrypt

安装完成后,我们将允许HTTP和HTTPS流量通过UFW防火墙:

sudo ufw allow 'Nginx Full'
Rule added
Rule added (v6)

要确认是否添加了规则,我们将运行:

sudo ufw status
Status: active

To                         Action      From
--                         ------      ----
OpenSSH                    ALLOW       Anywhere
Nginx Full                 ALLOW       Anywhere
OpenSSH (v6)               ALLOW       Anywhere (v6)
Nginx Full (v6)            ALLOW       Anywhere (v6)

现在,我们已允许流量通过防火墙,我们将创建用于测试的内容。

添加测试页

为了确保一致的访问者体验,后端通常应该相同,但是我们将创建一个网页来标识此后端,以便测试负载均衡器。

在Web服务器的文档根目录中,我们将添加一个名为lb.html的文件:

sudo nano /var/www/html/lb.html

我们将输入以下内容

/var/www/html/lb.html on backend-01
<h1 style="color:blue">Backend-01</h1>

我们将保存文件并退出编辑器,然后在Web浏览器中使用HTTP访问该页面:

http://backend-01_ip_address/lb.html

浏览器应显示以下内容:

backend-01测试页面的屏幕截图

在测试内容就位后,我们就可以创建负载均衡器了

第2步 - 创建负载均衡器

我们将导航到负载平衡器页面,通过单击“网络”,然后加载“平衡器”:

具有导航步骤高度的屏幕截图

接下来,我们将点击“创建负载均衡器”,当没有负载均衡器时,它位于屏幕中央,而在右上角,有负载均衡器。

create-load-balancer按钮

在“创建负载均衡器”屏幕上,我们将:

  • 将负载平衡器命名为“ssl-passthrough”

  • 添加“backend-01”,它将自动选择“backend-01”所在的区域。

  • 创建负载均衡器

直到我们在backend-01上配置SSL后,我们才会添加我们的Passthrough规则。 如果我们要在SSL可用之前添加规则,那么健康检查将失败,并且Droplet将不会在池中可用。

创建负载平衡器屏幕的屏幕截图

这将带我们到负载平衡器索引页面,并且创建负载平衡器时将显示一个进度条,这需要几分钟。 完成后,页面将自动更新并显示“新建”,并显示负载均衡器的IP地址。

新创建的负载平衡器的屏幕截图

完成后,我们可以检查端口80上的流量,以确保其正确转发到后端。

让我们通过负载均衡器的IP地址访问我们的测试页:

http://load_balancer_ip_address/lb.html

我们应该收到backend-01的内容,这次通过负载均衡器提供服务:

backend-01的屏幕截图由负载均衡器提供

这将验证负载平衡器是否已成功将流量引导到我们的后端。 下一步是配置DNS以生成SSL证书。

第3步 - 为负载均衡器分配域名

现在我们有了将域名指向负载均衡器的IP地址所需的信息。

您可以按照有关使用DigitalOcean设置域名的指南,为您的域创建A记录或查阅DNS服务的文档。

重要:请务必使用负载平衡器的IP地址,而不是特定Droplet的地址。

完成DNS配置后,您应该能够使用HTTP在Web浏览器中访问该域,负载均衡器应将请求传递到后端。

http://passthrough.example.com/lb.html

backend-01的屏幕截图通过域名访问

当您可以通过域名访问backend-01时,就可以设置SSL和证书。

第4步 - 配置Nginx使用SSL

由于我们将在后端解密HTTPS请求,因此我们需要配置Nginx接受HTTPS。 我们将在默认配置文件中这样做:

sudo nano /etc/nginx/sites-available/default

首先,我们将服务器名称添加到默认服务器配置:

/ etc / nginx / sites-available / default
 . . .
# Default server configuration
#
server {
        listen 80 default_server;
        listen [::]:80 default_server;
        server_name passthrough.example.com;
        # SSL configuration
        #
        # listen 443 ssl default_server;
        # listen [::]:443 ssl default_server;

当我们请求我们的证书时,Let's Encrypt将需要一个位置块来响应证书质询,所以我们现在添加该块。 我们将它放在我们的服务器名称正下方:

/ etc / nginx / sites-enabled / default
 . . .
server {
        listen 80 default_server;
        listen [::]:80 default_server;
        server_name passthrough.example.com;
        location ~ /.well-known {
           allow all;
        }
        # SSL configuration
        #
        # listen 443 ssl default_server;
        # listen [::]:443 ssl default_server;
    . . .
}

此正则表达式location块明确允许访问包含.well .well-known请求

接下来,我们将通过取消注释443条listen指令来启用SSL:

/ etc / nginx / sites-enabled / default
 . . .

server {
        listen 80 default_server;
        listen [::]:80 default_server;
        server_name passthrough.example.com;
        location ~ /.well-known {
           allow all;
        }
        # SSL configuration
        #
        listen 443 ssl default_server;
        listen [::]:443 ssl default_server;
    . . .
}

最后,我们将创建一个配置片段,以便Nginx可以加载证书文件。 我们现在将包括该文件。 在下面的行中,请确保在文件名称ssl- passthrough.example.com .conf中替换您的域名:

/ etc / nginx / sites-enabled / default
 . . .
        listen 443 ssl default_server;
        listen [::]:443 ssl default_server;
        include snippets/ssl-passthrough.example.com.conf;        
    . . .
}

完成后,保存并关闭文件。

在我们测试配置之前,我们需要创建代码片段文件,以便稍后填写:

sudo touch /etc/nginx/snippets/ssl-passthrough.example.com.conf

使用该文件,我们可以使用以下命令测试语法错误的配置:

sudo nginx -t

如果没有发现问题,我们应该收到如下输出:

nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

要使新配置生效,我们需要重新启动Nginx,但在我们这样做之前,我们将生成SSL证书并填写代码片段文件。

第5步 - 生成一个让我们加密证书

我们将使用以下命令为我们的域请求证书。 将您的域替换为第一个-d后的参数,以及附加-d标志后的任何其他名称:

sudo letsencrypt certonly -a webroot --webroot-path=/var/www/html -d passthrough.example.com

系统会提示您输入辅助电子邮件地址,然后接受我们的加密条款及细则。 在我们完成后,如果一切都成功,我们应该收到一条消息:

IMPORTANT NOTES:
 - If you lose your account credentials, you can recover through
   e-mails sent to sammy@digitalocean.com.
 - Congratulations! Your certificate and chain have been saved at
   /etc/letsencrypt/live/passthrough.example.com/fullchain.pem. Your
   cert will expire on 2017-05-10. To obtain a new version of the
   certificate in the future, simply run Let's Encrypt again.
 - Your account credentials have been saved in your Let's Encrypt
   configuration directory at /etc/letsencrypt. You should make a
   secure backup of this folder now. This configuration directory will
   also contain certificates and private keys obtained by Let's
   Encrypt so making regular backups of this folder is ideal.
 - If you like Let's Encrypt, please consider supporting our work by:

   Donating to ISRG / Let's Encrypt:   https://letsencrypt.org/donate
   Donating to EFF:                    https://eff.org/donate-le

要使用我们新生成的证书,我们将在snippets目录中创建一个新的Nginx配置片段。 这必须与我们之前添加到默认配置的文件名相匹配:

sudo nano /etc/nginx/snippets/ssl-passthrough.example.com.conf

在文件中,我们将设置ssl_certificatessl_certificate_key指令:

/etc/nginx/snippets/ssl-passthrough.example.com.conf
ssl_certificate /etc/letsencrypt/live/passthrough.example.com/fullchain.pem;
ssl_certificate_key /etc/letsencrypt/live/passthrough.example.com/privkey.pem;

我们将再次仔细检查配置语法:

sudo nginx -t

一旦我们确认语法是好的,我们将重新启动Web服务器以加载我们的配置更改:

sudo systemctl restart nginx

有关SSL配置的更详细的讨论,请参阅如何使用Ubuntu 16.04安全加密Nginx

现在,我们已经有一个SSL证书,并已配置Web服务器使用它,我们准备添加SSL直通规则。

第6步 - 添加负载平衡器SSL直通规则

我们测试了我们的DNS解析到负载平衡器,并且我们在后端配置了SSL,现在我们可以添加SSL直通规则。

为此,我们将返回到负载平衡器索引页面,并打开ssl-passthrough的“更多”菜单,然后选择“编辑设置”。

“展开的更多”菜单的屏幕截图

从这里,我们将点击“编辑”按钮添加转发规则:

编辑规则

从“新规则”下拉列表中,我们将选择HTTPS协议,这将打开一个新的选项行。 在显示“证书:”的下拉菜单中,我们将选择“Passthrough”。当我们这样做时,Droplet协议将自动更改为HTTPS,端口将更新为默认的SSL端口443,保存按钮将会可用。

完成的Passthrough规则的屏幕截图

我们将点击“保存”,我们已准备好通过使用HTTPS在网络浏览器中访问测试页来测试SSL直通:

https://domain_name/lb.html

我们应该看到测试内容,以及请求是安全的指示,虽然确切的符号将取决于Web浏览器:

负载平衡器由域提供的测试页面的屏幕截图

现在剩下的只是向后端添加另一个Droplet并验证平衡是否按预期工作。

第7步 - 复制Web服务器

对于SSL Passthrough,负载均衡器后面的所有Web服务器都需要使用相同的SSL证书。 为了实现这一点以及确保我们的后端配置相同,我们将拍摄backend-01的快照并创建一个额外的Droplet。

注意:如果愿意,您可以使用scprsync将证书文件从一个服务器复制到另一个服务器。

我们将导航到图片,选择Droplet backend-01 ,然后点击“拍摄快照”按钮:

“拍摄快照”页面的屏幕截图

当快照完成后,我们将点击右上角的“创建Droplet”按钮,这将带我们到“创建Droplets”屏幕。 在这里,我们将选择“快照”

我们会选择我们刚刚创建的图片。 您可以调整可用选项,如大小,其他选项,如果需要ssh键。 我们将保留默认值,并将此名称命名为Droplet backend-02 ,然后单击“创建”:

一旦我们的Droplet创建,我们将使用ssh连接到它,以更新测试页:

sudo nano /var/www/html/lb.html

我们将替换或更新标题为以下内容:

<h1 style="color: orange">Backend-02</h1>

最后,我们将保存并退出文件,然后通过Droplet IP地址查看更新的内容:

http://ip_address_of_backend-02/lb.html

后端-02-by-ip

一旦我们确认服务器IP地址的HTTP请求按预期加载,我们就可以将其添加到负载均衡器。

第8步 - 向负载均衡器添加后端-02

让我们添加backend-02 ,这样我们可以看到我们的负载平衡器在行动!

我们将返回到负载平衡器索引页面(网络>负载平衡器)。 如果只有一个负载均衡器,您可以从该页面添加Droplet; 否则,单击负载均衡器的名称,然后单击“添加Droplet”。 添加' backend-02 ,然后点击“添加Droplet”。

add-backend-02

一旦第二个服务器响应了健康检查并标记为健康,我们就可以测试了。

第9步 - 测试平衡

现在我们在后端有两个Droplets,我们可以通过使用HTTPS访问我们的测试页面通过域名测试我们的负载均衡器:

https://passthrough.example.com/lb.html

应加载两个后端之一。 应该在地址栏中将连接标记为安全,但安全状态的显示方式将因浏览器而异。

负载平衡器https-1

当我们刷新页面时,我们应该看到负载切换到第二个后端。

负载平衡器https-2

这确认了我们在两个后端服务器之间平衡SSL流量。 通过使用SSL Passthrough,我们确保HTTPS请求是端到端加密的。

注意:如果您在访问负载均衡器的IP地址时可以看到多个后端,但在访问域名时却无法看到多个后端,请验证是否使用负载均衡器的IP设置了DNS,而不是其中一个IP地址的IP地址后端Droplet。

结论

在本教程中,我们演示了如何通过在单个Droplet上设置Nginx with Let's Encrypt SSL证书来配置DigitalOcean负载均衡器以使用SSL Passthrough。 我们创建了第一个Droplet的DigitalOcean映像,然后用于为后端创建其他服务器。