Nginx: curl: (60) SSL certificate problem: unable to get local issuer certificate

Viewed 8004

I am runing nginx in docker over ssl, when I try to access using url I get below error

root@54a843786818:/# curl --location --request POST 'https://10.1.1.100/login' \
> --header 'Content-Type: application/json' \
> --data-raw '{
>     "username": "testuser",
>     "password": "testpassword"
> }'
curl: (60) SSL certificate problem: unable to get local issuer certificate
More details here: https://curl.haxx.se/docs/sslcerts.html

curl failed to verify the legitimacy of the server and therefore could not
establish a secure connection to it. To learn more about this situation and
how to fix it, please visit the web page mentioned above.

With No check certificate option it is working

curl -k --location --request POST 'https://10.1.1.100/login' --header 'Content-Type: application/json' --data-raw '{
    "username": "testuser",
    "password": "testpassword"
}'
{"access_token": "xxxxxxxxxxxxxxxxxxxxxxxkkkkkkkkkkkkkkkkkkkk", "refresh_token": "qqqqqqqqqoooooooooxxxx"}

My Config file

root@54a843786818:/# cat /etc/nginx/sites-enabled/api.conf
server {
    listen 443 ssl;
    listen [::]:443 ssl;
    ssl_certificate /root/certs/my_hostname.my.domain.name.com.pem;
    ssl_certificate_key /root/certs/my_hostname.my.domain.name.com.key;

    location / {
                proxy_set_header X-Real-IP $remote_addr;
                proxy_set_header HOST $http_host;
                proxy_pass http://10.1.1.100:5000;
                proxy_redirect off;
    }
}

I am suspecting something wrong with my certificates setup.

Below are steps exactly I followed it.

1) Taken private key and removed password using below commands

   # openssl rsa -in my_hostname.my.domain.name.com_password_ask.key -out my_hostname.my.domain.name.com.key

2) Converted .crt file .pem 
   # openssl x509 -in my_hostname.my.domain.name.com.crt -out my_hostname.my.domain.name.com.pem -outform PEM

3) Next copied .pem and .key and pasted under /root/certs on nginx docker container using cat and vim editor

4) Verified private keys  and public keys are matching below are the commands used 
  

root@54a843786818:~/certs# openssl rsa -noout -modulus -in my_hostname.my.domain.name.com.key | openssl md5
(stdin)= xcccxxxxxxxxxxxxxxxxxxxxxxxxxx
root@54a843786818:~/certs# openssl x509 -noout -modulus -in my_hostname.my.domain.name.com.pem | openssl md5
(stdin)= xcccxxxxxxxxxxxxxxxxxxxxxxxxxx

I got below certs separately, not sure I need bundle them, if yes what is the command

1) Certificate.pem
2) private_key
3) ca_intermediate_certificate.pem
4) ca_trusted_root

Can someone help me to fix the issue, I am not sure what I am doing wrong, Is there way I can validate my certificates and check those are able to serve https

or other than certificate, is there any issues like config, setup,

1 Answers

An SSL/TLS server, including HTTPS, needs to send the certificate chain, optionally excluding the root cert. Assuming your filenames are not actively perverse, you have a chain of 3 certs (server, intermediate, and root) and the server must send at least the entity cert and the 'ca_intermediate' cert; it may or may not include the 'trusted_root'. In nginx this is done by concatenating the certs into one file; see the overview documentation which links to the specific directive ssl_certificate.

Also, the root cert for your server's cert must be in the truststore of the client (every client if more than one). If that root cert is one of the established public CAs (like Digicert, GoDaddy, LetsEncrypt/ISRG) it will normally be already in the default truststores of most clients, usually including curl -- although curl's default can vary depending on how it was built; run curl -V (upper-vee) to see which SSL/TLS implementation it uses. If the root cert is a CA run by your company, the company's sysadmins will usually add it to the truststores on company systems, but if you are using a system that they don't know about or wasn't properly acquired and managed it may not have been set up correctly. If you need curl to accept a root cert that isn't in its default truststore, see the --cacert option on the man page, either on your system if Unixy or on the web. Other clients are different, but you didn't mention any.

Finally, as discussed in comments, the hostname you use in the URL must match the identity(ies) specified in the cert, and certificates are normally issued using only the domain name(s) of the server(s), not the IP address(es). (It is technically possible to have a cert for an IP address, or several, but by cabforum policy public CAs, if they issue certs for addresses at all, must not do so for private addresses such as yours -- 10.0.0.0/8 is one of the private ranges in RFC 1918. A company-run CA might certify such private addresses or it might not.) If your cert specifies domain name(s), you must use that name or one of those names as the host part of your URL; if you don't have your DNS or hosts file set up to resolve that domain name correctly to the host address, you can use curl option --resolve (also on the man page) to override.

Related