How To Create and use a Self-Signed SSL Certificate for Apache

Pinterest LinkedIn Tumblr

The Transport Layer Security(TLS) and its predecessor SSL(secure socket layer) are web protocols that are used to swap normal web traffic in a protected, encrypted wrapper.

Signing your own SSL certificates is usually done as an easy alternative to certificate authorities for internal communications or non-user facing sites that need still encryption. Here’s how to set one up with Apache.

Table of Content

  1. Install the required packages
  2. Generate and self sign an ssl certificate
  3. Configure Apache to use self signed certificates

1. Install required packages

Before proceeding, ensure your OS up to date. For Debian based systems like Ubuntu

sudo apt update
sudo apt upgrade -y 

We’ll use the openssl utility to generate the certificate and corresponding private key. Use this command to install if its not present:

For Ubuntu/Debian

sudo apt install openssl

2. Generate and Self Sign an SSL Certificate

generate the certificate with the following command:

sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/ssl/private/apache.key -out /etc/ssl/certs/apache.crt

openssl will ask you for some info about your organization. You can leave most of this blank, but the one important thing you’ll need to fill out is the “Common Name,” which you’ll want to set to your server’s IP address or domain name.

$ sudo openssl req -x509 -nodes -days 365 -newkey rsa:2048 -keyout /etc/ssl/private/apache.key -out /etc/ssl/certs/apache.crt
Generating a RSA private key
writing new private key to '/etc/ssl/private/apache.key'
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
Country Name (2 letter code) [AU]:KE
State or Province Name (full name) [Some-State]:Nairobi
Locality Name (eg, city) []:Nairobi
Organization Name (eg, company) [Internet Widgits Pty Ltd]:Citizix Ltd.
Organizational Unit Name (eg, section) []:Devops
Common Name (e.g. server FQDN or YOUR name) []:secure.citizix.com
Email Address []:[email protected]

openssl will take a second to run and generate a new private RSA key, which is used to sign the certificate and store it in /etc/ssl/private/apache.key. The certificate itself is stored in /etc/ssl/certs/apache.crt, and will be valid for a year.

Next let’s generate a Diffie-Hellman group. This is used for perfect forward secrecy, which generates ephemeral session keys to ensure that past communications cannot be decrypted if the session key is compromised. This isn’t entirely necessary for internal communications, but if you want to be as secure as possible you shouldn’t skip this step. Note, this does require you to have Apache version 2.4.8 or higher, so make sure you’re up to date.

sudo openssl dhparam -out /etc/ssl/certs/dhparam.pem 4096

3. Configure Apache to Use Your Self-Signed Certificate

First ensure that apache is installed.

For Debian:

sudo apt install -y apache2

First, we will create an Apache configuration snippet to define some SSL settings. This will set Apache up with a strong SSL cipher suite and enable some advanced features that will help keep our server secure. The parameters we will set can be used by any Virtual Hosts enabling SSL.

Create a new snippet in the /etc/apache2/conf-available directory. We will name the file ssl-params.conf to make its purpose clear:

sudo nano /etc/apache2/conf-available/ssl-params.conf

Open it up in your favorite text editor, and paste in the following configuration:

SSLProtocol All -SSLv2 -SSLv3 -TLSv1 -TLSv1.1
SSLHonorCipherOrder On
Header always set X-Frame-Options DENY
Header always set X-Content-Type-Options nosniff
SSLCompression off
SSLUseStapling on
SSLStaplingCache "shmcb:logs/stapling-cache(150000)"
SSLSessionTickets Off

SSLOpenSSLConfCmd DHParameters "/etc/ssl/certs/dhparam.pem"

The first block sets a few default SSL parameters, and the last line configures Apache to use the Diffie-Hellman group. You can omit this line if you skipped that step.

Next, open up the site SSL Virtual Host file at /etc/apache2/sites-available/default-ssl.conf.  Change the following lines to point to your certificate and key file:

SSLCertificateFile /etc/ssl/certs/apache.crt
SSLCertificateKeyFile /etc/ssl/private/apache.key

SSL should now be working, but you will likely will need to copy over some configuration from your current configuration file, because you just modified a blank one. You’ll have to make sure the ServerName , ServerAdmin , and DocumentRoot  directives are pointing to the correct locations.

Additionally, you’ll want to set up a redirect to forward HTTP traffic over to the encrypted HTTPS. Open up the default Apache config at /etc/apache2/apache2.conf , and add the following lines to rewrite HTTP traffic:

RewriteEngine On 
RewriteCond %{SERVER_PORT} 80 
RewriteRule ^(.*)$ https://www.yourdomain.com/$1 [R,L]

Self-signed certificates are most commonly used for private servers, so it’s not a bad idea to whitelist access to only your private LAN and use a VPN server to connect to it.

Once the ports are open you can test your SSL settings by navigating to your site in your browser. If everything worked correctly, you should see this warning:

Your connection is not private

This is normal, so don’t worry. You’ll have to manually select that you trust this certificate, which is the reason you can’t use self-signed certs for public facing sites.

I am a Devops Engineer, but I would describe myself as a Tech Enthusiast who is a fan of Open Source, Linux, Automations, Cloud and Virtualization. I love learning and exploring new things so I blog in my free time about Devops related stuff, Linux, Automations and Open Source software. I can also code in Python and Golang.

Write A Comment