nginx : upstream with multiple server directives?

after so rumbling & testing, I figured a way to make it work and be able to ship one config file per application.

Here it is, dispatched in one common file and a pair of upstream/location files per application:

  • /etc/nginx/conf.d/common-proxies.conf:

    include /upstreams/*.conf;
    
    server {
    include /locations/*.conf
    }
    
  • /etc/nginx/locations/backend1.conf

    location /backend1/ {
      upstream http://backend1;
    }
    
  • /etc/nginx/locations/backend2.conf

    location /backend2/ {
      upstream http://backend2;
    }
    
  • /etc/nginx/upstreams/backend1.conf

    upstream backend1 {
      http://localhost:8989;
    }
    
  • /etc/nginx/upstreams/backend2.conf

    upstream backend2 {
      http://localhost:8990;
    }
    

A http block can have many server children. However, nginx selects one server block to process a request. So, the request never 'sees' the backend2 location because it matches against the first server block.


Here is one such solution that works for me with basic authentication.

Install required packages to generate passwords using htpasswd

sudo yum install httpd-tools        [RHEL/CentOS]
sudo apt install apache2-utils      [Debian/Ubuntu]

create password files with below commands

htpasswd -c /home/osboxes/nginx1-auth.htpasswd  admin
htpasswd -c /home/osboxes/nginx2-auth.htpasswd  sysadmin
htpasswd -c /home/osboxes/glances-auth.htpasswd devopsadmin

nginx.conf file

    ###############Start-of-Nginx-Config-file #########
    
    events {}
    
    http {
    upstream backend_nginx1 {
        server nginx1;
    }
    upstream backend_nginx2 {
        server nginx2;
    }
    
    upstream backend_glances {
        server glances:61208;
    }
    
    
    
    server {
        listen 7070;
        server_name _;
        location / {
            #//turn on auth for this location
            auth_basic "Restricted";
            auth_basic_user_file /etc/nginx/nginx1-auth.htpasswd;
            proxy_pass http://backend_nginx1;
        }
    }
    
    server {
        listen 8080;
        server_name _;
        location / {
            #//turn on auth for this location
            auth_basic "Restricted";
            auth_basic_user_file /etc/nginx/nginx2-auth.htpasswd;
            proxy_pass http://backend_nginx2;
        }
    }
    
    server {
        listen 9090;
        server_name _;
        location / {
            #//turn on auth for this location
            auth_basic "Restricted";
            auth_basic_user_file /etc/nginx/glances-auth.htpasswd;
            proxy_pass http://backend_glances;
        }
    }
    
    
    }
#Proxy on nginx tcp port
stream {
  upstream postgres {
    server pdb3:5432;
  }
  server {
    listen 5432;
    proxy_pass postgres;
  }
}

Now deploying backend docker containers to be served by front-end nginx load-balancer

sudo docker run -d  --name nginx1  nginx

sudo docker run -d  --name nginx2  nginx

Glances container is a combination of top/htop for getting system/docker resources on console or on web browser.

sudo docker run -d --restart="always"  -e GLANCES_OPT="-w" -v /var/run/docker.sock:/var/run/docker.sock:ro --pid host --name glances docker.io/nicolargo/glances

Deploying Front-end nginx load-balancer to serve backend services/containers

sudo docker run -d --name nginx-reverseProxy  -p 7070:7070 -p 8080:8080 -p 9090:9090 --link nginx1:nginx1 --link nginx2:nginx2 --link glances:glances -v /home/osboxes/nginx.conf:/etc/nginx/nginx.conf -v  /home/osboxes/nginx1-auth.htpasswd:/etc/nginx/nginx1-auth.htpasswd  -v /home/osboxes/nginx2-auth.htpasswd:/etc/nginx/nginx2-auth.htpasswd -v /home/osboxes/glances-auth.htpasswd:/etc/nginx/glances-auth.htpasswd  nginx