Apache HTTP Server course

Configure HTTPS with SSL/TLS in Apache

Learn how to enable mod_ssl, activate Apache HTTPS virtual hosts, use certificates and private keys, and test HTTPS on Debian and Ubuntu.

HTTPS is HTTP transported over TLS, the modern protocol family commonly still called SSL. TLS encrypts data traveling between a browser and Apache, helping protect passwords, cookies, pages, and other content from interception or modification.

Encryption alone is not enough. A certificate identifies the server to the browser. The browser validates that the certificate is trusted, current, and issued for the hostname being requested. Without successful validation, a connection may be encrypted but still vulnerable to impersonation.

How Apache Provides HTTPS

Apache uses mod_ssl to provide SSL/TLS support. The module adds directives such as SSLEngine, SSLCertificateFile, and SSLCertificateKeyFile.

On Debian and Ubuntu, enable the module with the Apache helper command:

sudo a2enmod ssl

Apache must be reloaded or restarted after enabling modules or changing site configuration. A restart is used in the basic examples below:

sudo service apache2 restart

# Modern equivalent:
sudo systemctl restart apache2

Apache SSL Site Configuration

A VirtualHost is an Apache configuration block for a particular host and port combination. Debian and Ubuntu package a default SSL virtual host in /etc/apache2/sites-available/default-ssl.conf. The file is a source configuration; enabling the site creates the corresponding link under /etc/apache2/sites-enabled/, where Apache loads enabled site configurations.

The conventional HTTPS listener is TCP port 443. A normal HTTP virtual host commonly listens on port 80 and needs no certificate directives. An HTTPS virtual host listens on port 443, requires mod_ssl, and specifies a certificate and private key.

SettingHTTP siteHTTPS site
Listener port80443
Required Apache moduleCore HTTP supportmod_ssl
Certificate directivesNot normally requiredSSLCertificateFile and SSLCertificateKeyFile
Typical URL schemehttp://https://
Browser trust behaviorNo TLS certificate validationCertificate and hostname are validated

Certificates and Private Keys

A server certificate is the public identity document presented to clients. It contains the server's hostname and a public key, and is normally signed by a trusted Certificate Authority (CA). The private key is the secret key paired with the certificate. Apache uses it to prove that it controls the certificate identity during the TLS handshake.

Debian and Ubuntu commonly provide a self-signed test certificate and key:

ItemTypical pathPurpose
Default SSL site configuration/etc/apache2/sites-available/default-ssl.confPackaged HTTPS virtual-host settings
Default self-signed certificate/etc/ssl/certs/ssl-cert-snakeoil.pemTest certificate supplied by the operating system package
Default private key/etc/ssl/private/ssl-cert-snakeoil.keyPrivate key paired with the test certificate
Default document root/var/www/htmlDirectory containing the default web page
Site access log/var/log/apache2/access.logRecords incoming requests
Site error log/var/log/apache2/error.logRecords errors, warnings, and diagnostics

The default self-signed certificate is useful for testing, but browsers normally display an untrusted-certificate warning because it was not issued by a CA trusted by the browser. A public production website should use a certificate issued for its hostname by a trusted CA. Keep the private key confidential, restrict its file permissions, and do not place it in a publicly served document root.

Enable the Packaged HTTPS Site

The following procedure enables the default SSL virtual host for a fresh Debian or Ubuntu Apache installation:

  1. Enable SSL support.
  2. Enable the packaged default SSL site.
  3. Check the configuration syntax.
  4. Restart Apache.
  5. Open the HTTPS address in a browser.
sudo a2enmod ssl
sudo a2ensite default-ssl
sudo apache2ctl configtest
sudo service apache2 restart

a2ensite enables a site by linking its configuration from /etc/apache2/sites-available/ into /etc/apache2/sites-enabled/. The configtest command should report Syntax OK before the service is restarted.

Test HTTPS Access

Visit the server with an HTTPS URL, using a hostname or address appropriate to the certificate:

https://server-hostname/
https://server-address/

When the packaged self-signed certificate is active, the browser should show a certificate trust warning. In a controlled test environment, inspect the certificate details and continue only if you understand the risk. For production, replace the test certificate rather than training users to ignore warnings.

If the default site is enabled, Apache should serve the default document root, normally /var/www/html, through HTTPS. A command-line check can confirm that Apache responds on the TLS endpoint:

curl -I https://server-hostname/

A certificate warning may cause command-line clients to reject a self-signed certificate. That rejection is expected and is a useful indication that certificate validation is working.

Create a Site-Specific SSL Virtual Host

For a real website, create a separate SSL virtual-host file instead of relying on the packaged default SSL site. The certificate names must match the hostname clients request, such as www.example.com. A certificate for another name can cause a browser hostname-mismatch warning even when Apache is correctly configured.

For example, create /etc/apache2/sites-available/example-ssl.conf with this structure:

<VirtualHost *:443>
    ServerName www.example.com
    DocumentRoot /var/www/example

    SSLEngine on
    SSLCertificateFile /etc/ssl/certs/www.example.com.pem
    SSLCertificateKeyFile /etc/ssl/private/www.example.com.key

    ErrorLog ${APACHE_LOG_DIR}/example-ssl-error.log
    CustomLog ${APACHE_LOG_DIR}/example-ssl-access.log combined
</VirtualHost>

ServerName identifies the requested host, and DocumentRoot identifies the directory Apache serves. SSLEngine on activates TLS for the virtual host. The certificate and key directives point to the matching files. The separate ErrorLog and CustomLog paths make this site's diagnostics and requests easier to distinguish from other sites.

Enable and validate the site, then reload or restart Apache:

sudo a2ensite example-ssl
sudo apache2ctl configtest
sudo systemctl reload apache2

If the default SSL site is no longer needed, disable it so it does not unexpectedly handle requests:

sudo a2dissite default-ssl
sudo apache2ctl configtest
sudo systemctl reload apache2

Use restart instead of reload when required by your operational process. A reload applies valid configuration changes while generally preserving existing connections; a restart stops and starts the service.

Replace the Default Test Certificate

Inspect the enabled SSL virtual-host configuration and identify these directives:

SSLCertificateFile /etc/ssl/certs/ssl-cert-snakeoil.pem
SSLCertificateKeyFile /etc/ssl/private/ssl-cert-snakeoil.key

Replace the test paths with the certificate and matching private key issued for the intended hostname:

SSLCertificateFile /etc/ssl/certs/www.example.com.pem
SSLCertificateKeyFile /etc/ssl/private/www.example.com.key

Protect the key with restrictive ownership and permissions appropriate for the Apache installation, verify that the certificate and key are a matching pair, test the configuration, and reload or restart Apache. Then access the exact hostname covered by the certificate and retest with a browser or TLS client.

Troubleshooting HTTPS

Certificate is not trusted

  • Apache may still be serving the default self-signed test certificate.
  • The certificate may be issued for a different hostname.
  • The certificate may be expired, or its trust chain may be incomplete.
  • Use a valid certificate for the requested hostname and verify the configured certificate path.

Nothing listens on port 443

  • Confirm that mod_ssl is enabled with sudo a2enmod ssl.
  • Confirm that the intended SSL site is enabled with sudo a2ensite site-name.
  • Run sudo apache2ctl configtest, then reload or restart Apache.
  • Check local and network firewalls for TCP port 443.

Apache fails to restart

  • Run sudo apache2ctl configtest and correct the reported syntax error.
  • Check that certificate and key paths exist and are readable by Apache.
  • Review the Apache error log for the precise failure.
  • Ensure the certificate and private key match.

The wrong website appears over HTTPS

  • Set the correct ServerName in the intended HTTPS virtual host.
  • Make sure the desired site is enabled.
  • Disable or adjust an unused default SSL site when it is intercepting requests.
  • Test with the hostname that matches the virtual host and certificate.

Key Points

  • HTTPS protects HTTP traffic between the browser and Apache using TLS.
  • mod_ssl enables Apache SSL/TLS directives and HTTPS virtual hosts.
  • HTTPS normally uses port 443.
  • A certificate identifies the server; its private key must remain secret.
  • The packaged self-signed certificate is for testing and causes browser warnings.
  • Production sites need a trusted certificate issued for the requested hostname.
  • Validate configuration with apache2ctl configtest before reloading or restarting Apache.

For related Apache administration, see Create New Virtual Host, Sites Available Directory, Sites Enabled Directory, Access and Error Logs, and Apache ports.conf.