When you type example.com
into the address bar of a browser WITHOUT entering the scheme, i.e. http://
or https://
, Nginx redirects the user to https://api.example.com
instead of https://example.com
as intended. I'm pretty sure there's something wrong with my Nginx config, but I'm not sure what.
I'm hosting two websites on the same server, with the same IP. The relevant bits from the DNS zone file looks something like (domain and IP anonymized here):
example.com. 1800 IN A xxx.xxx.xxx.xxx
www.example.com. 1800 IN CNAME example.com.
api.example.com. 1800 IN CNAME example.com.
I have two SSL certs installed (provided by letsencrypt), one for each site, and both sites are configured to redirect to HTTPS. I have two vhost config files, one for each site, as follows:
/etc/nginx/sites-available/api
/etc/nginx/sites-available/default
Both are symlinked into /etc/nginx/sites-enabled/
. The relevant bits from the two config files are as follows:
# /etc/nginx/sites-available/api
server {
listen 80;
listen [::]:80 ipv6only=on;
server_name api.example.com;
return 301 https://api.example.com$request_uri;
}
server {
listen 443 ssl http2;
listen [::]:443 ssl http2;
include snippets/api-ssl-params.conf; # ssl config info
server_name api.example.com;
# ... the rest of the site config ...
}
and:
# /etc/nginx/sites-available/default
server {
listen 80;
listen [::]:80;
server_name www.example.com;
return 301 https://example.com$request_uri;
}
server {
listen 443 ssl http2 default_server;
listen [::]:443 default_server ipv6only=on;
include snippets/ssl-params.conf; # ssl config info
server_name example.com;
# ... the rest of the site config ...
}
I don't understand why just entering example.com
into the address bar would redirect to https://api.example.com
because:
example.com
doesn't appear in the api
config file anywhereexample.com
shouldn't match the server_name
directive api.example.com
default
are marked as default_server
so shouldn't that take precedence when an ambiguous domain name was typed in?Thanks!!!
Duh. Figured it out in the process of writing the question. The problem is that just plain example.com
doesn't appear in the server_name
directive for either of the sites listening on port 80. Since that causes ambiguity, nginx picks the first site in alphabetic order.
I updated the config file for the default
site as follows:
# /etc/nginx/sites-available/default
server {
listen 80;
listen [::]:80;
server_name example.com www.example.com; # <-- CHANGED THIS LINE
return 301 https://example.com$request_uri;
}
server {
listen 443 ssl http2 default_server;
listen [::]:443 default_server ipv6only=on;
include snippets/ssl-params.conf; # ssl config info
server_name example.com;
# ... the rest of the site config ...
}
And all was right with the universe.