Докеризация приложения django с помощью Nginx, gunicorn и docker-compose - проблема с подключением базы данных

Здесь я программист-любитель. Обычно я могу найти выход из любой ситуации с помощью гугла, но мне сложно справиться с огромным разнообразием настроек для docker (и, честно говоря, я чувствую себя немного подавленным). Я знаю о самых больших учебниках (включая знаменитый digitalocean), но это не помогло.

Как сказано в заголовке, я пытаюсь докеризировать приложение django (для развертывания на VPS), используя Nginx en gunicorn.

В моем файле docker-compose есть служба базы данных, служба django_unicorn и контейнер nginx. Контейнеры базы данных и nginx, похоже, настроены правильно. Но когда запускается мой django_unicorn, он не может подключиться к базе данных.

Сообщение об ошибке:

django.db.utils.OperationalError: (2003, "Невозможно подключиться к серверу MySQL на 'db' ([Errno 111] Connection refused)")]

Через некоторое время он останавливается и дает мне сервер localhost для подключения, но, очевидно, ничего не показывает.

Я попробовал проверить базу данных внутри моего контейнера docker. Он работает нормально, и я подключаюсь к нему с пользователем root и моим пользовательским пользователем. Я использую точно такие же учетные данные в моем файле settings.py в django. HOST и PORT выглядят нормально (ссылаясь на службу db в docker-compose и используя порт 3306, как в docker-compose.

).

Я очень хочу, чтобы мне удалось запустить это локально и, возможно, вскоре перейти на VPS.

Моя организация папок :

whatsthefit

  • .venv
  • conf
    • _pycache
    • gunicorn_config.py
  • nginx
    • default.conf
    • Dockerfile
  • whatzthefit
    • App1
    • App2
  • manage.py
  • requirements.txt
  • dockerignore
  • .env
  • .gitignore
  • docker-compose.yml
  • Dockerfile
  • entrypoint.sh

Элемент списка

Мои установочные файлы :

файл docker-compose

version: "3.7"

services:
  db:
    image: mysql:oraclelinux8
    restart: always
    environment:
      - MYSQL_ROOT_PASSWORD=${MYSQL_ROOT_PASSWORD}
      - MYSQL_DATABASE=${DB_NAME}
      - MYSQL_USER=${DB_USER}
      - MYSQL_PASSWORD=${DB_PASS}
    ports:
      - "3306:3306"
    expose:
      - "3306"
    volumes:
      - data:/var/lib/mysql
    healthcheck:
      test: ["CMD", "mysqladmin", "ping", "-h", "localhost", "-u", "${DB_USER}", "-p${MYSQL_ROOT_PASSWORD}"]
      interval: 10s
      retries: 3

  django_gunicorn:
    volumes:
      - static:/static
    env_file:
      - /home/ynot/fitweb/whatzthefit/.env
    build:
      context: .
    ports:
      - "8080:8080"
    depends_on:
      - db


  nginx:
    build: ./nginx
    volumes:
      - static:/static
      - media:/media
    ports:
      - "84:84"
    depends_on:
      - django_gunicorn


volumes:
  static:
  data:
  media:

NGINX файл default.conf

upstream django {
    server django_gunicorn:8080;
}

server {
    listen 84;

    location / {
        proxy_pass http://django;
    }

    location /static/ {
        alias /static;
    }

    location /media/{
        alias /media;
    }
}

** nginx Dockerfile**

FROM nginx:1.25.4-alpine-slim

COPY ./default.conf /etc/nginx/conf.d/default.conf

Основной докерфайл

FROM nginx:1.25.4-alpine-slim

# replace the nginx default conf by the one we made in this folder
COPY ./default.conf /etc/nginx/conf.d/default.conf

entrypoint.sh

#!/bin/sh

python manage.py migrate --noinput
python manage.py collectstatic --noinput

gunicorn fitweb.wsgi:application --bind 0.0.0.0:8000

gunicorn_config.py

import os

command = "/home/ynot/fitweb/whatzthefit/.venv/bin/gunicorn"
pythonpath = "/home/ynot/fitweb/whatzthefit/whatzthefit"
bind = "0.0.0.0:8000"
workers = 3

Заранее благодарю за помощь. Прошу прощения за вываливание кода, но я надеюсь, что это облегчит поиск проблемы.

Если вы пытаетесь подключить базу данных MySQL в docker compose, попробуйте использовать links опции в docker-compose.yml.

Используя links, это означает, что контейнер может искать другой контейнер, который связан с ним.

Как показано ниже, вы можете добавить ссылку на db в сервисе django-gunicorn:

django_gunicorn:
volumes:
  - static:/static
env_file:
  - /home/ynot/fitweb/whatzthefit/.env
build:
  context: .
ports:
  - "8080:8080"
depends_on:
  - db
links:
  - db

Поскольку имя связанного сервиса db, вы можете просто использовать db в качестве имени хоста.

DATABASES = {
    'default': {
        'ENGINE': 'django.db.backends.mysql',
        'NAME': '<DB_NAME>',
        'USER': '<DB_USER>',
        'PASSWORD': '<DB_PASS>',
        'HOST': 'db',  # Linked docker name
        'PORT': '3306',
    }
}
Вернуться на верх