我有一个使用 http2 和 https 在本地运行的 node.js 项目。一切都运行良好,我生成了一个自签名证书,并且运行应用程序时一切都正常。所以现在我试图将它移动到我的服务器,即运行 nginx 的 centos,并使用proxypass
映射http://myserverip:port
到http://example.com
。HTTP 工作正常并且目前正在运行,但在我尝试转换为 https 时,我无法显示网站。请注意,转到可以正常https://myserverip:port
工作并提供所有内容,因此我相信这与我的 nginx 配置无关。
以下是我为这个站点配置的 nginx 配置:
server
{
listen 80;
listen [::]:80;
server_name example.com www.example.com;
location /
{
proxy_pass http://127.0.0.1:3103;
include /etc/nginx/proxy_params;
}
}
server {
listen 443 ssl http2;
listen [::]:443;
server_name example.com www.example.com;
ssl_certificate /var/www/example.com/app/certs/example.crt;
ssl_certificate_key /var/www/example.com/app/certs/example.key;
location / {
proxy_pass https://127.0.0.1:3103;
}
}
在我的 nginx 日志中,我收到以下错误:no "ssl_certificate" is defined in server listening on SSL port while SSL handshaking
。这似乎很奇怪,因为我设置了ssl_certificate
& ssl_certificate_key
。有一件事确实让我有点困惑,那就是我的节点服务器要求我在代码中加载证书,因此必须两次加载同一个证书似乎很奇怪?以下是我的服务器上的相关代码,您可以看到它正在做什么。
const spdyOptions = {
key: fs.readFileSync( path.resolve(__dirname, `../certs/${certName}.key`) ),
cert: fs.readFileSync( path.resolve(__dirname, `../certs/${certName}.crt`) )
}
// Export
module.exports = handle => {
const server = express()
server
// Frontend
.get('*', (req, res) => handle(req, res))
spdy
.createServer(spdyOptions, server)
.listen(cf.port, listen)
}
希望您能注意到我做错了什么...我对 nginx 还很陌生,所以我可能只是误解了一些简单的事情。如果您需要更多信息,请直接询问!谢谢!
答案1
在当前配置中,您正在尝试建立双重 TLS 连接:从客户端到 nginx,再从 nginx 到 Node 服务器。
在这里建立两个 TLS 连接是没有意义的。
一般来说,这里有两个选择:
- 实现nginx通过普通http协议连接Node服务器。
- 使用 nginx
stream
TCP 代理功能将 TLS 数据包按原样代理到 Node 服务器,然后终止 TLS 连接。
我不知道这个 Node.js 模块是否确实为 HTTP/2 提供了一些额外的优化。如果确实如此,那么使用选项 1 时不会发生这种优化。
选项 2 的缺点是您无法在 Node 应用程序上获取客户端 IP 地址。