我正在尝试在 Ubuntu 16.04 上为 nginx 配置 HTTPS。我已经使用语句进行了设置listen 443 ssl
,并告诉它在哪里可以找到证书和私钥文件。之后,我使用 重新启动了服务器sudo service nginx restart
。
现在当我curl https://my_ip_address
,我收到以下消息:
curl: (35) gnutls_handshake() failed: Handshake failed
我已经检查了我所知道的两个日志文件/var/log/nginx/access.log
和/var/log/nginx/error.log
;但它没有显示任何来自请求的痕迹。
我的问题:SSL 握手失败时会记录任何内容吗?如果有,记录在哪里?一般来说,如何解决此类问题,即在 HTTP 请求发送到服务器或由服务器提取之前 SSL 协议中存在错误?
编辑:我通过从我的配置中删除以下几行来使其工作:
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;
更新:该ssl_ecdh_curve secp384r1;
行似乎是导致问题的原因。没有它,一切都正常,但有了它,SSL 握手就会失败。奇怪的是,错误消息是“没有共享密码”。我不确定它是做什么的,所以我把它删掉了。我还删除了 ssl_stapling 的内容,因为我不知道它是做什么用的,而且它自己也创建了错误消息
答案1
正如@Paul所说,解决方案是提高日志级别。我更改了文件中的一行nginx.conf
,因此现在内容如下:
error_log /var/log/nginx/error.log debug;
现在日志级别更高了,它会记录 SSL 握手错误:
2016/09/19 22:38:08 [info] 10114#10114: *2 SSL_do_handshake() failed (SSL: error:1408A0C1:SSL routines:ssl3_get_client_hello:no shared cipher) while SSL handshaking, client: 108.162.242.24, server: 0.0.0.0:443
答案2
实际上你已经使用了选项ssl_ecdh_曲线配置Diffie Hellman 密钥交换在 Nginx 中,但您没有提供参数文件。因此您必须使用选项ssl_dh参数并且必须使用 openssl 创建一个文件。
创建文件:
openssl dhparam -out /etc/ssl/certs/dhparam.pem 4096
在 Nginx 中使用文件和上面的 Diffie Hellman 配置:
ssl_dhparam /etc/ssl/certs/dhparam.pem;
ssl_ecdh_curve secp384r1;
答案3
您可以检查您的 nginx 服务器配置,有一行配置是:ssl_ciphers,默认值是:ssl_ciphers HIGH:!aNULL:!MD5;(http://nginx.org/en/docs/http/ngx_http_ssl_module.html#ssl_ciphers),但有时并非所料,就我而言,nginx-ingress-controller 默认值小于默认配置,并且 nginx 调试日志显示错误为:没有共享密码。当我在配置文件中添加一些密码并重新加载 nginx 时,该问题得到解决。您可以参考此配置模板:https://mozilla.github.io/server-side-tls/ssl-config-generator/