【问题标题】:How do I run multiple sites on the same server using docker and nginx?如何使用 docker 和 nginx 在同一台服务器上运行多个站点?
【发布时间】:2021-11-09 15:54:44
【问题描述】:

我试图在同一台服务器上以不同的 ip 在 django 上运行两个站点,出现端口繁忙的错误,我修复了端口,但站点无法启动。请告诉我错误在哪里? ip 工作,当我转到第二个 ip 时,我会重定向到第一个站点。为第二个站点指定了所有设置。最后,我添加了第一个站点的nginx设置

这是第二个 docker-compose 文件及其设置。非常感谢您的帮助

.env

#Django
# Should be one of dev, prod
MODE=prod
PORT=8008

#postgres
DB_NAME=xxx
DB_USER=xxx
DB_HOST=xxx
DB_PASSWORD=xxxx
DB_PORT=5432
POSTGRES_PASSWORD=mysecretpassword

#WSGI
WSGI_PORT=8008
WSGI_WORKERS=4
WSGI_LOG_LEVEL=debug

# Celery
CELERY_NUM_WORKERS=2

# Email
EMAIL_HOST_USER=xxxx
EMAIL_HOST_PASSWORD=xxxx

docker-compose.yml

version: '3'

services:

  backend:
    build: ./
    container_name: site_container
    restart: always
    command: ./commands/start_server.sh
    ports:
      - "${PORT}:${WSGI_PORT}"
    volumes:
      - ./src:/srv/project/src
      - ./commands:/srv/project/commands
      - static_content:/var/www/site
    env_file:
      - .env
    depends_on:
      - postgres

  postgres:
    image: postgres:12
    volumes:
      - pg_data:/var/lib/postgresql/data
    env_file:
      - .env
#    environment:
#      - DJANGO_SETTINGS_MODULE=app.settings.${MODE}

  nginx:
    image: nginx:1.19
    volumes:
      - ./nginx:/etc/nginx/conf.d
      - static_content:/var/www/site
    ports:
      - 81:80
      - 444:443
    env_file:
      - .env
    depends_on:
      - backend

volumes:
  pg_data: {}
  static_content: {}

default.conf

server {
    listen 80 default_server;

    server_name 183.22.332.12;

    location /static/ {
        root /var/www/site;
    }

    location /media/ {
        root /var/www/site;
    }

    location / {
        proxy_set_header Host $host;
        proxy_pass http://backend:8010;
    }
}

第一个站点的default.conf

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

    server_name site1 ip_site1;

    ssl_certificate /etc/letsencrypt/live/site1/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/site1/privkey.pem;
    ssl_trusted_certificate /etc/letsencrypt/live/site1/chain.pem;

    location /static/ {
        root /var/www/artads;
    }

    location /media/ {
        root /var/www/artads;
    }

    location / {
        proxy_set_header Host $host;
        proxy_pass http://backend:8008;
    }
}

server {
    listen 80 default_server;

    server_name ip_site2 site2;

    location /static/ {
        root /var/www/gdr_mr;
    }

    location /media/ {
        root /var/www/gdr_mr;
    }

    location / {
        proxy_set_header Host $host;
        proxy_pass http://backend:8013;
    }
}

server {
        listen 80;
        listen [::]:80;

        server_name www.site1 site1;

        location / {
                return 301 https://site1$request_uri;
        }
}

【问题讨论】:

  • 在 Django 上运行两个站点是什么意思?您必须使用相同的 Django 后端进行前端吗?如果您能更好地解释您的情况,那将有所帮助。另外,请提供您遇到的错误和有效的撰写文件
  • @NoamYizraeli 不,有 2 个不同的项目
  • @Oleksandr 似乎您在 8013 和 8008 运行两个站点,您需要确保两个应用程序中的 UWSGI 都没有使用该端口。
  • 您是否在同一个 docker 容器中运行这两个 django 项目?
  • 如果有人需要答案,在俄文版ru.stackoverflow.com/questions/1329007/…

标签: django nginx docker-compose


【解决方案1】:

感谢@Roman Tokaren 和@Oleksandr

这里是@Roman Tokaren here提交的英文翻译版


对于“正确”的发布,您总是可以争论很多——毕竟,有多少人,有多少意见,但我将描述一个示例 + - 一个“方便”且可扩展的配置。为了在这种配置下工作的“方便”,我建议安装nginxproxymanager作为反向代理并将容器和nginxproxymanager组合到一个网络中——之后可以通过http(s)转发容器端口, tcp、udp 到使用 GUI 的外部接口以及许多其他好东西,例如 SSL 证书的生成及其自动更新


首先,让我们自己创建网络

docker network create --driver bridge --subnet 172.26.0.0/24 testnet

让我们配置 NPM (nginxproxymanager) - 默认情况下,我们会将反向代理视为最后一个网络节点,结果我们会得到

version: "3"
services:
  app:
    image: 'jc21/nginx-proxy-manager:latest'
    networks:
      testnet:
        ipv4_address: 172.26.0.254
    restart: always
    ports:
      # Public HTTP Port:
      - '80:80'
      # Public HTTPS Port:
      - '443:443'
      # Admin Web Port:
      - '81:81'
    environment:
      # These are the settings to access your db
      DB_MYSQL_HOST: "172.26.0.253"
      DB_MYSQL_PORT: 3306
      DB_MYSQL_USER: "user"
      DB_MYSQL_PASSWORD: "pwd"
      DB_MYSQL_NAME: "npm"
    volumes:
      - ./data/nginx-proxy-manager:/data
      - ./letsencrypt:/etc/letsencrypt
    depends_on:
      - db
  db:
    image: yobasystems/alpine-mariadb:latest
    restart: always
    networks:
      testnet:
        ipv4_address: 172.26.0.253
    environment:
      MYSQL_ROOT_PASSWORD: "pwd"
      MYSQL_DATABASE: "npm"
      MYSQL_USER: "user"
      MYSQL_PASSWORD: "pwd"
    volumes:
      - ./data/mariadb:/var/lib/mysql
networks:
  testnet:
    external: true

并配置容器本身

version: '3'
services:
  backend:
    build: ./
    container_name: site_container
    restart: always
    command: ./commands/start_server.sh
    networks:
      testnet:
        ipv4_address: 172.26.0.2
    volumes:
      - ./src:/srv/project/src
      - ./commands:/srv/project/commands
      - static_content:/var/www/site
    env_file:
      - .env
    depends_on:
      - postgres

  postgres:
    image: postgres:12
    volumes:
      - pg_data:/var/lib/postgresql/data
    env_file:
      - .env
#    environment:
#      - DJANGO_SETTINGS_MODULE=app.settings.${MODE}

networks:
  testnet:
    external: true
volumes:
  pg_data: {}
  static_content: {}

之后我们根据instructions进行NPM的初始配置并添加主机

【讨论】:

    【解决方案2】:

    如果你想在一台服务器上运行多个站点,你可以

    1. 使用不同的ip
    2. 使用不同的port
    3. 使用不同的domain
    4. 使用不同的路径并重写 ...

    您可以选择最重要的提示之一。

    在您的配置中,您选择不同的 ip 和相同的端口,但您将所有站点设置为默认值,而不是监听不同的 ip

    server{
          listen      ip:port;
    }
    

    通常只是省略 IP。

    或者你可以一个ip和不同的端口。

    server{
          listen      port1;
    }
    
    server{
          listen      port2;
    }
    

    或者你可以一个ip和一个端口但是不同的域。

    server{
          listen      port;
          server_name 1.a.com;
    }
    
    server{
          listen      port;
          server_name 2.a.com;
    }
    

    【讨论】:

      【解决方案3】:

      如果您在同一台机器上运行两个具有不同 IP 的虚拟服务器,您需要在监听指令中指定 IP 地址:

      server {
          listen      192.168.1.1:80;
          server_name example.net www.example.net;
          ...
      }
      
      server {
          listen      192.168.1.2:80;
          server_name example.com www.example.com;
          ...
      }
      

      更多关于nginx如何处理请求的信息可以在这里找到:http://nginx.org/en/docs/http/request_processing.html

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2010-10-21
        • 1970-01-01
        • 2017-04-23
        • 2016-01-02
        • 1970-01-01
        • 1970-01-01
        • 2012-12-05
        • 2016-05-10
        相关资源
        最近更新 更多