Docker中的Django而不暴露于LAN

时间:2019-03-28 18:21:57

标签: python django docker

在容器中运行Django时,除非使用python manage.py runserver 0.0.0.0:8000运行,否则无法访问它。但是,这样做会使我网络上的任何人都可以连接,这是我所不希望的。

在我的docker compose文件中,我有:

ports:
      - "8000:8000"

仅通过运行127.0.0.1:8000访问python manage.py runserver时,会出现ERR_EMPTY_RESPONSE错误。

是否可以在不打开整个网络的情况下访问服务器?

3 个答案:

答案 0 :(得分:1)

简而言之:容器内部的进程必须绑定到0.0.0.0才能从容器外部完全访问;但是您可以使用Docker Compose的ports:选项来控制实际可到达的位置。如果将其更改为"127.0.0.1:8000:8000",将无法从主机访问它。

Docker容器在an isolated network中运行。典型的设置可能如下所示:

 ^^^
Router
  | 192.168.1.1
  +--------------------+-- ...
  | 192.168.1.2        | 192.168.1.3
/- Host -----------\   Host 2
|    172.17.0.1    |
|     |            |
|     | 172.17.0.2 |
|  Container       |
\------------------/

作为实现的详细信息,每个容器都有自己的专用IP地址。这是在隔离的网络上:192.168.1.3/24上的第二个主机不知道172.17.0.0/16上的容器专用网络甚至不存在如何在此处路由流量的想法。由于每个容器都有自己的专用网络堆栈,因此每个容器也具有自己的localhost含义概念。

(将此图与直接在主机上运行的服务器进行比较。它可以在192.168.1.2上访问,但只能从同一网络访问;位于路由器远端的客户端无法访问192.168.1.0/24专用服务器网络,并且即使服务器绑定到“所有接口”,服务器也无法从公共Internet访问。)

如果将容器进程设置为仅绑定到它自己的lo0接口127.0.0.1,则它将不接受来自172.17.0.2 eth0接口的入站流量,这意味着外部任何内容都无法到达它。

如果将容器进程设置为绑定到0.0.0.0(“所有接口”),则它将接受来自主机的流量,从172.17.0.1(可能是docker0接口)发送。不过,这与接受来自“整个网络”的流量并不相同:如前所述,主机2仍然不知道如何在此处路由流量。

您可以使用docker run -p或Docker Compose ports:选项来限制Docker将端口发布到的接口。如果将ports:更改为"127.0.0.1:8000:8000",则可以从主机上的端口8000访问该容器,但只能通过主机的环回接口访问该容器;再次,主机2没有路由将数据包发送到该进程。

答案 1 :(得分:0)

您直接运行python manage.py runserver还是通过docker-compose命令运行? docker-compose run --rm [appname] sh -c 'python manage.py runserver' 如果正确配置了Dockerfile和dockercompose.yml,这就是应该做的事情。

postgreqsl数据库的docker-compose.yml示例:

version: "3"

services:
  app:
    build:
      context: .
    ports:
      - "8000:8000"
    volumes:
      - ./app:/app
    command: >
      sh -c "python manage.py wait_for_db &&
             python manage.py migrate &&
             python manage.py runserver 0.0.0.0:8000"
    environment:
      - DB_HOST=db
      - DB_NAME=app
      - DB_USER=postgres
      - DB_PASS=supersecretpassword
    depends_on:
      - db

  db:
    image: postgres:10-alpine
    environment:
      - POSTGRES_DB=app
      - POSTGRES_USER=postgres
      - POSTGRES_PASSWORD=supersecretpassword

Dockerfile:

FROM python:3.7-alpine
MAINTAINER Pshop

ENV PYTHONUNBUFFERED 1

COPY ./requirements.txt /requirements.txt
RUN apk add --update --no-cache postgresql-client
RUN apk add --update --no-cache --virtual .tmp-build-deps \
    gcc libc-dev linux-headers postgresql-dev
RUN pip install -r /requirements.txt
RUN apk del .tmp-build-deps

RUN mkdir /app
WORKDIR /app
COPY ./app /app

RUN adduser -D user
USER user

应用程序是您的项目名称

我是从本教程中得到的:https://www.udemy.com/django-python-advanced/

答案 2 :(得分:0)

您可以在docker-compose中创建自定义网络,请参阅文档here。您所需要做的就是找出或分配该网络的IP,然后在浏览器中键入其 IP:端口来访问该容器。