Home > Software engineering >  how to set run nginx config for running two frontend apps and a backend server
how to set run nginx config for running two frontend apps and a backend server

Time:04-27

I was trying to setup two frontend react applications sharing a server written in nodejs. I tried setting up one frontend application it worked correctly but gets an error host not found in upstream "server" in /etc/nginx/conf.d/default.conf when i add the other one.

here is my docker-compose

version: "3"
services:
  postgres:
    image: "postgres:latest"
    environment:
      - POSTGRES_PASSWORD=postgres_password
  nginx:
    depends_on:
      - api
      - client
      - client2
    restart: always
    build:
      dockerfile: Dockerfile.dev
      context: ./nginx
    ports:
      - "3050:80"
  api:
    build:
      dockerfile: Dockerfile.dev
      context: "./server"
    volumes:
      - /app/node_modules
      - ./server:/app
    environment:
      - PGUSER=postgres
      - PGHOST=postgres
      - PGDATABASE=postgres
      - PGPASSWORD=postgres_password
      - PGPORT=5432
  client:
    stdin_open: true
    environment:
      - CHOKIDAR_USEPOLLING=true
    build:
      dockerfile: Dockerfile.dev
      context: ./client
    volumes:
      - /app/node_modules
      - ./client:/app
  client2:
    stdin_open: true
    environment:
      - CHOKIDAR_USEPOLLING=true
    build:
      dockerfile: Dockerfile.dev
      context: ./client2
    volumes:
      - /app/node_modules
      - ./client2:/app

nginx default.conf

upstream client {
    server client:3000;
}

upstream client2 {
    server client:3000;
}

upstream api {
    server api:5000;
}

server {
    listen 80;

    location / {
        proxy_pass http://client;
    }

    location /login {
        proxy_pass http://client2;
    }

    location /sockjs-node {
        proxy_pass http://client;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "Upgrade";
    }

    location /api {
        rewrite /api/(.*) /$1 break;
        proxy_pass http://api;
    }
}

apart from the above my two frontend react applications (client, client2) also contains an nginx directory with default.conf client/nginx/default.conf

server{
    listen 3000;

    location / {
        root /usr/share/nginx/html;
        index index.html index.htm;
        try_files $uri $uri/ /index.html;
    }
}

client2/nginx/default.conf

one of my client Dockerfile.dev

FROM node:14.14.0-alpine
WORKDIR /app
COPY ./package.json ./
RUN npm i
COPY . .
CMD ["npm", "run", "start"]

one of my client Dockerfile

FROM node:14.14.0-alpine as builder
WORKDIR /app
COPY ./package.json ./
RUN npm i
COPY . .
RUN npm run build

FROM nginx
EXPOSE 3000
COPY ./nginx/default.conf /etc/nginx/conf.d/default.conf
COPY --from=builder /app/build /usr/share/nginx/html

CodePudding user response:

You can just use linuxserver/swag images for subdomains, and etc.. your files would be:

docker-compose.yaml:

  nginx:
    image: linuxserver/swag
    ports:
       - 80:80
       - 443:443
    volumes:
       - ./nginx/config:/config
       - ./nginx/default.conf:/config/nginx/site-confs/default
       - ./nginx/ssl.conf:/config/nginx/ssl.conf
    container_name: nginx
    networks:
      main:
    restart: unless-stopped
    environment: 
       - PUID=1000
       - PGID=1000
       - TZ=Europe/Berlin
       - URL=example.eu
       - SUBDOMAINS=www,something #put your domain seperated by ','
       - VALIDATION=http
       - STAGING= false #optional 
       - [email protected]
    depends_on:
       - client1
       - client2
       - api

something.subdomain.conf file for your subdomain in /nginx/config/nginx/proxy-confs:

server {
    listen 443 ssl;
    listen [::]:443 ssl;

    server_name client2.*; #client2 (your docker container for your second frontend) or your subdomain...

    include /config/nginx/ssl.conf;

    client_max_body_size 0;


    location / {

     include /config/nginx/proxy.conf;
     include /config/nginx/resolver.conf;
     set $upstream_app client2;
     set $upstream_port 3001;
     set $upstream_proto https;
     proxy_pass $upstream_proto://$upstream_app:$upstream_port;

 }
}

NGINX default.conf file:

upstream api {
    server api:5001;
}

upstream client {
    server client1:3000;
}



server {
  listen 80;
  listen [::]:80;
  server_name _;
  return 301 https://$host$request_uri;
  
}

# main server block
server {
  listen 443 ssl http2 default_server;
  listen [::]:443 ssl http2 default_server;

  server_name _;

  # enable subfolder method reverse proxy confs
  include /config/nginx/proxy-confs/*.subfolder.conf;

  # all ssl related config moved to ssl.conf
  include /config/nginx/ssl.conf;

  client_max_body_size 0;
   
    location / {
        proxy_pass http://client1;

        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_cache_bypass $http_upgrade;
    }


     location /api {
        proxy_pass http://api;

        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection 'upgrade';
        proxy_set_header Host $host;
        proxy_cache_bypass $http_upgrade;

    }
}
# enable subdomain method reverse proxy confs
include /config/nginx/proxy-confs/*.subdomain.conf;

Please read these for more info:

CodePudding user response:

You need to point your set your upstream clients in your nginx config to be the names of the services in your docker-compose. Specifically here, you need to change under client2

upstream client {
    server client:3000;
}

upstream client2 {
    server client2:3000;
}

upstream api {
    server api:5000;
}

server {
    listen 80;

    location / {
        proxy_pass http://client;
    }

    location /login {
        proxy_pass http://client2;
    }

    location /sockjs-node {
        proxy_pass http://client;
        proxy_http_version 1.1;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection "Upgrade";
    }

    location /api {
        rewrite /api/(.*) /$1 break;
        proxy_pass http://api;
    }
}
  • Related