How does nginx distribute traffic among IPs associated with an upstream DNS name?

With this configuration:

upstream some_upstream {
  server some-elb.us-east-1.elb.amazonaws.com:80;
}

If some-elb.us-east-1.elb.amazonaws.com maps to 2 IP addresses, how will nginx distribute requests among them? Round-robin? (Say for version 1.1.19, in case the behavior changed at some point.)

Also, I read here that nginx caches DNS results on startup. If you use a variable, it will refresh them, but only if you have configured a DNS resolver. So if I haven't configured a DNS resolver, then what happens if one of the IPs for some-elb.us-east-1.elb.amazonaws.com changes? Will nginx continue to send traffic to the same set of IPs it found at startup?


Solution 1:

Please note that nginx 1.1.19 is a development version that went out 3+ years ago. As a good sysadmin, nothing of this kind should go live in your business. Let's focus on your actual question now.


As explained by the documentation :

  • About the usage of a domain name as a server entry :

A domain name that resolves to several IP addresses defines multiple servers at once.

  • About the usage of server entries in upstream blocks :

By default, requests are distributed between the servers using a weighted round-robin balancing method.


For the resolver part : yes nginx will issue domain name lookups for server entries on startup then cache any result until you restart it if you use static domain names in your configuration.

Your link points towards a post about reverse proxying and particularly the handling of domain names in the proxy_pass directive. This is a different case where you need to use variables in the directive value to force nginx to update its DNS cache : using the resolver directive for this particular case isn't sufficient.

Now, getting back to the server directive. Using the resolver directive and adding the resolve parameter will allow monitoring DNS records change and auto-reloading the new server list:

resolve
   monitors changes of the IP addresses that correspond to a domain name of 
   the server, and automatically modifies the upstream configuration without 
   the need of restarting nginx (1.5.12).

   In order for this parameter to work, the resolver directive must be
   specified in the http block.