Docker-compose服务已退出,代码为0

时间:2019-10-17 08:53:08

标签: django docker uwsgi

我是Docker的新手。我正在尝试在Docker上运行Django。以下是我的 docker-compose 文件。

version: '2'
services:
    django:
        build:
          context: .
          dockerfile: ./deploy/dev/Dockerfile
        tty: true
        command: python manage.py runserver 0.0.0.0:8000
        ports:
              - "8000:8000"
        volumes:
            - ./app:/src/app
        depends_on:
            - "workflow_db"
            - "rabbitmq"
        env_file:
            - ./deploy/dev/envvar.env
    workflow_db:
        image: postgres:9.6
        volumes:
            - postgres_data:/var/lib/postgresql/data/
        environment:
            - POSTGRES_USER=hello_django
            - POSTGRES_PASSWORD=hello_django
            - POSTGRES_DB=hello_django
    rabbitmq:
        image: "rabbitmq:3-management"
        hostname: "rabbitmq"
        environment:
            RABBITMQ_ERLANG_COOKIE: "SWQOKODSQALRPCLNMEQG"
            RABBITMQ_DEFAULT_USER: "rabbitmq"
            RABBITMQ_DEFAULT_PASS: "rabbitmq"
            RABBITMQ_DEFAULT_VHOST: "/"
        ports:
            - "15672:15672"
            - "5672:5672"
volumes:
  postgres_data:

DockerFile

FROM python:3.7-alpine

RUN apk update && apk add --no-cache gcc libffi-dev g++ python-dev build-base linux-headers postgresql-dev postgresql postgresql-contrib pcre-dev bash alpine-sdk \
  && pip install wheel

#Copy over application files
COPY ./app /src/app

#Copy over, and grant executable permission to the startup script
COPY ./deploy/dev/entrypoint.sh /
RUN chmod +x /entrypoint.sh

WORKDIR /src/app

#Install requirements pre-startup to reduce entrypoint time
RUN pip install -r requirements.txt

ENTRYPOINT [ "/entrypoint.sh" ]

最后是我的 entrypoint.sh

#! /bin/bash

cd /src/app || exit

echo "PIP INSTALLATION" && pip install -r requirements.txt

echo "UPGRADE" && python manage.py migrate

# echo "uwsgi" && uwsgi "uwsgi.ini"

我做django-compose build,它会建立图像。但是当我做docker-compose up django_1 exited with code 0时。

但是,如果我取消注释entrypoint.sh的最后一行,它将运行得很好。

有人可以帮助我了解其背后的原因吗?

3 个答案:

答案 0 :(得分:1)

当您同时拥有命令和入口点时,Docker仅运行 入口点,并将命令作为参数传递给它。请参阅Dockerfile文档中的Understand how CMD and ENTRYPOINT interact。入口点一退出,容器就结束了;它可以在命令部分做任何喜欢的事情,包括完全忽略它。

典型做法是使用以下符号结束入口点脚本

exec "$@"

这导致它只接受其命令行参数并将其作为命令运行,从而将入口点脚本替换为主容器进程。

否则,您将到达入口点脚本的结尾,并且容器已完成了被告知要执行的所有操作,因此容器成功退出(状态代码0)。

答案 1 :(得分:0)

AFAIU,当您取消注释入口点的最后一行时,容器不再具有可以保持其正常运行的前台进程,因此它以状态0退出。入口点必须具有一个前台进程以保持容器正常运行&运行。另外,您多次执行“ pip安装”。这一步应该只是在Dockerfile中。

尝试将python manage.py runserver 0.0.0.0:8000本身移至entrypoint.sh

更新-

在端口冲突的情况下,容器将不会以状态0退出并且STDOUT中出现端口冲突错误。同样,当他不加评论时,也没有端口冲突的机会。因此,似乎前台进程根本没有执行。

答案 2 :(得分:0)

如果要使容器保持运行,则需要执行以下操作之一

  1. 运行前台进程
  2. 通过--ti连接到其终端

您需要与终端连接,以在未执行uwsgi时查看python命令是否失败,从而停止容器