Cyber Deals - Get up to 65% off on CKA, CKAD, CKS, KCNA, KCSA exams and courses!

SSL Certificate Management - Quick Reference

1. Create a Root CA

$ mkdir RootCA && cd RootCA

# Create RootCA Key
$ openssl genrsa -out rootCA.key 4096

Remove the -des3 option for non-password protected key. The -des3 option specifies how the private key is encrypted with a password. Without a cipher option, the private key is not encrypted and no password is required.

Note: Optionally you can create the RootCA.csr and sign it.

$ openssl req -new -key ca.key -subj "/CN=MYROOT-CA" -out rootCA.csr
$ openssl x509 -req -in rootCA.csr -signkey rootCA.key -out rootCA.crt
# Create self-sign CA Certificate with 10 years validity
$ openssl req -x509 -new -nodes -key rootCA.key -sha512 -days 3650 -out rootCA.pem

2. Trusting new RootCA in system

Fedora / RHEL

$ sudo cp ../RootCA/rootCA.pem /etc/pki/ca-trust/source/anchors/iamgini-rootCA.pem

# make sure the certificate is made available through the /etc/pki/ca-trust/extracted
$ sudo update-ca-trust

# Verify Root CA - List trust or certificates
$ trust list

Ubuntu / Debian

$ sudo cp rootCA.pem /usr/local/share/ca-certificates/iamgini-rootCA.crt
$ sudo update-ca-certificates

3. Create Key, CSR and Certificate

Optional - create a folder to avoid overwrite.

$ cd .. && mkdir SSL_CERTS && cd SSL_CERTS

3.1. Create a new SSL Key for server/application

$ openssl genrsa -out myserver.key 4096

3.2. Generate Certificate Signing Request (CSR)

$ openssl req -new \
  -key myserver.key \
  -out myserver.csr \
  -subj "/C=SG/ST=Singapore/L=CBD/O=iamgini/OU=IT/CN=aap25.lab.iamgini.com/[email protected]"

Note: Adding -nodes (means no DES) tells OpenSSL not to encrypt the private key.

You can also create a new key and CSR together:

$ openssl req -newkey rsa:4096 \
  -keyout myserver.key \
  -out myserver.csr \
  -nodes \
  -subj "/C=SG/ST=Singapore/L=CBD/O=iamgini/OU=IT/CN=aap25.lab.iamgini.com/[email protected]"

For interactive CSR entry:

$ openssl req -newkey rsa:4096 \
  -keyout myserver.key \
  -out myserver.csr \
  -nodes

3.3. Generate myserver.crt Certificate using CSR and CA

$ openssl x509 -req \
  -CA ../RootCA/rootCA.pem \
  -CAkey ../RootCA/rootCA.key \
  -CAcreateserial \
  -in myserver.csr \
  -out myserver.crt \
  -days 1825 -sha512

Verify certificate content

$ openssl x509 -in myserver.crt -text -noout

Verify key and certificate matching using md5:

$ openssl rsa -noout -modulus -in myserver.key | openssl md5
MD5(stdin)= 22c83dc812316f248c20ba345410fb77

$ openssl x509 -noout -modulus -in myserver.crt | openssl md5
MD5(stdin)= 22c83dc812316f248c20ba345410fb77

Or match using fingerprint:

$ openssl rsa -in myserver.key -pubout -outform PEM | openssl sha256
SHA2-256(stdin)= df3581f4be1929b53745c5cda83e49914382c9f48fff39d83936ea76d8ccfc56

$ openssl x509 -in myserver.crt -pubkey -noout | openssl sha256
SHA2-256(stdin)= df3581f4be1929b53745c5cda83e49914382c9f48fff39d83936ea76d8ccfc56

Check a PKCS#12 file (.pfx or .p12):

$ openssl pkcs12 -info -in keyStore.p12

Check and verify Key file:

$ openssl rsa -in server.key -check

Verify CSR content:

$ openssl req -in server.csr -noout -text
$ openssl req -in server.csr -noout -text -verify

Generate Certificate using CSR, CA, and extension file:

$ openssl x509 -req \
  -passin file:passphrase.txt \
  -CA myserver-CA.pem -CAkey myserver-CA.key -CAcreateserial \
  -in myserver.csr \
  -out myserver.crt \
  -days 1825 -sha256 -extfile myserver.ext

$ openssl x509 -in myserver.crt -text -noout

4. How to verify SSL Certificates

4.1. Verify Certificate and Key

You should get the same md5 output for all three commands.

# certificate
$ openssl x509 -noout -modulus -in <file>.crt | openssl md5

# key
$ openssl rsa -noout -modulus -in <file>.key | openssl md5

# csr
$ openssl req -noout -modulus -in <file>.csr | openssl md5

Check the key only:

$ openssl rsa -check -noout -in myserver.key
RSA Key is ok

4.2. Change or remove passphrase

Remove passphrase from SSL key:

$ openssl rsa -in original.key -out new.key

Change the passphrase of the SSL key:

$ openssl rsa -aes256 -in original.key -out new.key

4.3. Extract from PFX file

$ openssl pkcs12 -in [yourfile.pfx] -nocerts -out [drlive.key]

4.4. Extract Certificate from P7B file

$ openssl pkcs7 -inform PEM -outform PEM -in certnew.p7b -print_certs > certificate.cer

5. Kubernetes CA Certificates

Kubernetes uses its own internal CA to sign certificates for cluster components (API server, kubelet, etcd, etc.).

5.1. Create Kubernetes CA

# Step 1: Generate CA key
$ openssl genrsa -out ca.key 2048

# Step 2: Create Certificate Signing Request
$ openssl req -new -key ca.key -subj "/CN=KUBERNETES-CA" -out ca.csr

# Step 3: Self-sign the CA certificate
$ openssl x509 -req -in ca.csr -signkey ca.key -out ca.crt

5.2. Sign Component Certificates with Kubernetes CA

Use the CA to sign certificates for cluster components (e.g. kube-apiserver, etcd, service accounts):

# Generate component key
$ openssl genrsa -out apiserver.key 2048

# Create CSR with correct CN and O (used for RBAC)
$ openssl req -new -key apiserver.key \
  -subj "/CN=kube-apiserver/O=system:masters" \
  -out apiserver.csr

# Sign with the CA
$ openssl x509 -req \
  -in apiserver.csr \
  -CA ca.crt -CAkey ca.key -CAcreateserial \
  -out apiserver.crt \
  -days 365

Note: Kubernetes uses the CN field as the username and O field as the group for RBAC purposes.

5.3. OpenShift / kubeadm kubeconfig Certs

When building a kubeconfig manually (e.g. for UPI installs), the client cert must be signed by the cluster CA. The CN in the cert becomes the Kubernetes username.

# Admin kubeconfig cert
$ openssl genrsa -out admin.key 2048
$ openssl req -new -key admin.key \
  -subj "/CN=kubernetes-admin/O=system:masters" \
  -out admin.csr
$ openssl x509 -req -in admin.csr \
  -CA ca.crt -CAkey ca.key -CAcreateserial \
  -out admin.crt -days 365

5.4. Verify Kubernetes Cluster Certificates

# Check API server cert on a running cluster
$ openssl s_client -connect <api-server>:6443 </dev/null 2>/dev/null | \
  openssl x509 -noout -text

# Check cert expiry
$ openssl x509 -in /etc/kubernetes/pki/apiserver.crt -noout -enddate

# Check all kubeadm-managed certs
$ kubeadm certs check-expiration

6. SAN (Subject Alternative Name) Certificates

SANs are required for multi-hostname or IP-based certificates. Most modern tools reject certs without SANs.

Create myserver.ext or myserver_csr.conf:

[req]
default_md = sha512
prompt = no
req_extensions = req_ext
distinguished_name = req_distinguished_name

[req_distinguished_name]
commonName = myserver.lab.iamgini.com
countryName = SG
stateOrProvinceName = Singapore
organizationName = iamgini

[req_ext]
subjectAltName = @alt_names

[alt_names]
DNS.0 = myserver.lab.iamgini.com
DNS.1 = myserver
IP.0 = 192.168.7.10

Generate key, CSR, and sign with CA:

$ openssl genrsa -out myserver.key 4096

$ openssl req -new -nodes \
  -key myserver.key \
  -config myserver_csr.conf \
  -out myserver.csr

$ openssl x509 -req \
  -in myserver.csr \
  -CA ../RootCA/rootCA.pem \
  -CAkey ../RootCA/rootCA.key \
  -CAcreateserial \
  -extensions req_ext \
  -extfile myserver_csr.conf \
  -out myserver.crt \
  -days 3650 -sha512

6.2. PostgreSQL / Database Example

$ openssl genrsa -out pgsql.key 4096

$ cat > pgsql_csr.conf << 'EOF'
[req]
default_md = sha512
prompt = no
req_extensions = req_ext
distinguished_name = req_distinguished_name

[req_distinguished_name]
commonName = database.ansible.com
countryName = US

[req_ext]
subjectAltName = @alt_names

[alt_names]
DNS.0 = database.ansible.com
IP.0 = 192.168.7.19
EOF

$ openssl req -new -nodes -key pgsql.key -config pgsql_csr.conf -out pgsql.csr

$ openssl x509 -req \
  -in pgsql.csr \
  -CA ~/RootCA/rootCA.pem \
  -CAkey ~/RootCA/rootCA.key \
  -CAcreateserial \
  -extensions req_ext \
  -extfile pgsql_csr.conf \
  -out pgsql.crt \
  -days 3650

Trust the CA on the controller node (RHEL/Fedora):

$ cp rootCA.pem /etc/pki/ca-trust/source/anchors/
$ restorecon -Rv /etc/pki/ca-trust/source/anchors/
$ update-ca-trust

7. References