我刚刚开始阅读本教程,并尝试将我的一些代码包装到docker中。这个问题对于您中的许多人来说可能听起来很耳熟,因为我可以看到非常相似的威胁,但是不幸的是我无法理解,所以决定在这里写下。
我使用python创建了一个电报聊天机器人。所有文件都位于/project/
下。我在/project/
calledDockerTelegramChatBot
下有另一个文件夹,其中有Dockerfile。
在DockerTelegramChatbot
内,我有两个文件Dockerfile
和requirements.txt
。
Dockerfile
的内容如下所示
# Use an official Python runtime as a parent image
FROM python:3.6-stretch
# Set the working directory to /app
WORKDIR /app
# Copy the current directory contents into the container at /app
COPY . /app
ADD . .
# Install any needed packages specified in requirements.txt
RUN pip install -r requirements.txt --default-timeout=100
# Make port 80 available to the world outside this container
EXPOSE 80
# Run app.py when the container launches
CMD pwd
CMD ls
CMD python /app/main_bot.py
我使用
构建图像docker build -t simpletelegramchatbot DockerTelegramChatBot/
并使用
运行它docker run -p 4000:80 simpletelegramchatbot
主要问题是如何解决“构建映像后没有此类文件或目录”的问题。但是,我也想知道解决这种情况的最佳实践是什么,如果我编辑dockerfile,是否每次都要从头开始构建它? “ pip安装要求”需要几分钟,并使整个过程变得很烦人。
答案 0 :(得分:1)
问::是否每次都要从头开始构建它? “ pip安装要求”需要几分钟,并使整个过程变得很烦人。
A:您可以使用已经预安装的所有python程序构建基础docker image
。然后,在实际程序的Dockerfile
中,您会说FROM xyz_img
,其中xyz_img是您构建的基本映像。从本质上讲,这将避免再次经历耗时的pip install
。
问::如何解决“构建映像后没有此类文件或目录”的问题
A :可以肯定有很多调试技巧。对我来说,最简单的方法是使您的docker容器保持活动状态并连接到其中以检查其中的目录。
要连接,您可以执行:docker exec -it CONTAINER_NAME bash
。
要使运行中的容器保持活动状态,最适合您的用例的可能是编写永不退出的python程序。例如。睡一分钟醒来,然后再睡一分钟。
答案 1 :(得分:0)
主要问题是如何解决“构建映像后没有此类文件或目录”的问题。
已经构建了一个映像,可以直接基于该映像启动一个容器,该容器运行一个交互式shell,而不是Dockerfile中的CMD:
docker run --rm -it simpletelegramchatbot bash
(注意:如果您常规使用ENTRYPOINT而不是CMD,则此命令行不起作用,这是我建议将CMD设置为默认值的两个原因之一。)
在运行docker build
时,每一步之后的输出还将包含一个长十六进制数。这些是有效的映像ID,例如,您可以在docker run
命令中使用这些ID,例如,通过在COPY步骤之后立即构建的中间映像上获取一个shell,来查看生成中间的情况。>
在描述项目布局时,听起来像是:
/project/
+-- main_bot.py
\-- DockerTelegramChatBot/
+-- Dockerfile
\-- requirements.txt
因此,当您运行docker build DockerTelegramChatBot
时,它仅 会看到该子目录,如果您查看生成的映像,则可能只会看到requirements.txt
文件。由于内部构建机制的原因,Docker实际上不可能访问父目录中的文件。解决这个问题非常简单:只需将两个文件移至父目录即可。
如果我编辑dockerfile,是否每次都要从头开始构建它? “ pip安装要求”需要几分钟的时间
是;但是,如果先前的docker build
从相同的映像开始并运行相同的命令,则Docker将跳过一个步骤。这称为层缓存。至关重要的是,如果其中涉及的任何文件发生更改,则任何COPY或ADD步骤都将中断层缓存。
一种非常常见的模式是复制少量文件,这些文件描述了如何获取需求(requirements.txt
,package.json
,Gemfile
,...),安装需求,然后安装其余的源代码。如果pip install
文件更改,这将导致Docker仅重新运行requirements.txt
步骤。您的Dockerfile可能如下所示:
FROM python:3.6-stretch
WORKDIR /app
COPY requirements.txt ./
RUN pip install -r requirements.txt --default-timeout=100
COPY . ./
EXPOSE 80
CMD ["./main_bot.py"]