首页 > 解决方案 > Docker compose:如何定义指向容器内某个文件而不是物理服务器的 env_file

问题描述

我在docker-compose文件中运行了一些服务:

myService:  
          image: 127.0.0.1:myimage
          stdin_open: true
          tty: true
          ports:
            - target: 8800
              published: 8800
              protocol: tcp
              mode: host
          deploy:
            mode: global
            resources:
              limits:
                memory: 1024M
            placement:
              constraints:
                - node.labels.myLabel== one
          env_file:
            - /opt/app/myFile.list # I WANT TO REUSE SOME FILE INSIDE THE CONTAINER
          healthcheck:
            disable: true

如您所见,我需要声明一个环境文件:

env_file:
     - /opt/app/myFile.list # I WANT TO REUSE SOME FILE INSIDE THE CONTAINER

我的目的是如何重用容器内的一些文件而不是指向物理机。

建议?

标签: dockerdocker-composedockerfiledocker-swarmdocker-machine

解决方案


Docker (Compose) 本身并不能直接支持这一点,但它很容易添加到您的图像中。

请记住,有两种机制可以将命令行传递给 Docker。如果同时使用入口点和命令,则入口点作为主容器进程启动,并将命令作为参数传递。这使您可以进行首次设置(例如设置环境变量),然后exec执行命令。

此类应用程序的典型入口点脚本可能如下所示

#!/bin/sh
if [ -n "$ENV_FILE" ]; then
  . "$ENV_FILE"
fi
exec "$@"

您将其添加到您的 Docker 映像中

...
COPY entrypoint.sh /
RUN chmod +x /entrypoint.sh
ENTRYPOINT ["/entrypoint.sh"]
CMD ["same", "as", "before"]

(有几个变体用于ENTRYPOINT命名主应用程序或只是一个语言解释器。对于这种模式,您需要将其移至CMD.)

然后,当您启动容器时,设置入口点脚本正在寻找的环境变量。

services:
  myservice:
    environment:
      ENV_FILE: /opt/app/myFile.list # inside the container

如果您使用 启动调试 shell docker run --rm myimage sh,它将通过入口点脚本,您将看到这些环境变量。 docker exec绕过入口点,您不会得到相同的环境。像这样的低级调试工具docker inspect也不会显示环境变量。


推荐阅读