Question

Docker Ngnix 502 Bad gateway error

Posted October 5, 2021 83 views
NginxDockerDjangoReact

My docker containers have two main services including react, django. After building, my React app homepage can run while Django admin/api return 502 bad gateway error.

Much appreciate if anyone can help to show errors in my below codes.

Many thanks.

docker-compose.yml

version: "3.8"

services:
  django:
    build:
      context: ./backend
      dockerfile: Dockerfile.prod
    volumes:
      - django_static_volume:/usr/src/app/static
    expose:
      - 8000
    env_file:
      - ./backend/.env
    command: gunicorn backend.wsgi:application --bind 0.0.0.0:8000
    depends_on:
      - db
  db:
    image: postgres:13.0-alpine
    volumes:
      - postgres_data:/var/lib/postgresql/data/
    env_file:
      - ./postgres/.env
  react:
    build:
      context: ./frontend
      dockerfile: Dockerfile.prod
      args:
        - API_SERVER=${ENV_API_SERVER}
    volumes:
      - react_static_volume:/usr/src/app/build/static
    expose:
      - 3000
    env_file:
      - .env
    command: serve -s build -l 3000
    depends_on:
      - django
  nginx:
    # restart: always
    build: ./nginx
    volumes:
      - django_static_volume:/usr/src/app/django_files/static
      - react_static_volume:/usr/src/app/react_files/static
      - ./nginx/production:/etc/nginx/conf.d
      - ./nginx/certbot/conf:/etc/letsencrypt
      - ./nginx/certbot/www:/var/www/certbot
    ports:
      - 80:80
      - 443:443
    depends_on:
      - react
      - django
  certbot:
    image: certbot/certbot
    restart: unless-stopped
    volumes:
        - ./nginx/certbot/conf:/etc/letsencrypt
        - ./nginx/certbot/www:/var/www/certbot
    entrypoint: "/bin/sh -c 'trap exit TERM; while :; do certbot renew; sleep 12h & wait $${!}; done;'"       
volumes:
  postgres_data:
  django_static_volume:
  react_static_volume:

default.conf

upstream django_backend {
    server django:8000;
}

upstream react_frontend {
    server react:3000;
}

server {
    listen 80;
    server_name mydomain.com;
    server_tokens off;

    location /.well-known/acme-challenge/ {
        root /var/www/certbot;
    }

    location / {
        return 301 https://$host$request_uri;
    }
}
server {
    listen 443 ssl;
    server_name mydomain.com;
    server_tokens off;

    ssl_certificate /etc/letsencrypt/live/mydomain.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/mydomain.com/privkey.pem;
    include /etc/letsencrypt/options-ssl-nginx.conf;
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;

    client_max_body_size 20M;
    ###########
        # URL ROUTING #
        ###########
    location /admin {
        proxy_pass http://django_backend;
        proxy_set_header X-Forwarded-Proto https;
        proxy_set_header X-Url-Scheme $scheme;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $http_host;
        proxy_redirect off;
    }

    location /api {
        proxy_pass http://django_backend;
        proxy_set_header X-Forwarded-Proto https;
        proxy_set_header X-Url-Scheme $scheme;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $http_host;
        proxy_redirect off;
    }

    ###########
    # STATIC FOLDER ROUTING #
    ###########

    location /static/admin/ {
        alias /usr/src/app/django_files/static/admin/;
    }

    location /static/rest_framework/ {
        alias /usr/src/app/django_files/static/rest_framework/;
    }

    location /static/ {
        alias /usr/src/app/react_files/static/;
    }

    location /media/ {
        alias /usr/src/app/media/;
    }

    ###########
    # URL ROUTING #
    ###########

    location / {
        proxy_pass http://react_frontend;
        proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
        proxy_set_header Host $host;
        proxy_redirect off;
    }
}

These answers are provided by our Community. If you find them useful, show some love by clicking the heart. If you run into issues leave a comment, or add your own answer to help others.

×
Submit an Answer
1 answer

Hi @duongbui,

The 502 Bad Gateway error is always related to your Nginx config file.

From looking at it, I’ve noticed you’ve added two proxy locations for your bakend :

 location /admin {
        proxy_pass http://django_backend;

 location /api {
        proxy_pass http://django_backend;

both of those redirect to

upstream django_backend {
    server django:8000;
}

The same goes for your frontend.

Can you tr and replace:

proxy_pass http://django_backend;

with

proxy_pass http://localhost:8000

in both places?

The same goes for your frontend. Try replacing the proxy_pass with http://localhost:3000, restart Nginx and see what happens.

  • Thanks @KFSys for your kind reply. I successfully fixed the error. The error is because I forgot to input my droplet’s IP in Trusted field in the Database.

    • Hi @duongbui,

      I’m glad to hear you managed to resolve the issue! Sounds about right, not having the permission to access something results in such an error as well.

      Thank you for the confirmation!