On CentOS, I have been using the default webRoot (/usr/share/nginx/html) until now to run my simple scripts and small applications. The other day, I had to configure nginx server blocks to run multiple applications through /var/www/html . After reading some tutorials I found there were two ways to do it, use the virtual.conf or make sites-available and sites-enabled folders and put the new conf in them.

  1. After deploying the application and editing the host file as dev.mysite.com www.dev.mysite.com (my local IP)

    the application works when I access localhost but my oldwebroot opens when I access dev.mysite.com. How do I fix this?

  2. I still dont get the idea of running multiple sites on one server, if I create my file hierarchy as /var/www/mysite1/html and /var/www/mysite2/html and create two confs for them in sites-available then how do we access them on the machine? What would be the edit made in hosts as they both use the localIP?

Please help me get over my confusions and clear the issue, I am linked my nginx.conf and mysite server block configuration.

server block - http://codepad.org/nMEvcycy nginx.conf - http://codepad.org/WLl4bd1x

  • What exactly do you call your oldwebroot ? Commented Oct 13, 2014 at 9:05
  • the location, /usr/share/nginx/html
    – user1502
    Commented Oct 13, 2014 at 9:19
  • That's because for some reason you are not sending the correct Host header. Commented Oct 13, 2014 at 9:22
  • Are you suggesting I change "listen localhost:80;" to "listen dev.mysite.com" ?
    – user1502
    Commented Oct 13, 2014 at 9:32
  • No, Im' telling you that your browser is not sending the correct Host header to nginx so it doesn't match the server_name directive and get served by the default nginx vhost with the default nginx root path. Commented Oct 13, 2014 at 9:36

1 Answer 1


1) I think the issue is with the listening directive as it's set on localhost while your domains resolve to in the resolv.conf file.


listen localhost:80;


listen 80;

Or just add another listen directive with your IP if you have additionnal network interfaces you don't want to listen on :

listen localhost:80;

2) When you go to a website your browser first resolve the IP behind the domain name with DNS resolution (in your particular case it's overriden locally in the hosts file so no external DNS is used). A webserver will listen on the IP behind that and dispatch requests between virtual hosts based on the Host header received. This means you can host multiple domains on the same IP address.

For instance you want to visit mysite1.com and mysite2.com. In the DNS mysite1.com and mysite2.com have IP X.X.X.X. What's gonna happen if you visit mysite1.com is : your browser will open multiple TCP connections (usually 4, in order to send requests in parallel and get linked content faster) to X.X.X.X port 80.

Then it will send

GET / HTTP/1.1
Host: mysite1.com
[ ... ]

Now you visit mysite2.com, same thing, it opens TCP connections to X.X.X.X port 80 but this time sends :

GET / HTTP/1.1
Host: mysite2.com
[ ... ]

And you will have the adequate content for each site.

For nginx to match the Host header, you have to set server_name directive in server blocks. So you can split your configuration with different server blocks using different server_name values and serve multiple sites behind one IP or put at disposal the same content for multiple domains by using multiple values in the server_name directive (however, never do that : it's called duplicate content and bots will blast you, use redirects, always). That was for HTTP.

Now, for HTTPS it's more complicated as the SSL handshake takes place before the HTTP traffic get exchanged. This handshake is a mean to secure the connection and exchange cryptographic information. But if you do that on the same IP and have multiple server blocks with different server_name values and thus different certificates, how can nginx know which certificate (and thus, server block) he must choose at this early stage of the SSL tunnel establishment ? No Host header have been seen yet !

To get over this problem, there's a SSL extension called Server Name Indication that allows the client to send the target Host at the handshake stage so the web server can choose the right vhost. Also other workarounds exist like the x509 SubjectAltName extension (certificate side) or simply one domain = one IP.

  • You previously had listen 80, now you changed it?
    – user1502
    Commented Oct 13, 2014 at 11:13
  • @user1502 I explained all cases in my answer, read it. Commented Oct 13, 2014 at 11:14
  • Ok, it works with listen 80. But my second questions was, for my site1, I made the following entry to the /etc/hosts, localhost dev.mysite1.com www.dev.mysite1.com. Now what if I want mysite2, what would be the entry for it?
    – user1502
    Commented Oct 13, 2014 at 11:15
  • Append the domains to this line ... Commented Oct 13, 2014 at 11:22
  • Oh ok, thanks! Now just to get the hang of it, what if I want to run an application from the old webroot? (/usr/share/nginx/html) where will those changes be made?
    – user1502
    Commented Oct 13, 2014 at 11:24

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .