Skip to main content
ertius.org

really default nginx vhost

One thing that mildly annoys me is that despite name-based virtual hosting being older than Zendaya, and SNI being old enough to drink, even in the US, I always seem to end up with a "default" vhost in nginx by accident - one of the configured sites will serve when the IP address or some broken hostname is passed in for Host: or in the ClientHello, and will do so with a TLS error.

So, I decided to solve that Once And For All.

There's two parts:

  1. create a self-signed (long duration) cert to serve by default (when no valid Server Name Indication is provided)
  2. configure a vhost to be the default, and have it return a 404 for everything

Generating a cert#

openssl req -x509 -nodes -days 3650 \
  -newkey rsa:2048 \
  -sha256 \
  -keyout /tmp/anonymous-default.key \
  -out /tmp/anonymous-default.crt \
  -subj "/C=TLD/ST=Someplace/L=Somewhere/O=Someorg/CN=whatever"

Config#

server {
    # be the default on ipv4
    listen 443 ssl http2 default_server;
    # be the default on ipv6
    listen [::]:443 ssl http2 default_server;

    # use our crappy self signed cert
    ssl_certificate     /etc/ssl/certs/default.crt;
    ssl_certificate_key /etc/ssl/private/default.key;
    ssl_protocols       TLSv1.2 TLSv1.3;

    # match all names
    server_name _;

    access_log /var/log/nginx/default-access.log;
    error_log /var/log/nginx/default-error.log warn;

    # return 404 for *every* request
    return 404;
}

# do the same for http - for real vhosts you'd want to either redirect or simply not
# serve HTTP at all, but we just want to absorb the request here
server {
    listen 80 default_server;
    listen [::]:80 default_server;

    server_name _;

    access_log /var/log/nginx/default-access.log;
    error_log /var/log/nginx/default-error.log warn;

    return 404;
}

voila, it's all unremarkable errors.