sunnyrjuneja
sunnyrjuneja

Reputation: 6123

nginx subdomain ssl redirect redirects top level domain

I setup a redirect for all HTTP traffic on my subdomain to go through HTTPS but I noticed that when I visit http://mydomain.com it is redirecting to https://subdomain.mydomain.com. No problem is encountered on https://mydomain.com.

Just to clarify,

http://mydomain.com should not redirect but it currectly redirects to https://subdomain.mydomain.com

http://subdomain.mydomain.com should redirect to https://subdomain.mydomain.com.

This is my nginx conf

server {
    listen *:80;
    server_name subdomain.mydomain.com;
    server_tokens off;
    root /nowhere; # this doesn't have to be a valid path since we are redirecting, you don't have to change it.
    rewrite ^ https://$server_name$request_uri permanent;
}

server {
    listen 443 ssl;
    server_name subdomain.mydomain.com;
    server_tokens off;
    .... other stuff ...
}

Upvotes: 1

Views: 2545

Answers (1)

foibs
foibs

Reputation: 3406

Quoting from http://nginx.org/en/docs/http/request_processing.html

nginx first decides which server should process the request. Let’s start with a simple configuration where all three virtual servers listen on port *:80:

server {
    listen      80;
    server_name example.org www.example.org;
    ...
}

server {
    listen      80;
    server_name example.net www.example.net;
    ...
}

server {
    listen      80;
    server_name example.com www.example.com;
    ...
}

In this configuration nginx tests only the request’s header field “Host” to determine which server the request should be routed to. If its value does not match any server name, or the request does not contain this header field at all, then nginx will route the request to the default server for this port. In the configuration above, the default server is the first one — which is nginx’s standard default behaviour.

That means that in your example, when you make a request to http://mydomain.com the only available server block to serve the request is the server_name subdomain.mydomain.com; block, so it redirects to https. The simplest solution is to create a new server block called which just returns a http status code and possibly a message. E.g.

server {
  listen 80;
  server_name mydomain.com;
  return 403 "nothing to see here";
}

You may also use default_server like this listen 80 default_server; to make sure that all 'unconfigured' hostnames will come in this block

Upvotes: 1

Related Questions