12
2022
12
09:51:30

运行OpenConnect VPN服务器;Apache/Nginx与HAProxy在同一个盒子上



推荐点击下面图片,通过本站淘宝优惠价购买:

image.png

先决条件



为了学习本教程,假设您已经使用Let's Encrypt TLS server证书设置了OpenConnect VPN服务器。如果没有,请遵循以下教程之一。



  • 在Ubuntu20.04上用Let's Encrypt设置OpenConnect VPN服务器(ocserv)

  • 使用Let's Encrypt在Ubuntu 16.04/18.04上设置OpenConnect VPN服务器(ocserv)

  • 使用Let's Encrypt在Debian 10 Buster上设置OpenConnect VPN服务器(ocserv)

  • 使用Let's Encrypt在CentOS 8/RHEL 8上设置OpenConnect VPN服务器(ocserv)



使OpenConnect VPN服务器和web服务器同时使用端口443



默认情况下,OpenConnect VPN服务器监听端口443。如果您已经让Apache/Nginx监听端口443,那么ocserv无法绑定到端口443。您可以将ocserv配置为在另一个端口上侦听,但这将要求最终用户在客户端软件中指定端口,如果您关心用户体验,应该避免使用该端口。此外,TCP端口443上的TLS流量通常在QoS(服务质量)方面享有更高的优先级,因此您将有更好的速度。



通常一个端口只能由一个进程使用。但是,我们可以使用HAproxy(高可用性代理)和SNI(服务器名称指示)使ocserv和Apache/Nginx同时使用端口443。



Ocserv配置



首先,编辑ocserv配置文件。



sudo nano /etc/ocserv/ocserv.conf



取消对以下行的注释。这将允许ocserv获取客户端IP地址,而不是HAproxy IP地址。



listen-proxy-proto = true



然后找到下面一行。



#listen-host = [IP|HOSTNAME]



换成



listen-host = 127.0.0.1



这将使ocserv监听127.0.0.1,因为稍后HAproxy将需要监听公共IP地址。保存并关闭文件。然后重启ocserv。



sudo systemctl restart ocserv



接下来,我们还需要让web服务器只监听本地主机,而不是监听公共IP地址。



Nginx配置



如果使用Nginx,请编辑服务器块文件。



sudo nano /etc/nginx/conf.d/example.com.conf



在SSL服务器块中,找到以下指令。



listen 443 ssl;



换成



listen 127.0.0.2:443 ssl;



这一次我们让它在127.0.0.2:443上收听,因为127.0.0.1:443已经被ocserv占用。保存并关闭文件。Nginx主配置文件/etc/Nginx/Nginx。conf和默认的server block/etc/nginx/sites enabled/default可能包括一个默认的虚拟主机监听443,所以您可能也需要编辑这个文件。



然后重新启动Nginx。



sudo systemctl restart nginx



Apache配置



如果使用Apache web服务器,请编辑虚拟主机文件。



Debian/Ubuntu



sudo nano /etc/apache2/sites-enabled/example.com.conf



森托斯/瑞尔



sudo nano /etc/httpd/conf.d/example.com.conf



在SSL虚拟主机中,更改



<VirtualHost *:443>





<VirtualHost 127.0.0.2:443>



这一次我们让它在127.0.0.2:443上收听,因为127.0.0.1:443已经被ocserv占用。保存并关闭文件。



然后编辑/etc/apache2/端口。Debian/Ubuntu上的conf文件。



sudo nano /etc/apache2/ports.conf



编辑/etc/httpd/conf.d/ssl。CentOS/RHEL上的conf文件。



sudo nano /etc/httpd/conf.d/ssl.conf



改变



Listen 443





Listen 127.0.0.2:443



保存并关闭文件。重启Apache。



sudo systemctl restart apache2





sudo systemctl restart httpd



单倍体构型



现在安装HAproxy。



sudo apt install haproxy





sudo dnf install haproxy



开始HAProxy



sudo systemctl start haproxy



编辑配置文件。



sudo nano /etc/haproxy/haproxy.cfg



如果使用Nginx,请将以下行复制并粘贴到文件末尾。将12.34.56.78替换为服务器的公共IP地址。替换vpn。实例com和ocserv和www.example使用的域名。com与您的web服务器使用的域名。



frontend https    bind 12.34.56.78:443    mode tcp    tcp-request inspect-delay 5s    tcp-request content accept if { req_ssl_hello_type 1 }     use_backend ocserv if { req_ssl_sni -i vpn.example.com }    use_backend nginx if { req_ssl_sni -i www.example.com }    use_backend nginx if { req_ssl_sni -i example.com }     default_backend ocserv  backend ocserv    mode tcp    option ssl-hello-chk    # pass requests to 127.0.0.1:443. Proxy protocol (v2) header is required by ocserv.    server ocserv 127.0.0.1:443 send-proxy-v2  backend nginx    mode tcp    option ssl-hello-chk    server nginx 127.0.0.2:443 check



如果使用Apache,请将以下行复制并粘贴到文件末尾。将12.34.56.78替换为服务器的公共IP地址。替换vpn。实例com和ocserv和www.example使用的域名。com与您的web服务器使用的域名。



frontend https    bind 12.34.56.78:443    mode tcp    tcp-request inspect-delay 5s    tcp-request content accept if { req_ssl_hello_type 1 }     use_backend ocserv if { req_ssl_sni -i vpn.example.com }    use_backend apache if { req_ssl_sni -i www.example.com }    use_backend apache if { req_ssl_sni -i example.com }     default_backend ocserv  backend ocserv    mode tcp    option ssl-hello-chk    # pass requests to 127.0.0.1:443. Proxy protocol (v2) header is required by ocserv.    server ocserv 127.0.0.1:443 send-proxy-v2  backend apache     mode tcp     option ssl-hello-chk     server apache 127.0.0.2:443 check



保存并关闭文件。然后重启HAproxy。



sudo systemctl restart haproxy



在上面的配置中,我们利用TLS中的SNI(服务器名称指示)功能来区分VPN流量和正常HTTPS流量。



  • 当vpn。实例com位于TLS客户端Hello,HAProxy将流量重定向到ocserv后端。

  • 当www.example。com位于TLS客户端Hello,HAProxy将流量重定向到apache/nginx后端。

  • 如果客户端没有在TLS client Hello中指定服务器名称,那么HAproxy将使用默认后端(ocserv)。



您可以使用openssl工具测试此设置。首先,多次运行以下命令。



echo | openssl s_client -connect your-server-IP:443 | grep subject



我们没有在上面的命令中指定服务器名称,因此HAproxy将始终将请求传递到默认后端(ocserv),其证书将发送到客户端。接下来,运行以下两个命令。



echo | openssl s_client -servername www.example.com -connect your-server-IP:443 | grep subject  echo | openssl s_client -servername vpn.example.com -connect your-server-IP:443 | grep subject



现在,我们在命令中指定了服务器名称,因此HAproxy将根据我们定义的SNI规则传递请求。请注意,Cisco AnyConnect应用程序不支持TLS SNI,因此最好在HAProxy配置文件中将ocserv设置为默认后端。



为您的网站续订Let's Encrypt证书时,建议您使用http-01质询而不是tls-alpn-01质询,因为HAproxy正在侦听公共IP地址的端口443,因此它可能会干扰续订过程。



sudo certbot renew --preferred-challenges http-01



修正单极性误差



如果您的Apache/Nginx网站没有显示在浏览器中,而您在haproxy日志(/var/log/haproxy.log)中看到以下消息



Server nginx/nginx is DOWN, reason: Socket error, info: "Connection reset by peer  backend nginx has no server available!  Layer6 invalid response



可能是您的后端Nginx web服务器正在使用带有OCSP扩展的TLS证书。Nginx不会在第一个HTTP请求时发送OCSP订书钉信息。要使其正常工作,请确保在Nginx虚拟主机配置中添加解析程序,如下所示。



{      ....      ssl_trusted_certificate /etc/letsencrypt/live/www.example.com/chain.pem;      ssl_stapling on;      ssl_stapling_verify on;      resolver 8.8.8.8;     .... }



保存并关闭文件。然后重新启动Nginx。



sudo systemctl restart nginx



此外,考虑删除HAproxy后端服务器的健康检查。所以改变



server nginx 127.0.0.2:443 check





server nginx 127.0.0.2:443



保存并关闭文件。然后重启HAproxy。



sudo systemctl restart haproxy



如何使用HAProxy在ocserv中启用IPv6



首先,为vpn创建AAAA记录。实例因此,当您在ocserv中完成IPv6设置后,DNS记录应该传播到Internet。



测试IPv6连接



要在IPv6协议中建立VPN隧道,请确保VPN服务器具有公共IPv6地址。(VPN客户端不必具有公共IPv6地址。)要找到答案,请运行以下命令。



ip addr



找到主网络接口。如果你能找到iNet 6。。。。范围全局行,如下图所示,则您有一个公共IPv6地址。带有作用域链接的inet6地址是专用IPv6地址。



那就去https://test-ipv6.com/检查你的IPv6连接。如果VPN客户端有一个公共IPv6地址,它可能会告诉您,您的VPN只保护一个协议,而不是两个协议。那是因为我们没有在ocserv中启用IPv6。



在ocserv中启用IPv6



要在ocserv中启用IPv6,请编辑ocserv配置文件。



sudo nano /etc/ocserv/ocserv.conf



找到下面两行并取消注释,这样VPN客户端将获得专用IPv6地址。



ipv6-network = fda9:4efe:7e3b:03ea::/48 ipv6-subnet-prefix = 64



如果你看到下面这行



ipv6-network = fda9:4efe:7e3b:03ea::/64



请将其更改为:



ipv6-network = fda9:4efe:7e3b:03ea::/48



保存并关闭文件。重新启动ocserv以使更改生效。



sudo systemctl restart ocserv



为IPv6启用IP转发



然后我们需要在Linux内核中为IPv6启用IP转发。编辑sysctl。conf文件。



sudo nano /etc/sysctl.conf



在该文件末尾添加以下行。



net.ipv6.conf.all.forwarding=1



保存并关闭文件。然后使用下面的命令应用更改。



sudo sysctl -p



在防火墙中设置IPv6(Debian、Ubuntu)



接下来,我们需要在UFW防火墙中设置IPv6伪装,以便服务器成为VPN客户端的虚拟路由器。



sudo nano /etc/ufw/before6.rules



默认情况下,过滤器表有一些规则。在该文件末尾添加以下行。将ens3替换为您自己的网络接口名称。在Nano文本编辑器中,按Ctrl+W,然后按Ctrl+V,可以转到文件的末尾。



# NAT table rules *nat :POSTROUTING ACCEPT [0:0] -A POSTROUTING -o ens3 -j MASQUERADE  # End each table with the 'COMMIT' line or these rules won't be processed COMMIT



默认情况下,UFW禁止数据包转发。我们可以允许我们的专用IPv6网络进行转发。在该文件中找到ufw6 before forward链,并添加以下3行,如果源IP或目标IP在fda9:4efe:7e3b:03ea::/48范围内,这3行将接受数据包转发。



# allow forwarding for VPN -A ufw6-before-forward -s fda9:4efe:7e3b:03ea::/48 -j ACCEPT -A ufw6-before-forward -d fda9:4efe:7e3b:03ea::/48 -j ACCEPT



保存并关闭文件。我们还需要在防火墙的输入链中允许IPv6 VPN客户端。



sudo ufw allow in from fda9:4efe:7e3b:03ea::/48



重新启动UFW以使更改生效。



sudo systemctl restart ufw



现在,如果使用以下命令列出NAT表的后路由链中的规则:



sudo ip6tables -t nat -L POSTROUTING



你可以看到化装规则。



断开当前VPN连接,为VPN添加AAAA记录。实例com并重新建立VPN连接。那就去https://test-ipv6.com/检查你的IPv6连接。



在防火墙中设置IPv6(CentOS)



为IPv6启用伪装。



sudo firewall-cmd --permanent --add-rich-rule='rule family="ipv6" source address="fda9:4efe:7e3b:03ea::/48" masquerade'



允许在输入链中使用VPN客户端。



sudo firewall-cmd --permanent --add-rich-rule='rule family="ipv6" source address="fda9:4efe:7e3b:03ea::/48" accept'



重新加载firewalld以使更改生效。



sudo systemctl reload firewalld



在绑定解析器中配置IPv6



如果在VPN服务器上运行自己的绑定DNS解析器,可以在/etc/ocserv/ocserv中添加以下行。conf文件,将VPN服务器设置为VPN客户端的DNS解析程序。



dns = fda9:4efe:7e3b::1



保存并关闭文件。要在IPv6中查询DNS名称,我们需要将BIND配置为允许IPv6 VPN客户端。



Debian/Ubuntu



sudo nano /etc/bind/named.conf.options



找到allow recursion参数并将其更改为:



allow-recursion { 127.0.0.1; 10.10.10.0/24; fda9:4efe:7e3b:03ea::/48; };



保存并关闭文件。重新启动BIND9。



sudo systemctl restart bind9



森托斯



sudo nano /etc/named.conf



找到allow query参数并将其更改为:



allow-query { 127.0.0.1; 10.10.10.0/24; fda9:4efe:7e3b:03ea::/48; };



保存并关闭文件。重新启动BIND9。



sudo systemctl restart named



在HAProxy中设置IPv6



编辑HAProxy配置文件。



sudo nano /etc/haproxy/haproxy.cfg



让https前端同时监听IPv4和IPv6地址。显然,您需要使用自己服务器的公共IPv6地址。



frontend https    bind 12.34.56.78:443    bind 2607:f8b0:4006:810::200e:443    mode tcp    tcp-request inspect-delay 5s    tcp-request content accept if { req_ssl_hello_type 1 }



然后找到ocserv后端并添加IPv6服务器。



backend ocserv    mode tcp    option ssl-hello-chk    server ocserv 127.0.0.1:443 send-proxy-v2    server ocserv6 [::1]:443 send-proxy-v2



保存并关闭文件。



要使ocserv同时在127.0.0.1和::1上侦听,请编辑/etc/hosts文件。



sudo nano /etc/hosts



编辑127.0.0.1和::1的条目,如下所示,这样vpn。实例com主机名可以解析为两个地址。



127.0.0.1   localhost vpn.example.com  ::1         ip6-localhost ip6-loopback vpn.example.com



保存并关闭文件。然后编辑ocserv配置文件。



sudo nano /etc/ocserv/ocserv.conf



找到下面这行。



listen-host = 127.0.0.1



换成



listen-host  = vpn.example.com



ocserv将查找vpn的IPv4和IPv6地址。实例com,并绑定到127.0.0.1和::1地址。保存并关闭文件。然后重启ocserv和HAProxy



sudo systemctl restart ocserv sudo systemctl restart haproxy



现在运行以下命令来检查ocserv的监听状态。您将看到它同时在127.0.0.1和::1上收听。



sudo ss -lnpt | grep ocserv



测试IPv6连接



重新启动VPN客户端并转到https://test-ipv6.com/检查你的IPv6连接。如果一切顺利,您应该在测试结果中看到VPN服务器的IPv4和IPv6地址。“VPN只保护一个协议”的警告应该消失。



如果在测试结果中看不到VPN服务器的IPv6地址,可能需要重新启动VPN客户端并重新建立VPN连接。



注意:VPN客户端不必具有公共IPv6地址。它可以通过IPv4 VPN隧道使用IPv6。


本文链接:https://hqyman.cn/post/3309.html 非本站原创文章欢迎转载,原创文章需保留本站地址!

分享到:





休息一下,本站随机推荐观看栏目:


« 上一篇 下一篇 »

发表评论:

◎欢迎参与讨论,请在这里发表您的看法、交流您的观点。

您的IP地址是: