Understanding the default Nginx virtual host (or server) configuration

After you had installed Nginx, one of the first thing to do is to check whether it is running ok.

One way to do so is to use your browser to send a HTTP request to test it.

If you had installed Nginx on your local machine, then you may enter http://localhost or http://127.0.0.1 into the location bar of your browser.

When you had setup Nginx on a separate machine on your home network, you may also enter http://<ip_address_of_the_machine> in the location bar of your browser. For example, in how to host a WordPress website on a Raspberry Pi with Raspbian Buster Lite and Nginx, I had entered http://192.168.1.114 as the location to test out the Nginx server running on my Raspberry Pi.

So be it http://localhost, http://127.0.0.1, http://<ip_address_of_the_machine>, you will always see this page on your browser screen:

default welcome page of Nginx 1.14.2

In case you are wondering why your Nginx behaves this way, this post will explain what the default Nginx Virtual Host configuration does to Nginx.

Where is your Nginx configuration file located at?

In order to know what the default Nginx Virtual Host configurations does, we need to find the file that contain them. Since Nginx process configurations from a file named as nginx.conf, we can use the find command to find it.

Given that, run the following command in your terminal to find nginx.conf:

sudo find / -name nginx.conf

Typically, you can find the file in either /usr/local/nginx/conf, /etc/nginx, or /usr/local/etc/nginx.

Looking for the default configuration file that came with your Nginx installation

Once you know where nginx.conf is, you can open up the configuration file to check its content. For example, on a Debian based operating system, I will run the following command to check the main configuration file:

 
cat /etc/nginx/nginx.conf

When this command was ran on my Raspbian Buster Lite, I got the following content:

user www-data;
worker_processes auto;
pid /run/nginx.pid;
include /etc/nginx/modules-enabled/*.conf;

events {
	worker_connections 768;
	# multi_accept on;
}

http {

	##
	# Basic Settings
	##

	sendfile on;
	tcp_nopush on;
	tcp_nodelay on;
	keepalive_timeout 65;
	types_hash_max_size 2048;
	# server_tokens off;

	# server_names_hash_bucket_size 32;
	# server_name_in_redirect off;

	include /etc/nginx/mime.types;
	default_type application/octet-stream;

	##
	# SSL Settings
	##

	ssl_protocols TLSv1 TLSv1.1 TLSv1.2; # Dropping SSLv3, ref: POODLE
	ssl_prefer_server_ciphers on;

	##
	# Logging Settings
	##

	access_log /var/log/nginx/access.log;
	error_log /var/log/nginx/error.log;

	##
	# Gzip Settings
	##

	gzip on;

	# gzip_vary on;
	# gzip_proxied any;
	# gzip_comp_level 6;
	# gzip_buffers 16 8k;
	# gzip_http_version 1.1;
	# gzip_types text/plain text/css application/json application/javascript text/xml application/xml application/xml+rss text/javascript;

	##
	# Virtual Host Configs
	##

	include /etc/nginx/conf.d/*.conf;
	include /etc/nginx/sites-enabled/*;
}


#mail {
#	# See sample authentication script at:
#	# http://wiki.nginx.org/ImapAuthenticateWithApachePhpScript
# 
#	# auth_http localhost/auth.php;
#	# pop3_capabilities "TOP" "USER";
#	# imap_capabilities "IMAP4rev1" "UIDPLUS";
# 
#	server {
#		listen     localhost:110;
#		protocol   pop3;
#		proxy      on;
#	}
# 
#	server {
#		listen     localhost:143;
#		protocol   imap;
#		proxy      on;
#	}
#}

Since we are investigating the default Nginx Virtual Host configurations, check the section commented with Virtual Host Configs to see what is going on. In case you are wondering, comments in Nginx configurations start with a # character.

Given that, we can see that the main configuration file will include:

  • any configuration file ending with .conf inside the /etc/nginx/conf.d/ directory.
  • all configuration files inside the /etc/nginx/sites-enabled/ directory.

Given these points, we can then look inside the /etc/nginx/conf.d/ and /etc/nginx/sites-enabled/ directories for the default configuration file.

Understanding the Nginx default configuration file

Within those two directories, you should be able to find a file that contain the default Virtual Host configurations. In the case of my Raspbian Buster Lite operating system, I found a symbolic link /etc/nginx/sites-enabled/default that points to /etc/nginx/sites-available/default. When we have such a file organization, we can remove the default Nginx configurations without deleting the actual file.

Let's run the following command to see what is in the default Nginx configuration file:

cat /etc/nginx/sites-available/default

After running the above command, you should get something similar to the following:

##
# You should look at the following URL's in order to grasp a solid understanding
# of Nginx configuration files in order to fully unleash the power of Nginx.
# https://www.nginx.com/resources/wiki/start/
# https://www.nginx.com/resources/wiki/start/topics/tutorials/config_pitfalls/
# https://wiki.debian.org/Nginx/DirectoryStructure
#
# In most cases, administrators will remove this file from sites-enabled/ and
# leave it as reference inside of sites-available where it will continue to be
# updated by the nginx packaging team.
#
# This file will automatically load configuration files provided by other
# applications, such as Drupal or WordPress. These applications will be made
# available underneath a path with that package name, such as /drupal8.
#
# Please see /usr/share/doc/nginx-doc/examples/ for more detailed examples.
##

# Default server configuration
#
server {
	listen 80 default_server;
	listen [::]:80 default_server;

	# SSL configuration
	#
	# listen 443 ssl default_server;
	# listen [::]:443 ssl default_server;
	#
	# Note: You should disable gzip for SSL traffic.
	# See: https://bugs.debian.org/773332
	#
	# Read up on ssl_ciphers to ensure a secure configuration.
	# See: https://bugs.debian.org/765782
	#
	# Self signed certs generated by the ssl-cert package
	# Don't use them in a production server!
	#
	# include snippets/snakeoil.conf;

	root /var/www/html;

	# Add index.php to the list if you are using PHP
	index index.html index.htm index.nginx-debian.html;

	server_name _;

	location / {
		# First attempt to serve request as file, then
		# as directory, then fall back to displaying a 404.
		try_files $uri $uri/ =404;
	}

	# pass PHP scripts to FastCGI server
	#
	#location ~ \.php$ {
	#	include snippets/fastcgi-php.conf;
	#
	#	# With php-fpm (or other unix sockets):
	#	fastcgi_pass unix:/run/php/php7.3-fpm.sock;
	#	# With php-cgi (or other tcp sockets):
	#	fastcgi_pass 127.0.0.1:9000;
	#}

	# deny access to .htaccess files, if Apache's document root
	# concurs with nginx's one
	#
	#location ~ /\.ht {
	#	deny all;
	#}
}


# Virtual Host configuration for example.com
#
# You can move that to a different file under sites-available/ and symlink that
# to sites-enabled/ to enable it.
#
#server {
#	listen 80;
#	listen [::]:80;
#
#	server_name example.com;
#
#	root /var/www/example.com;
#	index index.html;
#
#	location / {
#		try_files $uri $uri/ =404;
#	}
#}

Indeed, by looking at the information provided in this file, we can learn a lot about the Nginx server. If you want to be more proficient with Nginx, then you will want to access the resources provided in the comments.

However, the goal of this post is to understand what the default Nginx virtual host (or server) configuration does to our server. So let us focus on that for the moment.

From the configuration file, we can see that there is only one server block that is not commented out. Therefore, this is the configuration block that Nginx will take in.

The first two uncommented statements tell Nginx to listen to network packets at port 80 of the computer that it is running on:

	listen 80 default_server;
	listen [::]:80 default_server;

The first statement is for the case of a network interface holding an IPv4 address and the second one is for the case of a network interface holding an IPv6 address. In addition to that, the default_server parameter states that this server block will be used as the default configuration for Nginx.

Next,

root /var/www/html;

tells Nginx to look inside the /var/www/html directory on the server to look for files to serve HTTP requests directed at this server block.

After that,

server_name _;

marks the server block as a "catch all" block. Whenever Nginx cannot find any server block to match an incoming HTTP request, this server block will be used for deciding how to serve that request.

Finally,

    location / {
        # First attempt to serve request as file, then
        # as directory, then fall back to displaying a 404.
        try_files $uri $uri/ =404;
    }

will get Nginx to look for a file inside /var/www/html directory to return as the HTTP response for the incoming HTTP request. In case there is nothing to return, Nginx will return a HTTP response with a 404 status.

But how does the Nginx welcome page gets returned when we try to access the root url? If you trace the configurations from the main file, then you will see the following configuration:

index index.html index.htm index.nginx-debian.html;

This will cause Nginx to return one of the following files inside the root directory, if available:

  • index.html
  • index.htm
  • index.nginx-debian.html

Since there is a file named as index.nginx-debian.html inside /var/www/html, the contents of the file will be returned when we try to access the root url.

About Clivant

Clivant a.k.a Chai Heng enjoys composing software and building systems to serve people. He owns techcoil.com and hopes that whatever he had written and built so far had benefited people. All views expressed belongs to him and are not representative of the company that he works/worked for.