首页 > 解决方案 > Docker 运行后配置的最佳方式

问题描述

我对 Docker 很陌生,我正在尝试找到在我的容器启动后进行 Docker 配置的最佳方式。我们使用该docker-compose文件来构建我们的容器,我们的 compose 文件看起来像这样。

version: "3"

  php:
    image: wodby/drupal-php:$PHP_TAG
    container_name: "${PROJECT_NAME}_php"
    environment:   
      DB_HOST: $DB_HOST
      DB_PORT: $DB_PORT
      DB_USER: $DB_USER
      DB_PASSWORD: $DB_PASSWORD
      DB_NAME: $DB_NAME
      DB_DRIVER: $DB_DRIVER
      PHP_FPM_USER: wodby
      PHP_FPM_GROUP: wodby
      COLUMNS: 80 # Set 80 columns for docker exec -it.
    volumes:
      - ./Insider:/var/www/html

  nginx:
    image: wodby/nginx:$NGINX_TAG
    container_name: "${PROJECT_NAME}_nginx"
    depends_on:
      - php
    environment:
      NGINX_STATIC_OPEN_FILE_CACHE: "off"
      NGINX_ERROR_LOG_LEVEL: debug
      NGINX_BACKEND_HOST: php
      NGINX_SERVER_ROOT: /var/www/html/web
      NGINX_VHOST_PRESET: $NGINX_VHOST_PRESET
    ports:
      - '8000:80'
    volumes:
      - ./Insider:/var/www/html

现在我们需要在PHP容器启动后执行一些设置任务。现在我需要了解在这个容器中执行配置的最佳方式是什么。我们有两个想法,它们如下。

  1. 编写一个 shell 脚本并将其作为我们构建过程中的任务之一。
  2. 使用 ansible 并从不同的服务器连接来进行配置。

但理想的过程是,如果我们可以从我们的docker-compose.yml文件中以某种方式在 PHP 容器中包含一个 shell 脚本,并且当我们运行docker-compose up -d它时,它应该作为该容器启动过程的一部分运行并准备好一切,所以我们不需要经历 2nd命令/进程等。

标签: shelldockerdocker-composeprovisioning

解决方案


有一个为此使用入口点脚本的标准模式。

无论您指定为容器的入口点,都将作为主容器进程运行,并将容器的命令作为命令行参数传递。一个非常典型的入口点脚本具有以下形式

#!/bin/sh

# ... do startup-time setup ...

# Then launch the main container command
exec "$@"

在您的 Dockerfile 中,您需要照常复制它

COPY entrypoint.sh ./
# RUN chmod 0755 entrypoint.sh # if not already executable
ENTRYPOINT ["./entrypoint.sh"] # MUST be JSON-array form
CMD ["./my-app"]

入口点脚本可以访问每个执行的设置,例如在 中设置的环境变量docker-compose.yml,并联系在 Docker 中运行的其他服务。它可以export是主容器进程将看到的环境变量。(这些不会出现在其他面向调试的路径中,例如docker inspector docker exec,但docker run --rm -it myimage sh会看到它们。)一个重要的警告是入口点脚本将是此时容器中唯一运行的东西,因此它不能与除非它不遗余力地启动它(这很棘手),否则主容器进程将是什么。

我认为这种使用ENTRYPOINT非常有用且足够重要,以至于我倾向于为此目的保留该指令。如果您只有一个ENTRYPOINT(像许多 Java SO 问题一样),您可以将其更改为CMD没有不良影响。如果您曾经ENTRYPOINT命名解释器和CMD脚本(就像许多 Python SO 问题一样),您可以将它们组合成CMD一行。


推荐阅读