如何在Rocky Linux 9上使用Let’s Encrypt保护Nginx

介绍

Let’s Encrypt是一个证书颁发机构(CA),提供了一种方便获取和安装免费的TLS/SSL证书的方式,从而在web服务器上启用了加密的HTTPS。它通过提供一个软件客户端Certbot来简化该过程,该客户端试图自动化大部分(如果不是全部)所需的步骤。目前,在Apache和Nginx上获取和安装证书的整个过程都是完全自动化的。

在本教程中,您将使用Certbot为Rocky Linux 9上的Nginx获取一个免费的SSL证书,并设置您的证书以自动更新。

本教程将使用单独的Nginx服务器配置文件而不是默认文件。您应该为每个域创建新的Nginx服务器块文件,因为这有助于避免常见的错误并将默认文件保留为备用配置。

先决条件

要按照本教程,您需要:

  • 按照这个 Rocky Linux 9 初始服务器设置 教程设置的一个 Rocky Linux 9 服务器,包括一个启用 sudo 权限的非 root 用户和一个防火墙。

  • 一个已注册的域名。本教程将始终使用 example.com。您可以从 Namecheap 购买域名,使用 Freenom 免费获取一个,或者使用您选择的域名注册商。

  • 为您的服务器设置了以下两个 DNS 记录。如果您使用的是 DigitalOcean,请参阅我们的 DNS 文档 以获取有关如何添加它们的详细信息。

    • 一个 A 记录,指向您服务器的公共 IP 地址:example.com
    • 一个 A 记录,指向您服务器的公共 IP 地址:www.example.com
  • 按照 在 Rocky Linux 9 上安装 Nginx 中的指导安装 Nginx。确保你有一个针对你域名的服务器块。本教程将使用 `/etc/nginx/sites-available/example.com` 作为示例。

第一步 — 安装 Certbot

首先,你需要安装 certbot 软件包。以非根用户身份登录到你的 Rocky Linux 8 机器:

  1. ssh sammy@your_server_ip

certbot 软件包默认情况下无法通过软件包管理器获得。你需要启用 EPEL 仓库来安装 Certbot。

要添加 Rocky Linux 9 的 EPEL 仓库,请运行以下命令:

  1. sudo dnf install epel-release

当要求确认安装时,输入 y 并按 Enter。

现在你已经可以访问额外的仓库,安装所有所需的软件包:

  1. sudo dnf install certbot python3-certbot-nginx

这将安装Certbot本身以及Certbot所需的Nginx插件,该插件用于运行程序。

安装过程会询问您是否导入GPG密钥。确认后,安装即可完成。

现在您已经安装了Certbot,让我们运行它以获取证书。

步骤2 —— 确认Nginx的配置

Certbot需要能够在您的Nginx配置中找到正确的server块,以便能够自动配置SSL。具体来说,它通过查找与您请求证书的域匹配的server_name指令来实现此目的。

如果您在Nginx安装教程中遵循了服务器块设置步骤,您应该在/etc/nginx/conf.d/example.com下拥有一个用于您的域的服务器块,并且server_name指令已经适当设置。

要检查,请使用nano或您喜欢的文本编辑器打开您域的配置文件:

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

找到现有的server_name行。它应该像这样:

/etc/nginx/conf.d/example.com
...
server_name example.com www.example.com;
...

如果是这样,请退出编辑器并继续下一步。

如果不是,请更新以匹配。然后保存文件,退出编辑器,并验证您的配置编辑的语法:

  1. sudo nginx -t

如果出现错误,请重新打开服务器块文件并检查是否有拼写错误或缺少字符。一旦您的配置文件语法正确,重新加载 Nginx 以加载新配置:

  1. sudo systemctl reload nginx

Certbot 现在可以找到正确的 server 块并自动更新它。

接下来,让我们更新防火墙以允许 HTTPS 流量。

步骤 3 — 更新防火墙规则

由于您的先决设置启用了 firewalld,您需要调整防火墙设置,以允许外部连接到您的 Nginx web 服务器。

要检查已启用的服务,运行以下命令:

  1. sudo firewall-cmd --permanent --list-all

您将收到如下输出:

Output
public target: default icmp-block-inversion: no interfaces: sources: services: cockpit dhcpv6-client http ssh ports: protocols: masquerade: no forward-ports: source-ports: icmp-blocks: rich rules:

如果在服务列表中看不到 http,请通过运行以下命令启用它:

  1. sudo firewall-cmd --permanent --add-service=http

要允许 https 流量,请运行以下命令:

  1. sudo firewall-cmd --permanent --add-service=https

要应用更改,您需要重新加载防火墙服务:

  1. sudo firewall-cmd --reload

现在您已经将服务器开放给 https 流量,可以运行 Certbot 并获取您的证书了。

步骤 4 — 获取 SSL 证书

Certbot通过插件提供了多种获取SSL证书的方式。Nginx插件会负责重新配置Nginx并在必要时重新加载配置。要使用此插件,请输入以下命令:

  1. sudo certbot --nginx -d example.com -d www.example.com

这将使用--nginx插件运行certbot,并使用-d指定需要证书有效的域名。

运行命令时,您将被提示输入电子邮件地址并同意服务条款。之后,您应该会看到一条消息,告诉您该过程成功,并显示您的证书存储位置:

Output
Successfully received certificate. Certificate is saved at: /etc/letsencrypt/live/your_domain/fullchain.pem Key is saved at: /etc/letsencrypt/live/your_domain/privkey.pem This certificate expires on 2022-12-15. These files will be updated when the certificate renews. Certbot has set up a scheduled task to automatically renew this certificate in the background. Deploying certificate Successfully deployed certificate for your_domain to /etc/nginx/conf.d/your_domain.conf Successfully deployed certificate for www.your_domain to /etc/nginx/conf.d/your_domain.conf Congratulations! You have successfully enabled HTTPS on https://your_domain and https://www.your_domain

您的证书已下载、安装和加载,您的Nginx配置现在将自动将所有Web请求重定向到https://。尝试重新加载您的网站并注意您浏览器的安全指示器。它应该指示该站点已经得到适当的安全保护,通常会显示一个锁图标。如果您使用SSL实验室服务器测试测试服务器,它将获得一个A等级。

最后,让我们测试续订过程。

步骤5 —— 验证Certbot自动续订

Let’s Encrypt证书有效期为90天,但建议每60天更新一次证书,以留有错误的余地。Certbot Let’s Encrypt客户端具有一个renew命令,它会自动检查当前安装的证书,并在距离到期日期不足30天时尝试续订它们。

您可以通过运行以下命令来测试证书的自动续订:

  1. sudo certbot renew --dry-run

输出将类似于这样:

Output
Saving debug log to /var/log/letsencrypt/letsencrypt.log - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Processing /etc/letsencrypt/renewal/your_domain.conf - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - Cert not due for renewal, but simulating renewal for dry run Plugins selected: Authenticator nginx, Installer nginx Renewing an existing certificate Performing the following challenges: http-01 challenge for monitoring.pp.ua Waiting for verification... Cleaning up challenges - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - new certificate deployed with reload of nginx server; fullchain is /etc/letsencrypt/live/your_domain/fullchain.pem - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - ** DRY RUN: simulating 'certbot renew' close to cert expiry ** (The test certificates below have not been saved.) Congratulations, all renewals succeeded. The following certs have been renewed: /etc/letsencrypt/live/your_domain/fullchain.pem (success) ...

请注意,如果您创建了包含多个域名的捆绑证书,则输出中仅显示基础域名,但续订将适用于此证书中包含的所有域名。

A practical way to ensure your certificates will not get outdated is to create a cron job that will periodically execute the automatic renewal command for you. Since the renewal first checks for the expiration date and only executes the renewal if the certificate is less than 30 days away from expiration, it is safe to create a cron job that runs every week, or even every day.

编辑crontab以创建一个新的作业,每天运行两次续订。要编辑root用户的crontab,请运行:

  1. sudo crontab -e

您的文本编辑器将打开默认的crontab,在这一点上,它是一个空文本文件。通过按下i进入插入模式,并添加以下行:

crontab
0 0,12 * * * python -c 'import random; import time; time.sleep(random.random() * 3600)' && certbot renew --quiet

完成后,按ESC退出插入模式,然后按:wqENTER保存并退出文件。要了解更多关于文本编辑器Vi及其后继者Vim的信息,请查看我们的在云服务器上安装和使用Vim文本编辑器教程。

这将创建一个新的cron作业,每天中午和午夜执行。python -c 'import random; import time; time.sleep(random.random() * 3600)'将在一小时内选择一个随机分钟进行续订任务。

renew命令用于Certbot将检查系统上安装的所有证书,并更新任何在不到三十天后到期的证书。--quiet告诉Certbot不输出信息或等待用户输入。

有关续订的更详细信息可以在Certbot文档中找到。

结论

在本指南中,您安装了Let’s Encrypt客户端Certbot,为您的域名下载了SSL证书,并设置了自动证书续订。如果您对使用Certbot有任何疑问,可以查看官方Certbot文档

您还可以定期检查官方Let’s Encrypt博客以获取重要更新。

Source:
https://www.digitalocean.com/community/tutorials/how-to-secure-nginx-with-let-s-encrypt-on-rocky-linux-9