Nginx SSL Error – TLSv1 Alert Unknown CA

nginxsslssl-certificate

I'm currently trying to set up nginx as a proxy for a website which requires certificate authentication.
The following curl command works perfectly:

curl --cacert ca-cert.pem -v --key client.key --cert client.pem https://example.com:443

However, the following nginx configuration seems to be rejected by the server:

server {
        listen      80;

        location / {
            proxy_pass                      https://example.com;
            proxy_set_header                Host example.com;
            proxy_ssl_certificate           /etc/nginx/client.pem;
            proxy_ssl_certificate_key       /etc/nginx/client.key;
            proxy_ssl_trusted_certificate   /etc/nginx/ca-cert.pem;
            proxy_ssl_verify                off;
        }
    }

The full error from the nginx logs is:

2021/03/08 20:43:06 [error] 29#29: *1 SSL_do_handshake() failed (SSL: error:14094418:SSL routines:ssl3_read_bytes:tlsv1 alert unknown ca:SSL alert number 48) while SSL handshaking to upstream, client: 172.17.0.1, server: , request: "GET / HTTP/1.1", upstream: "https://x.x.x.x:443/", host: "localhost:80"

Does anyone know what's going on? Isn't the nginx config equivalent to the curl command?

Best Answer

...ssl3_read_bytes:tlsv1 alert unknown ca

The upstream server can not validate the send client certificate since it is missing intermediate certificates. Therefore it sends back to nginx the cause of the problem as an alert. The fix is probably to add the necessary intermediate certificates to client.pem in the right order (i.e. leaf certificate first, then what signed leaf certificate etc).

But why did it work with curl then: Depending on which TLS stack is used with curl and maybe depending on the version of curl it will automatically combine the certificate given with --cert with matching intermediate certificates given in --cacert and send the full chain to the server as part of the client certificate. If this is done then the server can successfully validate the client certificate.