因此,我按照Docker的this教程创建了Django映像。
通过从项目的根目录运行docker-compose up
命令,它完全可以在本地计算机上运行。
但是,在将映像推送到docker hub https://hub.docker.com/repository/docker/vivanks/firsttry
之后我将图像拉到另一台机器上,然后运行:
docker run -p 8020:8020 vivanks/firsttry
但是它没有开始并显示此错误:
EXITED(0)
有人可以帮助我如何拉动该图像并运行它吗?
我的Dockerfile
FROM python:3
ENV PYTHONUNBUFFERED 1
RUN mkdir /code
WORKDIR /code
COPY requirements.txt /code/
RUN pip install -r requirements.txt
COPY . /code/
我的docker-compose.yml
version: '3'
services:
db:
image: postgres
environment:
- POSTGRES_DB=postgres
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=postgres
web:
build: .
command: python manage.py runserver 0.0.0.0:8000
volumes:
- .:/code
ports:
- "8000:8000"
depends_on:
- db
答案 0 :(得分:1)
您的Dockerfile
未指定CMD
或ENTRYPOINT
。当您运行...
docker run -p 8020:8020 vivanks/firsttry
...该容器没有任何关系(这意味着它实际上将尝试启动Python交互式shell,但是由于您没有使用-t
分配终端,因此该shell会成功退出。)在您的docker-compose.yml
中,您传递了一个明确的命令:
command: python manage.py runserver 0.0.0.0:8000
因此等效的docker run
命令行如下所示:
docker run -docker run -p 8020:8020 vivanks/firsttry python manage.py runserver 0.0.0.0:8000
但是您可能想像这样将其烘烤到Dockerfile
中:
CMD python manage.py runserver 0.0.0.0:8000
答案 1 :(得分:1)
正如@larsks在他的回答中提到的那样,您的问题是您的命令位于Compose文件中,而不是Dockerfile中。
要按原样在另一台计算机上运行项目,请使用以下docker-compose.yml
:
version: '3'
services:
db:
image: postgres
environment:
- POSTGRES_DB=postgres
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=postgres
web:
image: vivanks/firsttry:latest
command: python manage.py runserver 0.0.0.0:8000
ports:
- "8000:8000"
depends_on:
- db
如果您已经将CMD python manage.py runserver 0.0.0.0:8000
添加到Dockerfile并重建了映像,则上述内容可以进一步简化为:
version: '3'
services:
db:
image: postgres
environment:
- POSTGRES_DB=postgres
- POSTGRES_USER=postgres
- POSTGRES_PASSWORD=postgres
web:
image: vivanks/firsttry:latest
ports:
- "8000:8000"
depends_on:
- db
无论哪种情况,使用docker run
都会失败,因为它不会建立数据库。
编辑:
OP,我很佩服您的持久性,但同时也不了解使用Docker CLI而非docker-compose的坚持。我建议使用以上docker-compose.yml
个文件之一来启动您的应用。
尽管如此,我接受在没有docker-compose的情况下运行它的挑战。
当您使用docker run
命令时,您的应用程序无法启动,因为它尝试连接到主机db
上不存在的数据库。在您(和我的)docker-compose.yml
中,有一个名为 db 的服务的定义。 Docker-compose使用该定义为您设置数据库容器,并使其在主机名db
下可用于您的应用程序。
要在不使用docker-compose的情况下启动应用程序,您需要手动自动完成它为您所做的所有工作(以下命令假定您已将CMD...
添加到Dockerfile
:
docker network create --driver bridge django-test-network
docker run --detach --env POSTGRES_DB=postgres --env POSTGRES_USER=postgres --env POSTGRES_PASSWORD=postgres --network django-test-network --name db postgres:latest
docker run -it --rm --network django-test-network --publish 8080:8000 vivanks/firsttry:latest
以上3条命令将创建一个新的桥接网络,使用连接到该网络的正确配置的数据库创建并启动一个分离的(后台)容器,最后根据您的映像创建并启动一个附加的(前景)容器,该容器也已附加到该容器新网络。由于两个容器都位于相同的非默认桥接网络中,因此您的应用程序将能够将主机名db
解析为数据库容器的内部IP地址并正确启动。
使用Ctrl+C
将其关闭后,包含应用程序的容器将自行删除(因为它是使用选项--rm
启动的),但是您还需要手动清理其余的容器。为此,请运行以下命令:
docker stop db
docker rm -v db
docker network remove django-test-network
第一个停止数据库容器,第二个删除数据库容器和它的匿名卷,第三个删除网络。
我希望这能解释一切。