如何为Nginx创建自签名SSL证书

简介

SSL(Secure Sockets Layer 安全套接层),及其继任者传输层安全(Transport Layer Security,TLS)是为网络通信提供安全及数据完整性的一种安全协议。 TLS与SSL在传输层对网络连接进行加密。

使用这种技术,服务器可以在服务器和客户端之间安全地发送流量,而不会被外部各方拦截。证书系统还可以帮助用户验证他们正在连接的站点的身份。

在本文中,我们将向您展示如何设置自签名SSL证书,以便与服务器上的Nginx Web服务器一起使用。

注意:自签名证书会加密服务器与任何客户端之间的通信。但是,由于Web浏览器没有包含任何受信任的证书颁发机构,因此用户无法使用该证书自动验证服务器的身份。

在您没有与服务器关联的域名以及加密Web界面不面向用户的情况下,则可能需要使用自签名证书。如果你已经有一个域名,在很多情况下,使用CA签名的证书会更好。您可以在此处了解如何使用腾讯云免费SSL证书设置可信证书。

准备

开始之前,你应该先购买一台服务器,我建议您使用腾讯云免费开发者专属在线实验平台进行试验。

您还需要安装Nginx Web服务器。如果您想在服务器上安装整个LNMP(Linux,Nginx,MySQL,PHP)可以参考这个教程

第一步、创建SSL证书

TLS/SSL通过公共证书和密钥的相互结合来运行。SSL密钥在服务器上保密。它用于加密发送给客户端的内容。SSL证书与任何请求获得内容的人共享。它可用于解密由关联的SSL密钥签名的内容。

我们可以在命令中使用OpenSSL创建自签名密钥和证书:

sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/ssl/private/nginx-selfsigned.key -out /etc/ssl/certs/nginx-selfsigned.crt

在我们继续操作之前,让我们看看命令中发生了什么:

  • openssl:这是用于创建和管理OpenSSL证书、密钥和其他文件的基本命令工具。
  • req:此子命令指定我们要使用X.509证书签名请求管理。“X.509”是SSL和TLS为其密钥和证书管理所遵循的公钥基础结构标准。我们想要创建一个新的X.509证书,所以我们使用这个子命令。
  • -x509:这通过告诉实用程序我们要创建自签名证书而不是生成证书签名请求来进一步修改上一个子命令。
  • -nodes:这告诉OpenSSL跳过用密码保护我们的证书的选项。当服务器启动时,我们需要Nginx能够在没有用户干预的情况下读取文件。密码短语会阻止这种情况发生,因为我们必须在每次重启后输入密码。
  • -days 365:此选项设置证书的有效时间长度。我们在这里设置了一年。
  • -newkey rsa:2048:这指定我们要同时生成新证书和新密钥。我们没有创建在上一步中签署证书所需的密钥,因此我们需要将其与证书一起创建。该rsa:2048部分告诉它制作一个2048位长的RSA密钥。
  • -keyout:这一行告诉OpenSSL在哪里放置我们正在创建的生成的私钥文件。
  • -out:这告诉OpenSSL在哪里放置我们正在创建的证书。

如上所述,这些选项将创建密钥文件和证书。我们将询问有关我们服务器的一些问题,以便将信息正确地填入到证书中。

 最重要的一行是请求Common Name (e.g. server FQDN or YOUR name)。您需要输入与服务器关联的域名,或者是您服务器的公共IP地址。

整个提示将如下所示:

Country Name (2 letter code) [AU]:US
State or Province Name (full name) [Some-State]:New York
Locality Name (eg, city) []:New York City
Organization Name (eg, company) [Internet Widgits Pty Ltd]:Bouncy Castles, Inc.
Organizational Unit Name (eg, section) []:Ministry of Water Slides
Common Name (e.g. server FQDN or YOUR name) []:server_IP_address
Email Address []:admin@your_domain.com

您创建的两个文件都将放在/etc/ssl目录的相应子目录中。

在我们使用OpenSSL的同时,我们还应该创建一个完整的Diffie-Hellman组,用于与客户协商完整的保密。

我们可以通过输入以下内容来执行

sudo openssl dhparam -out /etc/ssl/certs/dhparam.pem 2048

这可能需要几分钟,一旦完成,您将拥有一个强大的DH组。/etc/ssl/certs/dhparam.pem可以在我们的配置中使用。

第二步、配置Nginx以使用SSL

我们在/etc/ssl目录下创建了密钥和证书文件。现在我们只需要修改我们的Nginx配置就可以使用它们。

我们将对配置进行一些调整。

  1. 我们将创建一个包含SSL密钥和证书文件位置的配置代码。
  2. 我们将创建一个包含强SSL设置的配置代码,可以在将来与任何证书一起使用。
  3. 我们将调整我们的Nginx配置文件来处理SSL请求并使用上面的两个代码段。

这种配置Nginx的方法将允许将常见配置段放入可重用模块中。

创建指向SSL密钥和证书的配置代码

首先,让我们在/etc/nginx/snippets目录中创建一个新的Nginx配置代码。

为了正确区分此文件,我们称之为self-signed.conf

sudo nano /etc/nginx/snippets/self-signed.conf

在这个文件中,我们只需要将ssl_certificate设置为我们的证书文件和ssl_certificate_key相关的密钥。在我们的例子中,是这样的:

ssl_certificate /etc/ssl/certs/nginx-selfsigned.crt;
ssl_certificate_key /etc/ssl/private/nginx-selfsigned.key;

添加这些行后,保存并关闭该文件。

使用强加密设置创建配置代码

接下来,我们将创建另一个代码,用于定义一些SSL设置。这将使Nginx更加安全,并启用一些有助于保证我们的服务器安全的高级功能。

我们为了使设置的参数可以在将来的Nginx配置中重用,因此我们将为该文件指定一个通用名称:

sudo nano /etc/nginx/snippets/ssl-params.conf

您应该花点时间阅读HTTP严格传输安全性或HSTS,特别是有关“预加载”功能的信息。预加载HSTS可提高安全性,但如果意外启用或启用错误,可能会产生深远的影响。在本教程中,我们不会预加载设置,但如果您确定了解其含义,则可以对其进行修改:

# from https://cipherli.st/
# and https://raymii.org/s/tutorials/Strong_SSL_Security_On_nginx.html

ssl_protocols TLSv1 TLSv1.1 TLSv1.2;
ssl_prefer_server_ciphers on;
ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH";
ssl_ecdh_curve secp384r1;
ssl_session_cache shared:SSL:10m;
ssl_session_tickets off;
ssl_stapling on;
ssl_stapling_verify on;
resolver 8.8.8.8 8.8.4.4 valid=300s;
resolver_timeout 5s;
# Disable preloading HSTS for now.  You can use the commented out header line that includes
# the "preload" directive if you understand the implications.
#add_header Strict-Transport-Security "max-age=63072000; includeSubdomains; preload";
add_header Strict-Transport-Security "max-age=63072000; includeSubdomains";
add_header X-Frame-Options DENY;
add_header X-Content-Type-Options nosniff;

ssl_dhparam /etc/ssl/certs/dhparam.pem;

由于我们使用的是自签名证书,因此不会使用SSL stapling  。Nginx只会输出警告,并继续正常运行。

完成后保存并关闭文件。

调整Nginx配置以使用SSL

现在我们已经有了我们的代码片段,我们可以调整我们的Nginx配置来启用SSL。

我们将在本教程中假设您正在使用/etc/nginx/sites-available目录中的defaultNginx配置文件文件。如果您使用的是其他Nginx配置文件文件,请在以下命令中替换其名称。

在我们继续之前,让我们备份当前的nginx配置文件:

sudo cp /etc/nginx/sites-available/default /etc/nginx/sites-available/default.bak

现在,打开nginx配置文件进行调整:

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

在里面,您的nginx配置文件开始可能像这样:

server {
    listen 80 default_server;
    listen [::]:80 default_server;

    # SSL configuration

    # listen 443 ssl default_server;
    # listen [::]:443 ssl default_server;

    . . .

我们修改此配置,以便将未加密的HTTP请求自动重定向到加密的HTTPS。这为我们的网站提供了最佳安全性。如果要同时允许HTTP和HTTPS流量,请使用后面的配置。

我们将把配置分成两个独立的块。在两个第一个listen指令之后,我们将添加一个server_name指令,设置为服务器的域名,或者是IP地址。然后,我们将设置重定向到我们将要创建的第二个Nginx配置文件。之后,我们将关闭这个短块:

注意:我们将使用302重定向,直到我们确认网站正常。我们可以将其更改为永久301重定向。

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    server_name server_domain_or_IP;
    return 302 https://$server_name$request_uri;
}

    # SSL configuration

    # listen 443 ssl default_server;
    # listen [::]:443 ssl default_server;

    . . .

接下来,要在下面直接启动一个新的Nginx配置文件以合并剩余的配置。我们可以取消注释listen 443端口的两个指令。之后,我们只需要合并我们设置的两个片段文件:

注意:您可能只有一个 listen指令,其中包含default_server每个IP版本和端口组合的修饰符。如果已经为default_server设置的这些端口启用了其他Nginx配置文件,则必须删除其中一个。

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    server_name server_domain_or_IP;
    return 302 https://$server_name$request_uri;
}

server {

    # SSL configuration

    listen 443 ssl default_server;
    listen [::]:443 ssl default_server;
    include snippets/self-signed.conf;
    include snippets/ssl-params.conf;

    . . .

完成后保存并关闭文件。

(备用配置)允许HTTP和HTTPS流量

如果您想要或需要同时允许加密和未加密内容,则必须以不同方式配置Nginx。通常不建议这样做,但在某些情况下也许是必要的。基本上,我们只是将两个单独的Nginx配置文件压缩为一个块并删除重定向:

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    listen 443 ssl default_server;
    listen [::]:443 ssl default_server;

    server_name server_domain_or_IP;
    include snippets/self-signed.conf;
    include snippets/ssl-params.conf;

    . . .

完成后保存并关闭文件。

第三步、调整防火墙

如果启用了防火墙,则需要调整设置以允许SSL流量。所需的过程取决于您使用的防火墙软件。如果您当前没有配置防火墙,请随时跳过。如果你使用的是腾讯与的服务器,可以直接使用腾讯云安全组进行设置

UFW

如果您使用的是ufw,则可以通过输入以下内容来查看当前设置:

sudo ufw status

它可能看起来像这样,这意味着只允许HTTP流量进入Web服务器:

Status: active

To                         Action      From
--                         ------      ----
SSH                        ALLOW       Anywhere
WWW                        ALLOW       Anywhere
SSH (v6)                   ALLOW       Anywhere (v6)
WWW (v6)                   ALLOW       Anywhere (v6)

为了进一步允许HTTPS流量,我们可以允许“WWW

Full”配置文件,然后删除的“WWW”配置文件限额:

sudo ufw allow 'WWW Full'
sudo ufw delete allow 'WWW'

您的状态现在应该如下所示:

sudo ufw status
Status: active

To                         Action      From
--                         ------      ----
SSH                        ALLOW       Anywhere
WWW Full                   ALLOW       Anywhere
SSH (v6)                   ALLOW       Anywhere (v6)
WWW Full (v6)              ALLOW       Anywhere (v6)

现在,您的服务器应接受HTTPS请求。

iptables的

如果您正在使用iptables,可以通过输入以下内容来查看当前规则:

sudo iptables -S

如果您启用了规则,则会显示它们。示例配置可能如下所示:

-P INPUT DROP
-P FORWARD ACCEPT
-P OUTPUT ACCEPT
-A INPUT -i lo -j ACCEPT
-A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
-A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 80 -j ACCEPT

打开SSL流量所需的命令取决于您当前的规则。对于像上面那样的基本规则集,您可以通过输入以下内容来添加SSL访问:

sudo iptables -I INPUT -p tcp -m tcp --dport 443 -j ACCEPT

如果我们再次查看防火墙规则,我们应该看到新规则:

sudo iptables -S
-P INPUT DROP
-P FORWARD ACCEPT
-P OUTPUT ACCEPT
-A INPUT -p tcp -m tcp --dport 443 -j ACCEPT
-A INPUT -i lo -j ACCEPT
-A INPUT -m conntrack --ctstate RELATED,ESTABLISHED -j ACCEPT
-A INPUT -p tcp -m tcp --dport 22 -j ACCEPT
-A INPUT -p tcp -m tcp --dport 80 -j ACCEPT

如果您使用程序iptables在引导时自动应用规则,则需要确保使用新规则更新配置。

第四步、启用Nginx中的更改

现在我们已经进行了更改并调整了防火墙,我们可以重新启动Nginx以实现我们的新更改。

首先,我们应该检查以确保我们的文件中没有语法错误。我们可以通过输入以下内容来执

sudo nginx -t

如果一切顺利,您将得到如下结果:

nginx: [warn] "ssl_stapling" ignored, issuer certificate not found
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

在开头注意警告。如前所述,由于我们的自签名证书无法使用SSL stapling,因此此特定设置会发出警告。我们的服务器仍然可以正确加密连接。

如果输出与上述内容匹配,则配置文件没有语法错误。我们可以安全地重启Nginx以实现我们的更改:

sudo systemctl restart nginx

我们的服务器现在可以通过HTTPS访问。

第五步、测试加密

现在,我们已准备好测试我们的SSL服务器。

打开Web浏览器,然后在地址栏域名或IP中输入https://

https://server_domain_or_IP

由于我们创建的证书未由您的某个浏览器的受信任证书颁发机构签名,因此您可能会看到一个警告,如下所示:

Nginx自签名证书警告

这是正常的。我们只对证书的加密方面感兴趣,而不是对主机真实性的第三方验证感兴趣。单击“高级”,然后继续进入您的主机:

Nginx自签名覆盖

如果您查看浏览器地址栏,您将看到部分安全性的一些指示。这可能是一个带有“x”的锁或带有感叹号的三角形。在这种情况下,这只意味着无法验证证书。但它仍在加密您的连接。

如果您使用两个Nginx配置文件配置Nginx,自动将HTTP内容重定向到HTTPS,您还可以检查重定向是否正常运行:

http://server_domain_or_IP

如果你还是看到了警告,则证明重定向成功!

第六步、更改为永久重定向

如果您的重定向工作正常并且您确定只想允许加密流量,则应修改Nginx配置以使永久重定向。

再次打开Nginx配置文件配置文件:

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

找到return 302并将其更改为return 301

server {
    listen 80 default_server;
    listen [::]:80 default_server;
    server_name server_domain_or_IP;
    return 301 https://$server_name$request_uri;
}

. . .

保存并关闭文件。

检查配置是否存在语法错误:

sudo nginx -t

准备好后,重新启动Nginx以使重定向永久化:

sudo systemctl restart nginx

您的站点现在应该在通过HTTP访问时永久重定向到HTTPS。

结论

您已将Nginx服务器配置为对客户端连接使用强加密。这样您就可以安全地处理请求,并阻止黑客抓包阅读您的流量。我还是强烈建议您使用CA签名的证书,因为这些证书浏览器信任,您可以在此处了解如何使用腾讯云免费SSL证书设置可信证书。


参考文献:《How To Install Matrix Synapse on Ubuntu 16.04》

原创声明,本文系作者授权云+社区发表,未经许可,不得转载。

如有侵权,请联系 yunjia_community@tencent.com 删除。

发表于

我来说两句

0 条评论
登录 后参与评论

相关文章

来自专栏bboysoul

esxi 更换ssl证书

就是想换一个证书而已,你可以通过下面的途径去申请一个泛解析域名的证书之后再esxi上安装上

1911
来自专栏编程

Nginx HTTP Server中的SSL证书错误

安装SSL证书时快速解决Nginx HTTP服务器错误! Nginx HTTP Server是免费的开放源代码,它附带了高性能的HTTP服务器和反向代理。Ngi...

2628
来自专栏云计算教程系列

如何在Debian 9中为Apache创建自签名SSL证书

TLS或传输层安全性及其前身SSL(代表安全套接字层)是用于将正常流量包装在受保护的加密包装中的Web协议。

1342
来自专栏晨星先生的自留地

从iis认证方式的学习到一个路由器漏洞的调试

1705
来自专栏云计算教程系列

使用腾讯云SSL证书保护你的Nginx服务器

腾讯云SSL是一个新的证书颁发机构(CA),它提供了一种获取和安装免费TLS /SSL证书的简便方法,从而在Web服务器上启用加密的HTTPS。您可以在腾讯云W...

4431
来自专栏云计算教程系列

如何在CentOS 6上安装DavMail

如果您的工作场所或学校使用Microsoft Exchange发送电子邮件,您可能希望从不支持Exchange协议的电子邮件客户端访问您的Exchange电子邮...

1634
来自专栏PHP在线

JWT实现token-based会话管理

上文《3种web会话管理的方式》介绍了3种会话管理的方式,其中token-based的方式有必要从实现层面了解一下。本文主要介绍这方面的内容。上文提到token...

922
来自专栏运维小白

Linux基础(day52)

12.17 Nginx负载均衡 Nginx负载均衡目录概要 vim /usr/local/nginx/conf/vhost/load.conf // 写入如下内...

2337
来自专栏python3

startssl免费https证书申请

HTTP与HTTPS有什么区别? HTTP协议传输的数据都是未加密的,也就是明文的,因此使用HTTP协议传输隐私信息非常不安全,为了保证这些隐私数据能加密传输,...

4353
来自专栏Jackson0714

WCF安全3-Transport与Message安全模式

2918

扫码关注云+社区